Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Examplo #2

Open
rvalyi opened this issue Sep 24, 2020 · 0 comments
Open

Examplo #2

rvalyi opened this issue Sep 24, 2020 · 0 comments

Comments

@rvalyi
Copy link
Member

rvalyi commented Sep 24, 2020

replicando as explicações do Sergio Garcia desse issue de 2015 sped-br#1
caso venha a ser tirado do ar (projeto parente arquivado).

Segue exemplo com base no código do meu ERP para geração do ECD do ano de 2014.

Infelizmente meu ERP não está pronto e nem possuirá código aberto (a principio).

Este código possui diversas coisas hard code para maquiar parametros que ainda não existem no meu ERP.

Com o código abaixo, o ECD foi entregue gerado pelo sistema (tendo que ser validado e assinado no PVA) sem nenhum erro ou aviso.

O python-sped não exime o programador de conhecer a legislação do SPED e seguir sua documentação, ele apenas faz com que os arquivos sejam gerados sem erros de inconsistências. Validações mais elaboradas ficam a cargo do programador e/ou contador no PVA.

def sped_ecd(request):
    start_date = date(2014, 1, 1)
    end_date = date(2014, 12, 31)

    periods = Period.objects.filter(start_date__gte=start_date, end_date__lte=end_date).order_by('start_date')
    accounts = Account.objects.all().order_by('code')

    first_period = periods.first()
    last_period = periods.last()

    PeriodicBalance.calculate_for(last_period, True)

    #
    # Abertura do Arquivo
    #
    arquivo = ArquivoDigital()
    registro_abertura = arquivo._registro_abertura
    registro_abertura.DT_INI = start_date
    registro_abertura.DT_FIN = end_date
    registro_abertura.NOME = 'SUA EMPRESA LTDA'
    registro_abertura.CNPJ = '00000000000000'
    registro_abertura.UF = 'PR'
    registro_abertura.COD_MUN = 4106902
    registro_abertura.IM = '00000'
    registro_abertura.IND_SIT_INI_PER = '3'
    registro_abertura.IND_NIRE = '1'
    registro_abertura.IND_FIN_ESC = '0'
    registro_abertura.IND_GRANDE_PORTE = '0'
    registro_abertura.TIP_ECD = '0'

    bloco_0 = arquivo._blocos['0']

    registro_0007 = Registro0007()
    registro_0007.COD_ENT_REF = '00'
    bloco_0.add(registro_0007)

    bloco_i = arquivo._blocos['I']

    registro_i010 = RegistroI010()
    registro_i010.IND_ESC = 'G'            # Livro Diário Completo
    registro_i010.COD_VER_LC = '3.00'
    bloco_i.add(registro_i010)

    registro_i030 = RegistroI030()
    registro_i030.DNRC_ABERT = 'TERMO DE ABERTURA'
    registro_i030.NUM_ORD = 5
    registro_i030.NAT_LIVR = 'DIÁRIO GERAL'
    registro_i030.NOME = arquivo._registro_abertura.NOME
    registro_i030.NIRE = '000000'
    registro_i030.CNPJ = arquivo._registro_abertura.CNPJ
    registro_i030.DT_ARQ = date(2014, 1, 10)
    registro_i030.DESC_MUN = 'CURITIBA'
    registro_i030.DT_EX_SOCIAL = end_date
    bloco_i.add(registro_i030)

    for account in accounts:
        if not account.data['reference_account']:
            continue

        registro_i050 = RegistroI050()
        registro_i050.DT_ALT = start_date
        # TODO: Cadastrar a natureza na conta
        account_nature = '%02d' % (4 if int(account.get_root().code[0]) == 3 else int(account.get_root().code[0]))
        registro_i050.COD_NAT = account_nature
        registro_i050.IND_CTA = account.type
        registro_i050.NIVEL = account.level + 1
        registro_i050.COD_CTA = account.code
        if account.parent is not None:
            registro_i050.COD_CTA_SUP = account.parent.code
        registro_i050.CTA = account.name
        bloco_i.add(registro_i050)

        if account.type == Account.ANALYTICAL:
            registro_i051 = RegistroI051()
            registro_i051.COD_ENT_REF = '2'  # PJ Lucro Presumido
            registro_i051.COD_CTA_REF = account.data['reference_account']
            bloco_i.add(registro_i051)

            registro_i052 = RegistroI052()
            registro_i052.COD_AGL = account.code
            bloco_i.add(registro_i052)

    for period in periods:
        registro_i150 = RegistroI150()
        registro_i150.DT_INI = period.start_date
        registro_i150.DT_FIN = period.end_date
        bloco_i.add(registro_i150)

        for account in accounts.filter(type=Account.ANALYTICAL):
            periodic_balance = PeriodicBalance.objects.filter(period=period, account=account).first()

            if not periodic_balance:
                continue

            if not periodic_balance.initial_balance and \
               not periodic_balance.debit_value and \
               not periodic_balance.credit_value and \
               not periodic_balance.final_balance:
                continue

            registro_i155 = RegistroI155()
            registro_i155.COD_CTA = account.code
            registro_i155.VL_SLD_INI = abs(periodic_balance.initial_balance)
            registro_i155.IND_DC_INI = 'C' if periodic_balance.initial_balance > 0 else 'D'
            registro_i155.VL_DEB = abs(periodic_balance.debit_value)
            registro_i155.VL_CRED = abs(periodic_balance.credit_value)
            registro_i155.VL_SLD_FIN = abs(periodic_balance.final_balance)
            registro_i155.IND_DC_FIN = 'C' if periodic_balance.final_balance > 0 else 'D'
            bloco_i.add(registro_i155)

    for entry in Entry.objects.filter(date__gte=start_date,
                                      date__lte=end_date):
        registro_i200 = RegistroI200()
        registro_i200.NUM_LCTO = str(entry.id)
        registro_i200.DT_LCTO = entry.date
        registro_i200.VL_LCTO = entry.value

        if entry.memo == 'APURAÇÃO RESULTADO 12/2014':
            registro_i200.IND_LCTO = 'E'  # N or E
        else:
            registro_i200.IND_LCTO = 'N'  # N or E

        bloco_i.add(registro_i200)

        for item in entry.items.all():
            registro_i250 = RegistroI250()
            registro_i250.COD_CTA = item.account.code
            registro_i250.VL_DC = abs(item.credit_value or item.debit_value)
            registro_i250.IND_DC = 'C' if item.credit_value else 'D'
            registro_i250.HIST = entry.memo
            bloco_i.add(registro_i250)

    registro = RegistroI350()
    registro.DT_RES = end_date
    bloco_i.add(registro)

    PeriodicBalance.calculate_for(last_period, False)

    for account in accounts.filter(code__startswith='3', type=Account.ANALYTICAL):
        periodic_balance = PeriodicBalance.objects.filter(period=last_period, account=account).first()

        if not periodic_balance:
            continue

        registro_i355 = RegistroI355()
        registro_i355.COD_CTA = account.code
        registro_i355.VL_CTA = abs(periodic_balance.final_balance)
        registro_i355.IND_DC = account.nature
        bloco_i.add(registro_i355)

    bloco_j = arquivo._blocos['J']
    registro_j005 = RegistroJ005()
    registro_j005.DT_INI = start_date
    registro_j005.DT_FIN = end_date
    registro_j005.ID_DEM = 1
    bloco_j.add(registro_j005)

    #
    # Calculo Balanco Patrimonial
    #

    PeriodicBalance.calculate_for(last_period, True)

    for account in accounts.filter(Q(code__startswith='1') | Q(code__startswith='2')):
        first_balance = PeriodicBalance.objects.filter(period=first_period, account=account).first()
        last_balance = PeriodicBalance.objects.filter(period=last_period, account=account).first()

        if not first_balance.initial_balance and not last_balance.final_balance:
            continue

        registro_j100 = RegistroJ100()

        registro_j100.COD_AGL = account.code
        registro_j100.NIVEL_AGL = account.level + 1
        registro_j100.DESCR_COD_AGL = account.name
        registro_j100.IND_GRP_BAL = account.code[:1]

        registro_j100.VL_CTA_INI = abs(first_balance.initial_balance)
        registro_j100.IND_DC_BAL_INI = 'C' if first_balance.initial_balance >= 0 else 'D'
        registro_j100.VL_CTA = abs(last_balance.final_balance)
        registro_j100.IND_DC_BAL = 'C' if last_balance.final_balance >= 0 else 'D'

        bloco_j.add(registro_j100)

    #
    # Calculo Resultado (DRE)
    #
    res = dict([(account, Decimal(0)) for account in accounts.filter(code__startswith='3')])

    for item in EntryItem.all_objects.filter(entry__memo='APURAÇÃO RESULTADO 12/2014', account__code__startswith='3'):
        account = item.account
        while account:
            res[account] += (item.credit_value - item.debit_value)
            account = account.parent

    for account in accounts.filter(Q(level=2) | Q(level=4), code__startswith='3').order_by('code'):
        registro_j150 = RegistroJ150()
        if account.nature == Account.ANALYTICAL:
            registro_j150.COD_AGL = account.code
        registro_j150.NIVEL_AGL = account.level + 1
        registro_j150.DESCR_COD_AGL = account.name

        if not res[account]:
            continue

        registro_j150.VL_CTA = abs(res[account])

        if res[account] >= Decimal(0):
            registro_j150.IND_VL = 'D' if account.nature == Account.ANALYTICAL else 'N'
        else:
            registro_j150.IND_VL = 'R' if account.nature == Account.ANALYTICAL else 'P'

        bloco_j.add(registro_j150)

    #
    # Encerramento
    #
    registro_j900 = RegistroJ900()
    registro_j900.DNRC_ENCER = 'TERMO DE ENCERRAMENTO'
    registro_j900.NUM_ORD = 5
    registro_j900.NAT_LIVRO = 'DIÁRIO GERAL'
    registro_j900.NOME = 'SUA EMPRESA LTDA'
    registro_j900.DT_INI_ESCR = start_date
    registro_j900.DT_FIN_ESCR = end_date
    bloco_j.add(registro_j900)

    # Dados do Socio
    registro_j930 = RegistroJ930()
    registro_j930.IDENT_NOM = 'ADMINSTRADOR DA SILVA'
    registro_j930.IDENT_CPF = '0000000000000'
    registro_j930.IDENT_QUALIF = 'Administrador'
    registro_j930.COD_ASSIN = '205'
    registro_j930.EMAIL = '[email protected]'
    registro_j930.FONE = '00000'
    bloco_j.add(registro_j930)

    # Dados do Contador
    registro_j930 = RegistroJ930()
    registro_j930.IDENT_NOM = 'CONTADOR DA SILVA'
    registro_j930.IDENT_CPF = '0000000000000'
    registro_j930.IDENT_QUALIF = 'Contador'
    registro_j930.COD_ASSIN = '900'
    registro_j930.EMAIL = '[email protected]'
    registro_j930.FONE = '00000'

    registro_j930.IND_CRC = '00000/O'
    registro_j930.UF_CRC = 'PR'
    registro_j930.NUM_SEQ_CRC = 'PR/2015/000000'
    registro_j930.DT_CRC = date(2015, 6, 30)
    bloco_j.add(registro_j930)

    response = HttpResponse(content_type='text/plain; charset=iso-8859-1')
    response['Content-Disposition'] = 'attachment; filename="sped.txt"'

    arquivo.prepare()
    registro_i030.QTD_LIN = arquivo._registro_fechamento[2]
    registro_j900.QTD_LIN = arquivo._registro_fechamento[2]
    arquivo.write_to(response)

    return response
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant