Brunomm/br_nfe

View on GitHub
lib/br_nfe/product/nota_fiscal.rb

Summary

Maintainability
C
1 day
Test Coverage
module BrNfe
    module Product
        class NotaFiscal  < BrNfe::ActiveModelBase
            # include BrNfe::Association::HaveCondicaoPagamento

            # Identificação do emitente da NF-e
            # Versão do XML
            attr_accessor :versao

            # Identificação do emitente da NF-e
            #
            # <b>Type:     </b> _BrNfe.emitente_product_class
            # <b>Required: </b> _Yes_
            # <b>tag:      </b> emit
            #
            has_one :emitente, 'BrNfe.emitente_product_class', null: false
            alias_attribute :emit, :emitente

            # Identificação do Destinatário da NF-e
            #  Grupo obrigatório para a NF-e (modelo 55)
            #
            # <b>Type:     </b> _BrNfe.destinatario_product_class_
            # <b>Required: </b> _Yes_ (No if modelo_nf == 65)
            # <b>tag:      </b> dest
            #
            has_one :destinatario, 'BrNfe.destinatario_product_class', null: false
            alias_attribute :dest, :destinatario

            # Código do Tipo de Emissão da NF-e
            #  ✓ 1=Emissão normal (não em contingência);
            #  ✓ 6=Contingência SVC-AN (SEFAZ Virtual de Contingência do AN);
            #  ✓ 7=Contingência SVC-RS (SEFAZ Virtual de Contingência do RS);
            #  ✓ 9=Contingência off-line da NFC-e (as demais opções de contingência são válidas
            #      também para a NFC-e).
            #  Para a NFC-e somente estão disponíveis e são válidas as opções de contingência 5 e 9.
            #
            # <b>Type:     </b> _Number_
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _1_
            # <b>Length:   </b> _1_
            # <b>tag:      </b> tpEmis
            #
            attr_accessor :codigo_tipo_emissao
            alias_attribute :tpEmis, :codigo_tipo_emissao


            attr_accessor :chave_de_acesso

            def chave_de_acesso_dv
                chave_de_acesso[-1]
            end
            def chave_de_acesso_sem_dv
                chave_de_acesso[0..-2]
            end
            def chave_de_acesso
                @chave_de_acesso ||= gerar_chave_de_acesso!
            end


            # Código numérico que compõe a Chave de Acesso. Número aleatório gerado pelo
            # emitente para cada NF-e para evitar acessos indevidos da NF-e.
            # Resumo: É um código controlado pelo sistema. Pode por exemplo ser
            #        utilizado o ID da tabela da nota fiscal.
            #
            # <b>Type:     </b> _Number_
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _nil_
            # <b>Length:  </b> _max: 8_
            # <b>tag:      </b> cNF
            #
            attr_accessor :codigo_nf
            alias_attribute :cNF, :codigo_nf


            # Série do Documento Fiscal, preencher com zeros na hipótese
            # de a NF-e não possuir série. (v2.0)
            # Série 890-899: uso exclusivo para emissão de NF-e avulsa, pelo
            #    contribuinte com seu certificado digital, através do site do Fisco
            #    (procEmi=2). (v2.0)
            # Serie 900-999: uso exclusivo de NF-e emitidas no SCAN. (v2.0)
            #
            # <b>Type:     </b> _Number_
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _nil_
            # <b>Length:   </b> _max: 3_
            # <b>tag:      </b> serie
            #
            attr_accessor :serie

            # Número do Documento Fiscal.
            # Número da nota fiscal De fato
            #
            # <b>Type:     </b> _Number_
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _nil_
            # <b>Length:   </b> _max: 9_
            # <b>tag:      </b> nNF
            #
            attr_accessor :numero_nf
            alias_attribute :nNF, :numero_nf

            # Descrição da Natureza da Operação
            # Informar a natureza da operação de que decorrer a saída ou a
            # entrada, tais como: venda, compra, transferência, devolução,
            # importação, consignação, remessa (para fins de demonstração,
            # de industrialização ou outra), conforme previsto na alínea 'i',
            # inciso I, art. 19 do CONVÊNIO S/No, de 15 de dezembro de
            # 1970.
            #
            # <b>Type:     </b> _String_
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _'Venda'_
            # <b>tag:      </b> natOp
            #
            attr_accessor :natureza_operacao
            alias_attribute :natOp, :natureza_operacao

            # Indicador da forma de pagamento
            # 0=Pagamento à vista; (Default)
            # 1=Pagamento a prazo;
            # 2=Outros.
            #
            # <b>Type:     </b> _Number_ OR _String_
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _0_
            # <b>Length:   </b> _1_
            # <b>tag:      </b> indPag
            #
            attr_accessor :forma_pagamento
            alias_attribute :indPag, :forma_pagamento

            # Código do Modelo do Documento Fiscal
            # 55=NF-e emitida em substituição ao modelo 1 ou 1A; (Default)
            # 65=NFC-e, utilizada nas operações de venda no varejo (a critério da UF aceitar este modelo de documento).
            #
            # <b>Type:     </b> _Number_ OR _String_
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _55_
            # <b>Length:   </b> _2_
            # <b>tag:      </b> mod
            #
            attr_accessor :modelo_nf
            alias_attribute :mod, :modelo_nf

            # Data e hora de emissão do Documento Fiscal
            #
            # <b>Type:     </b> _Time_
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _Time.current_
            # <b>tag:      </b> dhEmi
            #
            attr_accessor :data_hora_emissao
            def data_hora_emissao
                convert_to_time(@data_hora_emissao)
            end
            alias_attribute :dhEmi, :data_hora_emissao

            # Data e hora de Saída ou da Entrada da Mercadoria/Produto
            # Campo não considerado para a NFC-e.
            #
            # <b>Type:     </b> _Time_
            # <b>Required: </b> _Yes_ (apenas para modelo 55)
            # <b>Default:  </b> _Time.current_
            # <b>tag:      </b> dhSaiEnt
            #
            attr_accessor :data_hora_expedicao
            def data_hora_expedicao
                convert_to_time(@data_hora_expedicao)
            end
            alias_attribute :dhSaiEnt, :data_hora_expedicao

            # Tipo de Operação
            # 0=Entrada;
            # 1=Saída (Default)
            #
            # <b>Type:     </b> _Number_ OR _String_
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _1_
            # <b>Length:   </b> _1_
            # <b>tag:      </b> tpNF
            #
            attr_accessor :tipo_operacao
            alias_attribute :tpNF, :tipo_operacao

            # Formato de Impressão do DANFE
            # 0=Sem geração de DANFE;
            # 1=DANFE normal, Retrato; (Default)
            # 2=DANFE normal, Paisagem;
            # 3=DANFE Simplificado;
            # 4=DANFE NFC-e;
            # 5=DANFE NFC-e em mensagem eletrônica (o envio de mensagem eletrônica pode
            #   ser feita de forma simultânea com a impressão do DANFE; usar o tpImp=5
            #   quando esta for a única forma de disponibilização do DANFE).
            #
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _1_
            # <b>tag:      </b> tpEmis
            #
            attr_accessor :tipo_impressao
            alias_attribute :tpEmis, :tipo_impressao

            # Finalidade de emissão da NF-e
            # 1=NF-e normal; (Default)
            # 2=NF-e complementar;
            # 3=NF-e de ajuste;
            # 4=Devolução de mercadoria.
            #
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _1_
            # <b>tag:      </b> finNFe
            #
            attr_accessor :finalidade_emissao
            alias_attribute :finNFe, :finalidade_emissao


            # Indica operação com Consumidor final
            # false=Normal;
            # true=Consumidor final;
            #
            # Preencher esse campo com true ou false
            #
            # <b>Type:     </b> _Boolean_
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _false_
            # <b>tag:      </b> indFinal
            #
            attr_accessor :consumidor_final
            def consumidor_final
                convert_to_boolean(@consumidor_final)
            end
            alias_attribute :indFinal, :consumidor_final

            # Indicador de presença do comprador no estabelecimento comercial no
            # momento da operação:
            #   0=Não se aplica (por exemplo, Nota Fiscal complementar ou de ajuste);
            #   1=Operação presencial;
            #   2=Operação não presencial, pela Internet;
            #   3=Operação não presencial, Teleatendimento;
            #   4=NFC-e em operação com entrega a domicílio;
            #   9=Operação não presencial, outros. (Default)
            #
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _9_
            # <b>tag:      </b> indPres
            #
            attr_accessor :presenca_comprador
            alias_attribute :indPres, :presenca_comprador

            # Processo de emissão da NF-e
            # 0=Emissão de NF-e com aplicativo do contribuinte; (Default)
            # 1=Emissão de NF-e avulsa pelo Fisco;
            # 2=Emissão de NF-e avulsa, pelo contribuinte com seu certificado digital, através do site do Fisco;
            # 3=Emissão NF-e pelo contribuinte com aplicativo fornecido pelo Fisco.
            #
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _0_
            # <b>tag:      </b> procEmi
            #
            attr_accessor :processo_emissao
            alias_attribute :procEmi, :processo_emissao

            # Versão do Processo de emissão da NF-e
            # Informar a versão do aplicativo emissor de NF-e.
            #
            # <b>Required: </b> _Yes_
            # <b>Default:  </b> _0_
            # <b>tag:      </b> verProc
            #
            attr_accessor :versao_aplicativo
            alias_attribute :verProc, :versao_aplicativo

            # Chave de acesso de notas referenciadas. (por enquanto aceita apenas a chave de acesso)
            #
            # <b>Type:     </b> _Array_
            # <b>Required: </b> _No_
            # <b>Default:  </b> _[]_
            # <b>tag:      </b> NFref > refNFe
            #
            attr_accessor :notas_referenciadas
            def notas_referenciadas
                @notas_referenciadas = [@notas_referenciadas].flatten unless @notas_referenciadas.is_a?(Array)
                @notas_referenciadas.compact!
                @notas_referenciadas
            end
            alias_attribute :NFref, :notas_referenciadas

            # Endereço da retirada da mercadoria
            #
            # <b>Type:     </b> _BrNfe.endereco_class_
            # <b>Required: </b> _No_
            # <b>Default:  </b> _nil_
            # <b>tag:      </b> retirada
            #
            has_one :endereco_retirada, 'BrNfe.endereco_class'
            alias_attribute :retirada, :endereco_retirada

            # CPF ou CNPJ do local de retirada da mercadoria.
            # Só é obrigatório se o endereco_retirada for preenchido
            #
            # <b>Type:     </b> _String_
            # <b>Required: </b> _No_ (_Yes_ if endereco_retirada is present)
            # <b>Default:  </b> _nil_
            # <b>tag:      </b> retirada/CPF ou retirada/CNPJ
            #
            attr_accessor :endereco_retirada_cpf_cnpj
            def endereco_retirada_cpf_cnpj
                return unless @endereco_retirada_cpf_cnpj.present?
                BrNfe::Helper::CpfCnpj.new(@endereco_retirada_cpf_cnpj).sem_formatacao
            end


            # Endereço da entrega da mercadoria
            # Informar apenas quando for diferente do endereço do destinatário
            #
            # <b>Type:     </b> _BrNfe.endereco_class_
            # <b>Required: </b> _No_
            # <b>Default:  </b> _nil_
            # <b>tag:      </b> entrega
            #
            has_one :endereco_entrega, 'BrNfe.endereco_class'
            alias_attribute :entrega, :endereco_entrega

            # CPF ou CNPJ do local de entrega da mercadoria.
            # Só é obrigatório se o endereco_entrega for preenchido
            #
            # <b>Type:     </b> _String_
            # <b>Required: </b> _No_ (_Yes_ if endereco_entrega is present)
            # <b>Default:  </b> _nil_
            # <b>tag:      </b> entrega/CPF ou entrega/CNPJ
            #
            attr_accessor :endereco_entrega_cpf_cnpj
            def endereco_entrega_cpf_cnpj
                return unless @endereco_entrega_cpf_cnpj.present?
                BrNfe::Helper::CpfCnpj.new(@endereco_entrega_cpf_cnpj).sem_formatacao
            end

            # CPF ou CNPJ das pessoas que estão autorizadas a fazer o download do XML da NF-e.
            # Deve ser um Array com os CPF's e CNPJ's válidos.
            #
            # <b>Type:     </b> _Array_
            # <b>Required: </b> _No_
            # <b>Default:  </b> _[]_
            # <b>tag:      </b> autXML
            #
            attr_accessor :autorizados_download_xml
            def autorizados_download_xml
                @autorizados_download_xml = [@autorizados_download_xml].flatten unless @autorizados_download_xml.is_a?(Array)
                @autorizados_download_xml.compact!
                @autorizados_download_xml
            end
            alias_attribute :autXML, :autorizados_download_xml

            # Transporte da mercadoria
            # Informações referentes ao transporte da mercadoria.
            #
            # <b>Type:     </b> _BrNfe.transporte_product_class_
            # <b>Required: </b> _No_
            # <b>Default:  </b> _nil_
            # <b>tag:      </b> transp
            #
            has_one :transporte, 'BrNfe.transporte_product_class'
            alias_attribute :transp, :transporte

            # Dados da cobrança da NF-e
            # Fatura e Duplicatas da Nota Fiscal
            # Utilizado para especificar os dados da fatura e das duplicatas.
            # No caso desta GEM, a fatura contém o Array de duplicatas.
            # Ex:
            #    self.fatura.duplicatas
            #    => [#<::Cobranca::Duplicata:0x00000006302b80 ...>, #<::Cobranca::Duplicata:0x00000046465bw4 ...>]
            #
            # <b>Type:     </b> _BrNfe.fatura_product_class_
            # <b>Required: </b> _No_
            # <b>Default:  </b> _nil_
            # <b>Exemplo:  </b> _BrNfe::Product::Nfe::Cobranca::Fatura.new(numero_fatura: 'FAT646498'...)_
            # <b>tag:      </b> cobr
            #
            has_one :fatura, 'BrNfe.fatura_product_class'
            alias_attribute :cobranca, :fatura
            alias_attribute :cobr, :fatura

            # Array com as informações dos pagamentos
            # IMPORTANTE: Utilizado apenas para NFC-e
            #
            # Pode ser adicionado os dados dos pagamentos em forma de `Hash`
            # ou o próprio objeto da classe BrNfe.pagamento_product_class.
            #
            # Exemplo com Hash:
            #    self.pagamentos = [{forma_pagamento: '1', total: 100.00, ...},{forma_pagamento: '2', total: 200.00, ...}]
            #    self.pagamentos << {forma_pagamento: '3', total: 300.00, ...}
            #    self.pagamentos << {forma_pagamento: '4', total: 400.00, ...}
            #
            # Exemplo com Objetos:
            #    self.pagamentos = [BrNfe::Product::Nfe::Cobranca::Pagamento.new({forma_pagamento: '5', total: 500.00, ...}),{forma_pagamento: '11', total: 600.00, ...}]
            #    self.pagamentos << BrNfe::Product::Nfe::Cobranca::Pagamento.new({forma_pagamento: '10', total: 700.00, ...})
            #    self.pagamentos << {forma_pagamento: '12', total: 800.00, ...}
            #
            # Sempre vai retornar um Array de objetos da class configurada em `BrNfe.pagamento_product_class`
            #
            # <b>Tipo:    </b> _BrNfe.pagamento_product_class (BrNfe::Product::Nfe::Cobranca::Pagamento)_
            # <b>Min:     </b> _0_
            # <b>Max:     </b> _100_
            # <b>Default: </b> _[]_
            # <b>tag:     </b> pag
            #
            has_many :pagamentos, 'BrNfe.pagamento_product_class'
            alias_attribute :pag, :pagamentos

            # DETALHAMENTO DE PRODUTOS E SERVIÇOS
            #
            # <b>Type:    </b> _BrNfe.item_product_class (BrNfe::Product::Nfe::Item)_
            # <b>Default: </b> _[]_
            # <b>Length:  </b> _min: 1, max: 990_
            # <b>tag:     </b> det
            #
            has_many :itens, 'BrNfe.item_product_class'
            alias_attribute :det, :itens

            ##########################################################################
            #########################  TOTAIS PARA PRODUTOS  #########################
                # BASE DE CÁLCULO DO ICMS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vBC
                #
                attr_accessor :total_icms_base_calculo
                alias_attribute :ICMSTot_vBC, :total_icms_base_calculo
                validates :total_icms_base_calculo, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO ICMS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vICMS
                #
                attr_accessor :total_icms
                alias_attribute :ICMSTot_vICMS, :total_icms
                validates :total_icms, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO ICMS DESONERADO
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vICMSDeson
                #
                attr_accessor :total_icms_desonerado
                alias_attribute :ICMSTot_vICMSDeson, :total_icms_desonerado
                validates :total_icms_desonerado, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO ICMS RELATIVO FUNDO DE COMBATE À POBREZA(FCP)
                # DA UF DE DESTINO
                #   Valor total do ICMS relativo ao Fundo de Combate à Pobreza
                #   (FCP) para a UF de destino.
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _108.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vFCPUFDest
                #
                attr_accessor :total_icms_fcp_uf_destino
                alias_attribute :ICMSTot_vFCPUFDest, :total_icms_fcp_uf_destino
                validates :total_icms_fcp_uf_destino, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO ICMS INTERESTADUAL PARA A UF DE DESTINO
                #   Valor total do ICMS Interestadual para a UF de destino, já
                #   considerando o valor do ICMS relativo ao Fundo de Combate à
                #   Pobreza naquela UF
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _108.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vICMSUFDest
                #
                attr_accessor :total_icms_uf_destino
                alias_attribute :ICMSTot_vICMSUFDest, :total_icms_uf_destino
                validates :total_icms_uf_destino, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO ICMS INTERESTADUAL PARA A UF DO REMETENTE
                #   Valor total do ICMS Interestadual para a UF do remetente.
                #   Nota: A partir de 2019, este valor será zero.
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _108.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vICMSUFRemet
                #
                attr_accessor :total_icms_uf_origem
                alias_attribute :ICMSTot_vICMSUFRemet, :total_icms_uf_origem
                validates :total_icms_uf_origem, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # BASE DE CÁLCULO DO ICMS ST
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vBCST
                #
                attr_accessor :total_icms_base_calculo_st
                alias_attribute :ICMSTot_vBCST, :total_icms_base_calculo_st
                validates :total_icms_base_calculo_st, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO ICMS ST
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vST
                #
                attr_accessor :total_icms_st
                alias_attribute :ICMSTot_vST, :total_icms_st
                validates :total_icms_st, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DOS PRODUTOS E SERVIÇOS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vProd
                #
                attr_accessor :total_produtos
                alias_attribute :ICMSTot_vProd, :total_produtos
                validates :total_produtos, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO FRETE
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vFrete
                #
                attr_accessor :total_frete
                alias_attribute :ICMSTot_vFrete, :total_frete
                validates :total_frete, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO SEGURO
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vSeg
                #
                attr_accessor :total_seguro
                alias_attribute :ICMSTot_vSeg, :total_seguro
                validates :total_seguro, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO DESCONTO
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vDesc
                #
                attr_accessor :total_desconto
                alias_attribute :ICMSTot_vDesc, :total_desconto
                validates :total_desconto, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO II
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vII
                #
                attr_accessor :total_imposto_importacao
                alias_attribute :ICMSTot_vII, :total_imposto_importacao
                validates :total_imposto_importacao, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO IPI
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vIPI
                #
                attr_accessor :total_ipi
                alias_attribute :ICMSTot_vIPI, :total_ipi
                validates :total_ipi, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO PIS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vPIS
                #
                attr_accessor :total_pis
                alias_attribute :ICMSTot_vPIS, :total_pis
                validates :total_pis, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO COFINS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vCOFINS
                #
                attr_accessor :total_cofins
                alias_attribute :ICMSTot_vCOFINS, :total_cofins
                validates :total_cofins, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # OUTRAS DESPESAS ACESSÓRIAS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vOutro
                #
                attr_accessor :total_outras_despesas
                alias_attribute :ICMSTot_vOutro, :total_outras_despesas
                validates :total_outras_despesas, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DA NF-E
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vNF
                #
                attr_accessor :total_nf
                alias_attribute :ICMSTot_vNF, :total_nf
                validates :total_nf, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR APROXIMADO TOTAL DE TRIBUTOS FEDERAIS, ESTADUAIS E MUNICIPAIS.
                # (NT 2013/003)
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ICMSTot/vTotTrib
                #
                attr_accessor :total_tributos
                alias_attribute :ICMSTot_vTotTrib, :total_tributos
                validates :total_tributos, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true
            ##########################################################################
            #########################  TOTAIS PARA SERVIÇOS  #########################
                # VALOR TOTAL DOS SERVIÇOS SOB NÃO-INCIDÊNCIA OU NÃO TRIBUTADOS PELO ICMS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _Yes_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ISSQNtot/vServ
                #
                attr_accessor :total_servicos
                alias_attribute :ISSQNtot_vServ, :total_servicos
                validates :total_servicos, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL BASE DE CÁLCULO DO ISS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ISSQNtot/vBC
                #
                attr_accessor :total_servicos_base_calculo
                alias_attribute :ISSQNtot_vBC, :total_servicos_base_calculo
                validates :total_servicos_base_calculo, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO ISS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ISSQNtot/vISS
                #
                attr_accessor :total_servicos_iss
                alias_attribute :ISSQNtot_vISS, :total_servicos_iss
                validates :total_servicos_iss, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DO PIS SOBRE SERVIÇOS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ISSQNtot/vPIS
                #
                attr_accessor :total_servicos_pis
                alias_attribute :ISSQNtot_vPIS, :total_servicos_pis
                validates :total_servicos_pis, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DA COFINS SOBRE SERVIÇOS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ISSQNtot/vCOFINS
                #
                attr_accessor :total_servicos_cofins
                alias_attribute :ISSQNtot_vCOFINS, :total_servicos_cofins
                validates :total_servicos_cofins, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # DATA DA PRESTAÇÃO DO SERVIÇO
                #
                #
                # <b>Type:     </b> _Date_
                # <b>Required: </b> _Yes_ apenas se tiver algum serviço nos itens
                # <b>Default:  </b> _Date.current_
                # <b>Example:  </b> _Date.current_
                # <b>Length:   </b> _8_ YYYYMMDD
                # <b>tag:      </b> total/ISSQNtot/dCompet
                #
                attr_accessor :servicos_data_prestacao
                def servicos_data_prestacao
                    convert_to_date(@servicos_data_prestacao)
                end
                alias_attribute :ISSQNtot_dCompet, :servicos_data_prestacao
                validates :servicos_data_prestacao, presence: true, if: :has_any_service?

                # VALOR TOTAL DEDUÇÃO PARA REDUÇÃO DA BASE DE CÁLCULO
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ISSQNtot/vDeducao
                #
                attr_accessor :total_servicos_deducao
                alias_attribute :ISSQNtot_vDeducao, :total_servicos_deducao
                validates :total_servicos_deducao, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL OUTRAS RETENÇÕES DO ISSQN
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ISSQNtot/vOutro
                #
                attr_accessor :total_servicos_outras_retencoes
                alias_attribute :ISSQNtot_vOutro, :total_servicos_outras_retencoes
                validates :total_servicos_outras_retencoes, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DESCONTO INCONDICIONADO
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ISSQNtot/vDescIncond
                #
                attr_accessor :total_servicos_desconto_incondicionado
                alias_attribute :ISSQNtot_vDescIncond, :total_servicos_desconto_incondicionado
                validates :total_servicos_desconto_incondicionado, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL DESCONTO CONDICIONADO
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ISSQNtot/vDescCond
                #
                attr_accessor :total_servicos_desconto_condicionado
                alias_attribute :ISSQNtot_vDescCond, :total_servicos_desconto_condicionado
                validates :total_servicos_desconto_condicionado, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR TOTAL RETENÇÃO ISS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/ISSQNtot/vISSRet
                #
                attr_accessor :total_servicos_iss_retido
                alias_attribute :ISSQNtot_vISSRet, :total_servicos_iss_retido
                validates :total_servicos_iss_retido, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # CÓDIGO DO REGIME ESPECIAL DE TRIBUTAÇÃO
                #  1 = Microempresa Municipal;
                #  2 = Estimativa;
                #  3 = Sociedade de Profissionais;
                #  4 = Cooperativa;
                #  5 = Microempresário Individual (MEI);
                #  6 = Microempresário e Empresa de Pequeno Porte (ME/EPP)
                #
                # <b>Type:     </b> _Number_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _2_
                # <b>Default:  </b> _1_
                # <b>Length:   </b> _1_
                # <b>tag:      </b> total/ISSQNtot/cRegTrib
                #
                attr_accessor :regime_tributario_servico
                def regime_tributario_servico
                    @regime_tributario_servico.to_i if @regime_tributario_servico.present?
                end
                alias_attribute :ISSQNtot_cRegTrib, :regime_tributario_servico
                validates :regime_tributario_servico, inclusion: {in: [1,2,3,4,5,6]}
            ##########################################################################
            #########################  TOTAIS DAS RETENÇÕES  #########################
                # VALOR RETIDO DE PIS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/retTrib/vRetPIS
                #
                attr_accessor :total_retencao_pis
                alias_attribute :retTrib_vRetPIS, :total_retencao_pis
                validates :total_retencao_pis, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR RETIDO DE COFINS
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/retTrib/vRetCOFINS
                #
                attr_accessor :total_retencao_cofins
                alias_attribute :retTrib_vRetCOFINS, :total_retencao_cofins
                validates :total_retencao_cofins, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR RETIDO DE CSLL
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/retTrib/vRetCSLL
                #
                attr_accessor :total_retencao_csll
                alias_attribute :retTrib_vRetCSLL, :total_retencao_csll
                validates :total_retencao_csll, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # BASE DE CÁLCULO DO IRRF
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/retTrib/vBCIRRF
                #
                attr_accessor :total_retencao_base_calculo_irrf
                alias_attribute :retTrib_vBCIRRF, :total_retencao_base_calculo_irrf
                validates :total_retencao_base_calculo_irrf, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR RETIDO DO IRRF
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/retTrib/vIRRF
                #
                attr_accessor :total_retencao_irrf
                alias_attribute :retTrib_vIRRF, :total_retencao_irrf
                validates :total_retencao_irrf, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # BASE DE CÁLCULO DA RETENÇÃO DA PREVIDÊNCIA SOCIAL
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/retTrib/vBCRetPrev
                #
                attr_accessor :total_retencao_base_calculo_previdencia
                alias_attribute :retTrib_vBCRetPrev, :total_retencao_base_calculo_previdencia
                validates :total_retencao_base_calculo_previdencia, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true

                # VALOR DA RETENÇÃO DA PREVIDÊNCIA SOCIAL
                #
                # <b>Type:     </b> _Float_
                # <b>Required: </b> _No_
                # <b>Example:  </b> _178.46_
                # <b>Length:   </b> _13v2_
                # <b>tag:      </b> total/retTrib/vRetPrev
                #
                attr_accessor :total_retencao_previdencia
                alias_attribute :retTrib_vRetPrev, :total_retencao_previdencia
                validates :total_retencao_previdencia, numericality: {greater_than_or_equal_to: 0.0}, allow_blank: true
            ##########################################################################
            ########################  INFORMAÇÕES ADICIONAIS  ########################
                # INFORMAÇÕES ADICIONAIS DE INTERESSE DO FISCO
                #
                # <b>Type:     </b> _String_
                # <b>Required: </b> _No_
                # <b>Default:  </b> _nil_
                # <b>Length:   </b> _max: 2000_
                # <b>tag:      </b> infAdic/infAdFisco
                #
                attr_accessor :informacoes_fisco
                alias_attribute :infAdFisco, :informacoes_fisco

                # INFORMAÇÕES COMPLEMENTARES DE INTERESSE DO CONTRIBUINTE
                #
                # <b>Type:     </b> _String_
                # <b>Required: </b> _No_
                # <b>Default:  </b> _nil_
                # <b>Length:   </b> _max: 5000_
                # <b>tag:      </b> infAdic/infCpl
                #
                attr_accessor :informacoes_contribuinte
                alias_attribute :infCpl, :informacoes_contribuinte

                # GRUPO PROCESSO REFERENCIADO
                # (NT 2012/003)
                #
                # <b>Type:    </b> _BrNfe.processo_referencia_product_class (BrNfe::Product::Nfe::ProcessoReferencia)_
                # <b>Default: </b> _[]_
                # <b>Length:  </b> _max: 100_
                # <b>tag:     </b> procRef
                #
                has_many :processos_referenciados, 'BrNfe.processo_referencia_product_class'
                alias_attribute :procRef, :processos_referenciados
            ##########################################################################
            ######################  INFORMAÇÕES DE EXPORTAÇÃO  #######################
                # SIGLA DA UF DE EMBARQUE OU DE TRANSPOSIÇÃO DE FRONTEIRA
                # Não aceita o valor "EX"
                #
                # <b>Type:     </b> _String_
                # <b>Required: </b> _No_
                # <b>Default:  </b> _nil_
                # <b>Length:   </b> _2_
                # <b>tag:      </b> exporta/UFSaidaPais
                #
                attr_accessor :exportacao_uf_saida
                alias_attribute :UFSaidaPais, :exportacao_uf_saida
                validates :exportacao_uf_saida, inclusion: {in: BrNfe::Constants::SIGLAS_UF-['EX'] }, allow_blank: true

                # DESCRIÇÃO DO LOCAL DE EMBARQUE OU DE TRANSPOSIÇÃO DE FRONTEIRA
                #
                # <b>Type:     </b> _String_
                # <b>Required: </b> _No_
                # <b>Default:  </b> _nil_
                # <b>Length:   </b> _max: 60_
                # <b>tag:      </b> exporta/xLocExporta
                #
                attr_accessor :exportacao_local_embarque
                alias_attribute :xLocExporta, :exportacao_local_embarque

                # DESCRIÇÃO DO LOCAL DE DESPACHO
                # Informação do Recinto Alfandegado
                #
                # <b>Type:     </b> _String_
                # <b>Required: </b> _No_
                # <b>Default:  </b> _nil_
                # <b>Length:   </b> _max: 60_
                # <b>tag:      </b> exporta/xLocDespacho
                #
                attr_accessor :exportacao_local_despacho
                alias_attribute :xLocDespacho, :exportacao_local_despacho

            ############################################################################
            #########################  DADOS SETADOS NO RETORNO #######################
                # Utilizado para setar o XML da nfe na resposta
                attr_accessor :xml

                # Utilizado para setar o XML da tag <infNFe>
                # Serve apenas se deseja pegar apenas a informação da NF-e sem a assinatura.
                #
                attr_accessor :xml_inf_nfe

                # PROTOCOLO / NÚMERO DO RECIBO
                #  Número do Recibo gerado pelo Portal da
                #  Secretaria de Fazenda Estadual
                #
                attr_accessor :protocol
                alias_attribute :nProt, :protocol

                # VALOR DIGEST DO RETORNO
                #  Digest Value da NF-e processada
                #  Utilizado para conferir a integridade da NFe
                #  original.
                #
                attr_accessor :digest_value
                alias_attribute :digVal, :digest_value

                # DATA E HORA DO PROCESSAMENTO DA REQUISIÇÃO
                #
                attr_accessor :processed_at
                def processed_at
                    convert_to_time(@processed_at)
                end
                alias_attribute :dhRecbto, :processed_at

                # STATUS DA OPERAÇÃO
                # Esse é o status final da operação com anota fiscal.
                # A partir do status é possível identificar se obteve sucesso
                # no processamento da nota (para qualquer operação)
                #
                attr_accessor :status_code
                attr_accessor :status_motive
                def status
                    if "#{status_code}   ".strip.in?( BrNfe::Constants::NFE_STATUS_SUCCESS )
                        :success
                    elsif "#{status_code}".strip.in?( BrNfe::Constants::NFE_STATUS_PROCESSING )
                        :processing
                    elsif "#{status_code}".strip.in?( BrNfe::Constants::NFE_STATUS_OFFLINE )
                        :offline
                    elsif "#{status_code}".strip.in?( BrNfe::Constants::NFE_STATUS_DENIED )
                        :denied
                    elsif status_code.present?
                        :error
                    end
                end

                # SITUAÇÃO DA NOTA FISCAL
                # Informa o status atual da nota fiscal.
                # Retorna se a nota fiscal está autorizada, cancelada, denegada, rejeitada, ajustada.
                # Exemplo:
                # - :authorized - Quando a nota fiscal está autorizada para uso
                # - :adjusted - Quando a nota fiscal está autorizada para o uso e foi realizado algum
                #               evento posterior que a mesma foi ajustada
                # - :draft    - Quando a nota fiscal ainda não tem validade fiscal.
                # - :canceled - Quando a nota fiscal foi cancelada.
                # - :denied   - Quando a nota fiscal foi denegada e o XML deve ser guardado.
                # - :rejected - Quando a nota fiscal foi rejeitada e pode ser enviada novamente com as correções.
                #
                attr_accessor :situation
                def situation
                    @situation ||= get_situation_by_status_code
                end
                def get_situation_by_status_code
                    if "#{status_code}".strip.in?(    BrNfe::Constants::NFE_SITUATION_AUTORIZED )
                        :authorized
                    elsif "#{status_code}".strip.in?( BrNfe::Constants::NFE_SITUATION_ADJUSTED )
                        :adjusted
                    elsif "#{status_code}".strip.in?( BrNfe::Constants::NFE_SITUATION_CANCELED )
                        :canceled
                    elsif "#{status_code}".strip.in?( BrNfe::Constants::NFE_SITUATION_DENIED )
                        :denied
                    elsif status_code.blank? || "#{status_code}".strip.in?( BrNfe::Constants::NFE_SITUATION_DRAFT )
                        :draft
                    else
                        :rejected
                    end
                end

            ##################################################################################
            #########################  DADOS SETADOS NA LEITURA DO XML #######################
                attr_accessor :tipo_ambiente
                alias_attribute :tbAmb, :tipo_ambiente

            def default_values
                {
                    versao_aplicativo:   0,
                    natureza_operacao:   'Venda',
                    forma_pagamento:     0, # 0=À vista
                    modelo_nf:           55, #NF-e
                    data_hora_emissao:   Time.current.in_time_zone,
                    data_hora_expedicao: Time.current.in_time_zone,
                    tipo_operacao:       1, # 1=Saída
                    tipo_impressao:      1, # 1=DANFE normal, Retrato;
                    finalidade_emissao:  1, # 1=NF-e normal;
                    presenca_comprador:  9, # 9=Operação não presencial, outros.
                    processo_emissao:    0, # 0=Emissão de NF-e com aplicativo do contribuinte;
                    codigo_tipo_emissao: 1, # 1=Normal
                    servicos_data_prestacao:   Date.current,
                    regime_tributario_servico: 1, # 1=Microempresa Municipal;
                }
            end

            validates :codigo_tipo_emissao, presence: true
            validates :codigo_tipo_emissao, inclusion: [1, 6, 7, 9, '1', '6', '7', '9']

            validates :codigo_nf, presence: true
            validates :codigo_nf, numericality: { only_integer: true }
            validates :codigo_nf, length: { maximum: 8 }

            validates :serie, presence: true
            validates :serie, numericality: { only_integer: true }
            validates :serie, length: { maximum: 3 }
            validates :serie, exclusion: [890, 899, 990, 999, '890', '899', '990', '999']

            validates :numero_nf, presence: true
            validates :numero_nf, numericality: { only_integer: true }
            validates :numero_nf, length: { maximum: 9 }

            validates :natureza_operacao, presence: true

            validates :forma_pagamento, presence: true
            validates :forma_pagamento, inclusion: [0, 1, 2, '0', '1', '2']

            validates :modelo_nf, presence: true
            validates :modelo_nf, inclusion: [55, 65, '55', '65']

            validates :data_hora_emissao, presence: true
            validates :data_hora_expedicao, presence: true, if: :nfe?

            validates :tipo_operacao, presence: true
            validates :tipo_operacao, inclusion: [0, 1, '0', '1']

            validates :tipo_impressao, presence: true
            validates :tipo_impressao, inclusion: [0, 1, 2, 3, 4, 5, '0', '1', '2', '3', '4', '5']

            validates :presenca_comprador, presence: true
            validates :presenca_comprador, inclusion: [0, 1, 2, 3, 4, 9, '0', '1', '2', '3', '4', '9']

            validates :processo_emissao, presence: true
            validates :processo_emissao, inclusion: [0, 1, 2, 3, '0', '1', '2', '3']

            validates :autorizados_download_xml, length: { maximum: 10 }

            validate_has_many :itens, message: :invalid_item
            validates         :itens, length:  {minimum: 1, maximum: 990}

            validate_has_many :processos_referenciados, message: :invalid_processo

            with_options if: :nfce? do |record|
                record.validate_has_many :pagamentos
                record.validates :pagamentos, length: {maximum: 100}
            end

            validate_has_one  :transporte
            validate_has_one  :fatura
            validate_has_one  :destinatario
            validate_has_one  :emitente

            validate_has_one  :endereco_retirada
            with_options if: :endereco_retirada do |record|
                record.validates :endereco_retirada_cpf_cnpj, presence: true
                record.validates :endereco_retirada_cpf_cnpj, length: {maximum: 14}
            end

            validate_has_one  :endereco_entrega
            with_options if: :endereco_entrega do |record|
                record.validates :endereco_entrega_cpf_cnpj, presence: true
                record.validates :endereco_entrega_cpf_cnpj, length: {maximum: 14}
            end

            def nfe?
                modelo_nf.to_i == 55
            end

            def nfce?
                modelo_nf.to_i == 65
            end

            def has_any_service?
                itens.select(&:is_service?).any?
            end

            def has_any_product?
                itens.select(&:is_product?).any?
            end

            # MÉTODO PARA SABER SE EXISTE ALGUM VALOR NO TOTALIZADOR DE RETENÇÃO DE IMPOSTOS.
            # Utilizado para saber se deve ou não colocar a tag de totalizador de retenções
            # no XML.
            #
            # <b>Tipo: </b> _Boolean_
            #
            def has_taxes_retention?
                total_retencao_pis.to_f  > 0.0 || total_retencao_cofins.to_f > 0.0 ||
                total_retencao_csll.to_f > 0.0 || total_retencao_irrf.to_f > 0.0   ||
                total_retencao_previdencia.to_f > 0.0
            end

        private

            ###############################################################################################
            #       | Código | AAMM da | CNPJ do  | Modelo | Série | Número  | Cód. tipo | Código   | DV  |
            #       | da UF  | emissão | Emitente |        |       | da NF-e | emissão   | Numérico |     |
            #       ---------------------------------------------------------------------------------------
            # Tam = |  02    |   04    |    14    |   02   |   03  |   09    |    01     |    08    | 01  |
            #       °°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°
            def gerar_chave_de_acesso!
                chave_sem_dv =  "#{emitente.endereco.codigo_ibge_uf}"
                chave_sem_dv << "#{data_hora_emissao.try(:strftime, '%y%m')}"
                chave_sem_dv << "#{emitente.cnpj}".rjust(14,'0')
                chave_sem_dv << "#{modelo_nf}"
                chave_sem_dv << "#{serie}".rjust(3, '0')
                chave_sem_dv << "#{numero_nf}".rjust(9, '0')
                chave_sem_dv << "#{codigo_tipo_emissao}"
                chave_sem_dv << "#{codigo_nf}".rjust(8, '0')
                dv = BrNfe::Calculos::Modulo11FatorDe2a9RestoZero.new(chave_sem_dv)
                "#{chave_sem_dv}#{dv}"
            end
        end
    end
end