Pular para o conteúdo principal

Emissão RTC (Reforma Tributária)

A NFS-e no layout da Reforma Tributária do Consumo (RTC) usa o mesmo método da emissão comum: client.service_invoices.create (ou create_and_wait). Não há recurso, URL nem cabeçalho diferente. O que liga o layout RTC é a presença do grupo ibsCbs no corpo. Com ele, a API valida o grupo na hora e grava os códigos da Reforma na nota.

O tipo ServiceInvoiceCreateParams já aceita ibsCbs e nbsCode. Consulta, cancelamento, PDF e XML funcionam igual.

O que foi provado​

Em 10/10/2026, notas RTC foram emitidas e canceladas com o SDK 0.1.0 numa empresa de teste (Simples Nacional, ambiente de testes):

CenárioResultado
Payload mínimo com ibsCbs202, Issued em ~5 s; ibsCbs e nbsCode devolvidos na consulta
Com ISS retido e retenções federaisIssued em ~4 s; retido 8,15 e líquido 91,85 numa nota de 100,00
operationIndicator com 7 dígitos400: ibsCbs.operationIndicator must be exactly 6 digits. Nenhuma nota criada
Sem nbsCodeAceito no ambiente de testes (veja o alerta abaixo)
CNPJ do tomador como str com zeros à esquerdaZeros preservados no XML
cancel_and_waitCancelled em ~3,5 s

Payload mínimo​

from decimal import Decimal

from nfeio import NfeClient
from nfeio.types import ServiceInvoiceCreateParams

client = NfeClient()
company_id = "ID_DA_EMPRESA"

params: ServiceInvoiceCreateParams = {
"cityServiceCode": "10677", # código de serviço do município
"federalServiceCode": "01.01", # item da LC 116, formato NN.NN
"nbsCode": "115021000", # NBS 1.1502.10.00, 9 dígitos sem pontos
"description": "Desenvolvimento de software sob encomenda",
"servicesAmount": Decimal("10.00"),
"ibsCbs": {
"operationIndicator": "100301", # indicador da operação: exatamente 6 dígitos
"classCode": "000001", # classificação tributária (cClassTrib): 6 dígitos
},
"borrower": {
"type": "LegalEntity",
"name": "Tomador Exemplo Ltda",
"federalTaxNumber": "11222333000181", # str preserva zeros à esquerda
"address": {
"country": "BRA",
"postalCode": "01310-200",
"street": "Avenida Paulista",
"number": "2000",
"district": "Bela Vista",
"city": {"code": "3550308", "name": "São Paulo"},
"state": "SP",
},
},
}

invoice = client.service_invoices.create_and_wait(
company_id, params, external_id="pedido-rtc-1001"
)
print(invoice.flow_status) # "Issued"
print(invoice["ibsCbs"]["operationIndicator"], invoice["nbsCode"])

O que cada campo pede:

CampoFormatoObservação
ibsCbs.operationIndicator6 dígitos, como strDefine o local de incidência e qual endereço a nota precisa trazer. 100301 (serviço prestado a distância) exige o endereço do tomador.
ibsCbs.classCode6 dígitos, como strClassificação tributária do IBS/CBS (000001 é tributação integral). Os 3 primeiros dígitos são o CST.
nbsCode9 dígitos, sem pontosPrecisa ser coerente com o item da LC 116 em federalServiceCode.
federalServiceCodeNN.NNItem da LC 116.
borrower.addresspostalCode, street, city.code (IBGE, 7 dígitos), city.name, stateObrigatórios quando um endereço brasileiro é informado.

Os valores de IBS e CBS não são enviados: a NFE.io calcula a partir de operationIndicator, classCode e servicesAmount. Os campos opcionais do grupo (purpose, destinationIndicator, compras governamentais, locação de bens móveis etc.) estão na documentação funcional do layout RTC. O par federalServiceCode × nbsCode × operationIndicator × classCode sugerido para cada serviço está na tabela de correlação LC 116 × NBS, e os indicadores, na tabela de indicador da operação.

O indicador da operação tem 6 dígitos

Alguns exemplos de payload RTC publicados usam operationIndicator com 7 dígitos ("1005011"). A API recusa com 400 e o SDK levanta InvalidRequestError. Use sempre 6 dígitos, como texto.

Com retenções​

As retenções continuam nos campos da raiz durante a transição, e convivem com o ibsCbs. Alíquotas são frações (0.02 = 2%):

from decimal import Decimal

from nfeio import NfeClient
from nfeio.types import ServiceInvoiceCreateParams

client = NfeClient()

params: ServiceInvoiceCreateParams = {
"cityServiceCode": "10677",
"federalServiceCode": "01.01",
"nbsCode": "115021000",
"description": "Consultoria em tecnologia",
"servicesAmount": Decimal("100.00"),
"ibsCbs": {"operationIndicator": "100301", "classCode": "000001"},
"retentionType": "WithheldByBuyer", # ISS retido pelo tomador
"issRate": Decimal("0.02"),
"issAmountWithheld": Decimal("2.00"),
"irAmountWithheld": Decimal("1.50"),
"pisAmountWithheld": Decimal("0.65"),
"cofinsAmountWithheld": Decimal("3.00"),
"csllAmountWithheld": Decimal("1.00"),
"borrower": {
"type": "LegalEntity",
"name": "Tomador Exemplo Ltda",
"federalTaxNumber": "11222333000181",
"address": {
"country": "BRA",
"postalCode": "01310-200",
"street": "Avenida Paulista",
"number": "2000",
"district": "Bela Vista",
"city": {"code": "3550308", "name": "São Paulo"},
"state": "SP",
},
},
}

invoice = client.service_invoices.create_and_wait(
"ID_DA_EMPRESA", params, external_id="pedido-rtc-1002"
)
print(invoice.amount_net) # 91.85 (Decimal)
print(invoice["amountWithheld"]) # 8.15 (float, como no JSON)
if str(invoice["retentionType"]).lower() != "withheldbybuyer":
print("retenção diferente da enviada")
  • Retenção de PIS/COFINS vai em pisAmountWithheld/cofinsAmountWithheld, nunca em pisAmount/cofinsAmount, que são o débito próprio.
  • Se nenhum campo de imposto federal for informado, a NFE.io calcula as retenções pela configuração da empresa. Envie os campos só quando o seu sistema já tiver os valores.
  • A API devolve retentionType com outra caixa (withheldByBuyer): compare sem diferenciar maiúsculas e minúsculas.
  • Não existe campo de retenção de IBS/CBS no layout.

Lendo a nota RTC​

Os campos da Reforma não têm propriedade tipada na versão 0.1: leia pelo nome do JSON, como invoice["ibsCbs"], invoice["nbsCode"], invoice["federalServiceCode"] e invoice["amountWithheld"]. Valores com propriedade tipada (invoice.amount_net, invoice.services_amount, invoice.iss_tax_amount) voltam como Decimal.

O CNPJ do tomador volta da API como número, sem os zeros à esquerda. Use a propriedade invoice.borrower.federal_tax_number, que devolve str com 11 ou 14 dígitos.

O que depende da empresa​

O contrato da API está provado. O resto depende da parametrização da empresa na NFE.io, e não do payload:

  • Para onde a nota vai. A emissão pelo Ambiente Nacional depende do cadastro da inscrição municipal da empresa ("Emitir via Emissor Nacional de NFS-e"). Na empresa de teste, que não está no Emissor Nacional, a nota saiu no modelo municipal, com CodigoNbs mas sem as tags de IBS/CBS no XML.
  • Cálculo de IBS/CBS. Nenhuma das notas de teste trouxe valores de IBS/CBS calculados. Isso é coerente com uma empresa do Simples Nacional em ambiente de testes: optantes pelo Simples Nacional e MEI, num primeiro momento, não testam as novas tags. Para validar o cálculo, use uma empresa do Lucro Presumido ou Real habilitada no Emissor Nacional, parametrizada pelo suporte.
  • nbsCode. A API aceitou nota sem NBS no ambiente de testes, mas o Ambiente Nacional rejeita NBS ausente ou incoerente com o item da LC 116. Envie sempre.
  • ISS. A alíquota vem do cadastro do código de serviço da empresa. Na empresa de teste (Simples Nacional, alíquota zero), issTaxAmount voltou 0.

Veja também​

NFE.io

A NFE.io é uma empresa de tecnologia que fornece soluções para automatizar e simplificar a emissão e gestão de notas fiscais eletrônicas. Com suas ferramentas, as empresas podem economizar tempo e reduzir erros, aumentando a eficiência e precisão do processo de emissão de notas fiscais.

Um dos principais cases de sucesso da NFE.io é a implementação da solução na empresa de transporte Rodonaves. Com a automatização da emissão e gestão de notas fiscais eletrônicas, a Rodonaves conseguiu reduzir em até 80% o tempo gasto nesse processo, o que se traduziu em uma significativa melhoria na eficiência operacional. Além disso, a empresa também conseguiu eliminar erros e atrasos na emissão de notas fiscais, o que melhorou a relação com seus clientes e aumentou a confiança dos órgãos fiscais.

Outro exemplo é a implementação da NFE.io na empresa de comércio eletrônico, a Loja Integrada. Com a automatização da emissão de notas fiscais, a Loja Integrada conseguiu aumentar a velocidade de emissão de notas em até 10 vezes, o que permitiu que a empresa atendesse a uma maior quantidade de clientes e, consequentemente, aumentar as suas vendas.

Além desses exemplos, a NFE.io também tem outros cases de sucesso com empresas de setores como indústria, construção, varejo e serviços, mostrando a versatilidade e eficácia da sua solução.

Em resumo, a NFE.io é uma empresa de tecnologia que oferece soluções para automatizar e simplificar a emissão e gestão de notas fiscais eletrônicas, ajudando as empresas a economizar tempo e reduzir erros, melhorando a eficiência e precisão do processo. Com cases de sucesso em diferentes setores, a NFE.io tem se destacado como uma empresa líder em automação fiscal.