Code Monkey home page Code Monkey logo

django-afip's Issues

Problemas al generar NC: Error 10197

Esto no me ha pasado en otras prubas, pero hoy haciendo algunas pruebas de implementación me arroja el error:

Validación de comprobante falló: ['Error 10197: Si el comprobante es Debito o Credito, enviar estructura CbteAsoc o PeriodoAsoc.'].

Dicho comprobante tiene asignado un comprobante relacionado. Lo he probado desde el panel de Admin por si era un error de implementación de mi lado, pero dá el mismo error.

Esto me pasa en sandbox y no lo he probado en producción (y es NC C).

Capturas:
ebiller_nc_test_1
ebiller_nc_test_2

Django==3.1
django-afip==8.0.1
Python 3.8.5

MySQL backend does not support timezone-aware datetimes when USE_TZ is False.

Hola. Yo tengo la siguiente configuración en settings.py

TIME_ZONE = 'America/Argentina/Cordoba'

USE_I18N = True

USE_L10N = True

USE_TZ = False

Esta forma hacía que ande correctamente la fecha cuando guardaba datos en la BD de mysql, pero al instalarle AFIP me salta este error. Tenés idea por qué? Disculpá la molestia

Supported Pythons / Djangos / SQLs

CI is a mess right now, it runs all combinations of databases and pythons and djangos, but there's no point in supporting the whole matrix. It currently runs 21 different environments: https://github.com/WhyNotHugo/django-afip/actions/runs/2304224481

This needs to be reduced to a few version, This will speed up CI in general, but also reduce energy waste. I intend to keep reasonable combinations. Postgres is likely to stay for a variety of combinations of versions of Python and Django. Sqlite will only run for the latest python and the latest django. I doubt anyone actually uses this module with sqlite on production, but if anyone does: let me know.

I also don't see the point of keeping LTSs in the support matrix; we've never done backports of bugfixes, the path has always been to track latest stables. If someone is using an old django, they can use an old django-afip just fine.

Falta dependencia de migración v7.1.1

Realizando una instalación en limpio (dentro de venv) y al aplicar la migración (python manage.py migrate), me muestra este error:

django.db.migrations.exceptions.NodeNotFoundError: Migration users.0001_initial dependencies reference nonexistent parent node ('afip', '0004_auto_20200115_1418')

Python v3.8
Django v3.1

Integrar FEDummy para chequear estado del servidor AFIP

Creo que podria llegar a ser util tener algun mecanismo para consultar el estado del servidor, ya sea para verificar antes de enviar un .validate() o simplemente consultar el estado ante un mal funcionamiento de la app (no me funciona el sistema, veamos si es AFIP u otra cosa)

Encontre que tienen un endpoint para esto: FEDummy "Metodo dummy para verificacion de funcionamiento", y se podria almacenar la respuesta a modo de log en algun model StatusCheck

Error 10015 AFIP

Tengo un problema de validacion que me inquieta, cuando valido una receipt tipo 'Factura B' con un cuit que no esta registrado en los padrones de AFIP la validacion me devuelve:
['Error 10015: Factura B (CbteDesde igual a CbteHasta), DocTipo: 80, DocNro 20402908323 no se encuentra registrado en los padrones de AFIP y no corresponde a una cuit pais.']
Ahora el problema esta que si registro la misma factura pero con tipo 'Factura A' la validacion pasa y no me devuelve ningun error.
No deberia generar conflicto al no estar registrado en los padrones de AFIP?
NOTA: estoy en modo sand_box.

No se puede generar nota de credito

Al parecer estoy teniendo este problema tambien en produccion:
['Error 10197: Si el comprobante es Debito o Credito, enviar estructura CbteAsoc o PeriodoAsoc.']

Por mas que asocie correctamente las related receipts y estas se creen en la base de datos la linea

wso = f.FECAERequest(
genera el cuerpo:

{
    'FeCabReq': {
        'CantReg': 1,
        'PtoVta': 1,
        'CbteTipo': '8'
    },
    'FeDetReq': {
        'FECAEDetRequest': [
            {
                'Concepto': '1',
                'DocTipo': '99',
                'DocNro': 0,
                'CbteDesde': 1,
                'CbteHasta': 1,
                'CbteFch': '20210405',
                'ImpTotal': Decimal('100.00'),
                'ImpTotConc': Decimal('0.00'),
                'ImpNeto': Decimal('82.64'),
                'ImpOpEx': Decimal('0.00'),
                'ImpTrib': 0,
                'ImpIVA': Decimal('17.36'),
                'FchServDesde': None,
                'FchServHasta': None,
                'FchVtoPago': None,
                'MonId': 'PES',
                'MonCotiz': Decimal('1.000000'),
                'CbtesAsoc': None,
                'Tributos': None,
                'Iva': {
                    'AlicIva': [
                        {
                            'Id': '5',
                            'BaseImp': Decimal('82.64'),
                            'Importe': Decimal('17.36')
                        }
                    ]
                },
                'Opcionales': None,
                'Compradores': None,
                'PeriodoAsoc': None
            }
        ]
    }
}

Como se puede ver 'CbtesAsoc': None, y no hay forma de hacer que se valide correctamente la factura. Antes pasaba solo en testing (pensamos que era por que solo era el entorno de testing), a partir de hoy tambien pasa en produccion.

Factory references file relative to tests dir

The factories (and their resources) should probably be an optional extras.

_________________________________ ERROR at setup of test_print_batch_labels _________________________________

    @pytest.fixture
    @pytest.mark.django_db
    def dummy_pos():
        """Creates a dummy POS with the system default POS's pk.

        This is needed for some views that load it in order to extract data from it
        (eg: CUIT).
        """
>       afip_factories.PointOfSalesFactory(
            pk=settings.DEFAULT_POS,
            owner__key="",
            owner__certificate="",
        )

idf/admin/tests/test_batch_admin.py:18:
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
/usr/local/lib/python3.8/site-packages/factory/base.py:40: in __call__
    return cls.create(**kwargs)
/usr/local/lib/python3.8/site-packages/factory/base.py:528: in create
    return cls._generate(enums.CREATE_STRATEGY, kwargs)
/usr/local/lib/python3.8/site-packages/factory/django.py:117: in _generate
    return super()._generate(strategy, params)
/usr/local/lib/python3.8/site-packages/factory/base.py:465: in _generate
    return step.build()
/usr/local/lib/python3.8/site-packages/factory/builder.py:258: in build
    step.resolve(pre)
/usr/local/lib/python3.8/site-packages/factory/builder.py:199: in resolve
    self.attributes[field_name] = getattr(self.stub, field_name)
/usr/local/lib/python3.8/site-packages/factory/builder.py:344: in __getattr__
    value = value.evaluate_pre(
/usr/local/lib/python3.8/site-packages/factory/declarations.py:48: in evaluate_pre
    return self.evaluate(instance, step, context)
/usr/local/lib/python3.8/site-packages/factory/declarations.py:395: in evaluate
    return step.recurse(subfactory, extra, force_sequence=force_sequence)
/usr/local/lib/python3.8/site-packages/factory/builder.py:216: in recurse
    return builder.build(parent_step=self, force_sequence=force_sequence)
/usr/local/lib/python3.8/site-packages/factory/builder.py:258: in build
    step.resolve(pre)
/usr/local/lib/python3.8/site-packages/factory/builder.py:199: in resolve
    self.attributes[field_name] = getattr(self.stub, field_name)
/usr/local/lib/python3.8/site-packages/factory/builder.py:344: in __getattr__
    value = value.evaluate_pre(
/usr/local/lib/python3.8/site-packages/factory/declarations.py:48: in evaluate_pre
    return self.evaluate(instance, step, context)
/usr/local/lib/python3.8/site-packages/factory/django.py:224: in evaluate
    filename, content = self._make_content(extra)
/usr/local/lib/python3.8/site-packages/factory/django.py:207: in _make_content
    content = django_files.File(func())
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _

    def _tiny_image_file():
>       return open(os.path.join(settings.BASE_DIR, "tiny.png"), "rb")
E       FileNotFoundError: [Errno 2] No such file or directory: '/app/tiny.png'

/usr/local/lib/python3.8/site-packages/django_afip/factories.py:35: FileNotFoundError

Move factories to django_afip.testing

This has breaking API changes, so it'll have to wait for v9.0.

Move django_afip.factories to django_afip.testing.factories, to make it very clear that these are testing utilities.

Validating receipts

Hi,

I have a doubt about validating receipts in batch.

Let suppose that I'm trying to validated receipts from a queryset. If I understand, errors on the validation process are appended to a list, but that list does not contain a reference to which receipt failed to validate. Or I am wrong?

I am asking this because In my view I generate ReceiptPDF once is validated, but If I validate a batch of receipts and one of them failed, I need to know which one in that process.

Thanks in advance.

QR Codes

Need QR codes before the end of the week.

nombre del archivo pdf

Viendo en la última actualización, al pasar un nombre del archivo al método

def upload_to(self, filename='untitled', instance=None):

en el modelo ReceiptPDF, el nombre del archivo siempre se genera con el uuid.
En esta linea de código

        filename = ''.join([uuid4().hex, extension])

no habría que cambiar la doble comilla simple ( '' ), por el nombre del archivo que se pasa como parámetro?
Saludos.

Authentication is broken

Apparently AFIP has mixed up the certificates assigned to each server:

ssl.SSLCertVerificationError: ("hostname 'wsaa.afip.gov.ar' doesn't match either of 'auth.afip.gob.ar', 'auth.afip.gov.ar', 'websec1.afip.gob.ar', 'websec2.afip.gob.ar', 'websec3.afip.gob.ar'",)

Error 501: Error interno de base de datos - FECAESolicitar

Hola,

Desde hoy a la tarde empecé a tener este error. Por el tipo de error calculo que es un error de la AFIP, ¿Verdad?

EDIT: Por las dudas aclaro que me pasa en el entorno de desarrollo, aún no lo he probado en producción.

Por las dudas actualicé la versión de django_afip.

DataError: value too long for type character varying(24) when trying to fetch point of sales

Hi, I recently came across an issue when trying to fetch point of sales from a given taxpayer.
I'm using

django=3.2.13
python=3.10.4
postgresql=14

When I run taxpayer.fetch_point_of_sales() an exception occurs.
The traceback is the following:

---------------------------------------------------------------------------
DoesNotExist                              Traceback (most recent call last)
File /usr/local/lib/python3.10/site-packages/django/db/models/query.py:581, in QuerySet.get_or_create(self, defaults, **kwargs)
    580 try:
--> 581     return self.get(**kwargs), False
    582 except self.model.DoesNotExist:

File /usr/local/lib/python3.10/site-packages/django/db/models/query.py:435, in QuerySet.get(self, *args, **kwargs)
    434 if not num:
--> 435     raise self.model.DoesNotExist(
    436         "%s matching query does not exist." %
    437         self.model._meta.object_name
    438     )
    439 raise self.model.MultipleObjectsReturned(
    440     'get() returned more than one %s -- it returned %s!' % (
    441         self.model._meta.object_name,
    442         num if not limit or num < limit else 'more than %s' % (limit - 1),
    443     )
    444 )

DoesNotExist: PointOfSales matching query does not exist.

During handling of the above exception, another exception occurred:

StringDataRightTruncation                 Traceback (most recent call last)
File /usr/local/lib/python3.10/site-packages/django/db/backends/utils.py:84, in CursorWrapper._execute(self, sql, params, *ignored_wrapper_args)
     83 else:
---> 84     return self.cursor.execute(sql, params)

StringDataRightTruncation: value too long for type character varying(24)


The above exception was the direct cause of the following exception:

DataError                                 Traceback (most recent call last)
Input In [34], in <cell line: 1>()
----> 1 tp.fetch_points_of_sales()

File /usr/local/lib/python3.10/site-packages/django_afip/models.py:468, in TaxPayer.fetch_points_of_sales(self, ticket)
    465 results = []
    466 for pos_data in response.ResultGet.PtoVenta:
    467     results.append(
--> 468         PointOfSales.objects.update_or_create(
    469             number=pos_data.Nro,
    470             owner=self,
    471             defaults={
    472                 "issuance_type": pos_data.EmisionTipo,
    473                 "blocked": pos_data.Bloqueado == "N",
    474                 "drop_date": parsers.parse_date(pos_data.FchBaja),
    475             },
    476         )
    477     )
    479 return results

File /usr/local/lib/python3.10/site-packages/django/db/models/manager.py:85, in BaseManager._get_queryset_methods.<locals>.create_method.<locals>.manager_method(self, *args, **kwargs)
     84 def manager_method(self, *args, **kwargs):
---> 85     return getattr(self.get_queryset(), name)(*args, **kwargs)

File /usr/local/lib/python3.10/site-packages/django/db/models/query.py:608, in QuerySet.update_or_create(self, defaults, **kwargs)
    604 self._for_write = True
    605 with transaction.atomic(using=self.db):
    606     # Lock the row so that a concurrent update is blocked until
    607     # update_or_create() has performed its save.
--> 608     obj, created = self.select_for_update().get_or_create(defaults, **kwargs)
    609     if created:
    610         return obj, created

File /usr/local/lib/python3.10/site-packages/django/db/models/query.py:588, in QuerySet.get_or_create(self, defaults, **kwargs)
    586     with transaction.atomic(using=self.db):
    587         params = dict(resolve_callables(params))
--> 588         return self.create(**params), True
    589 except IntegrityError:
    590     try:

File /usr/local/lib/python3.10/site-packages/django/db/models/query.py:453, in QuerySet.create(self, **kwargs)
    451 obj = self.model(**kwargs)
    452 self._for_write = True
--> 453 obj.save(force_insert=True, using=self.db)
    454 return obj

File /usr/local/lib/python3.10/site-packages/django/db/models/base.py:739, in Model.save(self, force_insert, force_update, using, update_fields)
    736     if loaded_fields:
    737         update_fields = frozenset(loaded_fields)
--> 739 self.save_base(using=using, force_insert=force_insert,
    740                force_update=force_update, update_fields=update_fields)

File /usr/local/lib/python3.10/site-packages/django/db/models/base.py:776, in Model.save_base(self, raw, force_insert, force_update, using, update_fields)
    774     if not raw:
    775         parent_inserted = self._save_parents(cls, using, update_fields)
--> 776     updated = self._save_table(
    777         raw, cls, force_insert or parent_inserted,
    778         force_update, using, update_fields,
    779     )
    780 # Store the database on which the object was saved
    781 self._state.db = using

File /usr/local/lib/python3.10/site-packages/django/db/models/base.py:881, in Model._save_table(self, raw, cls, force_insert, force_update, using, update_fields)
    878     fields = [f for f in fields if f is not meta.auto_field]
    880 returning_fields = meta.db_returning_fields
--> 881 results = self._do_insert(cls._base_manager, using, fields, returning_fields, raw)
    882 if results:
    883     for value, field in zip(results[0], returning_fields):

File /usr/local/lib/python3.10/site-packages/django/db/models/base.py:919, in Model._do_insert(self, manager, using, fields, returning_fields, raw)
    914 def _do_insert(self, manager, using, fields, returning_fields, raw):
    915     """
    916     Do an INSERT. If returning_fields is defined then this method should
    917     return the newly created data for the model.
    918     """
--> 919     return manager._insert(
    920         [self], fields=fields, returning_fields=returning_fields,
    921         using=using, raw=raw,
    922     )

File /usr/local/lib/python3.10/site-packages/django/db/models/manager.py:85, in BaseManager._get_queryset_methods.<locals>.create_method.<locals>.manager_method(self, *args, **kwargs)
     84 def manager_method(self, *args, **kwargs):
---> 85     return getattr(self.get_queryset(), name)(*args, **kwargs)

File /usr/local/lib/python3.10/site-packages/django/db/models/query.py:1270, in QuerySet._insert(self, objs, fields, returning_fields, raw, using, ignore_conflicts)
   1268 query = sql.InsertQuery(self.model, ignore_conflicts=ignore_conflicts)
   1269 query.insert_values(fields, objs, raw=raw)
-> 1270 return query.get_compiler(using=using).execute_sql(returning_fields)

File /usr/local/lib/python3.10/site-packages/django/db/models/sql/compiler.py:1416, in SQLInsertCompiler.execute_sql(self, returning_fields)
   1414 with self.connection.cursor() as cursor:
   1415     for sql, params in self.as_sql():
-> 1416         cursor.execute(sql, params)
   1417     if not self.returning_fields:
   1418         return []

File /usr/local/lib/python3.10/site-packages/django/db/backends/utils.py:98, in CursorDebugWrapper.execute(self, sql, params)
     96 def execute(self, sql, params=None):
     97     with self.debug_sql(sql, params, use_last_executed_query=True):
---> 98         return super().execute(sql, params)

File /usr/local/lib/python3.10/site-packages/django/db/backends/utils.py:66, in CursorWrapper.execute(self, sql, params)
     65 def execute(self, sql, params=None):
---> 66     return self._execute_with_wrappers(sql, params, many=False, executor=self._execute)

File /usr/local/lib/python3.10/site-packages/django/db/backends/utils.py:75, in CursorWrapper._execute_with_wrappers(self, sql, params, many, executor)
     73 for wrapper in reversed(self.db.execute_wrappers):
     74     executor = functools.partial(wrapper, executor)
---> 75 return executor(sql, params, many, context)

File /usr/local/lib/python3.10/site-packages/django/db/backends/utils.py:79, in CursorWrapper._execute(self, sql, params, *ignored_wrapper_args)
     77 def _execute(self, sql, params, *ignored_wrapper_args):
     78     self.db.validate_no_broken_transaction()
---> 79     with self.db.wrap_database_errors:
     80         if params is None:
     81             # params default might be backend specific.
     82             return self.cursor.execute(sql)

File /usr/local/lib/python3.10/site-packages/django/db/utils.py:90, in DatabaseErrorWrapper.__exit__(self, exc_type, exc_value, traceback)
     88 if dj_exc_type not in (DataError, IntegrityError):
     89     self.wrapper.errors_occurred = True
---> 90 raise dj_exc_value.with_traceback(traceback) from exc_value

File /usr/local/lib/python3.10/site-packages/django/db/backends/utils.py:84, in CursorWrapper._execute(self, sql, params, *ignored_wrapper_args)
     82     return self.cursor.execute(sql)
     83 else:
---> 84     return self.cursor.execute(sql, params)

DataError: value too long for type character varying(24)

For context:

response = client.service.FEParamGetPtosVenta(
serializers.serialize_ticket(ticket),
)

The response in the line above is:

{
    'ResultGet': {
        'PtoVenta': [
            {
                'Nro': 7,
                'EmisionTipo': 'CAEA - Ri Iva CONTINGENCIA',
                'Bloqueado': 'N',
                'FchBaja': 'NULL'
            }
        ]
    },
    'Errors': None,
    'Events': None
}

This results in a length of 26 characters for EmisionTipo, which is too long for the issuance_type field defined in PointOfSales model.

Posibilidad de personalizar el nombre del archivo PDF generado

Hola,

¿Habría alguna manera de personalizar el nombre del archivo generado en PDF?

Actualmente en mi implementación, al validar un comprobante es enviado al cliente, pero digamos que el nombre original generado no es muy "amigable" (por lo que en mi caso, copio el PDF en una ubicación temporal para renombrarlo y enviarlo).

Error en .validate()

Hola Hugo, traigo un error que se me presento al validar una Receipt y no se que es lo que lo provoca ya que el servidor esta en produccion por mas de un mes y recien ahora trae este error.

File "/home/venv/lib/python3.6/site-packages/django_afip/models.py", line 1105, in validate
    rv = Receipt.objects.filter(pk=self.pk).validate(ticket)
  File "/home/venv/lib/python3.6/site-packages/django_afip/models.py", line 790, in validate
    qs.order_by('issued_date', 'id')._assign_numbers()
  File "/home/venv/lib/python3.6/site-packages/django_afip/models.py", line 730, in _assign_numbers
    first.receipt_type,
  File "/home/venv/lib/python3.6/site-packages/django_afip/models.py", line 859, in fetch_last_receipt_number
    receipt_type.code,
  File "/home/venv/lib/python3.6/site-packages/zeep/proxy.py", line 45, in __call__
    kwargs,
  File "/home/venv/lib/python3.6/site-packages/zeep/wsdl/bindings/soap.py", line 122, in send
    response = client.transport.post_xml(options["address"], envelope, http_headers)
  File "/home/venv/lib/python3.6/site-packages/zeep/transports.py", line 95, in post_xml
    return self.post(address, message, headers)
  File "/home/venv/lib/python3.6/site-packages/zeep/transports.py", line 62, in post
    address, data=message, headers=headers, timeout=self.operation_timeout
  File "/home/venv/lib/python3.6/site-packages/requests/sessions.py", line 581, in post
    return self.request('POST', url, data=data, json=json, **kwargs)
  File "/home/venv/lib/python3.6/site-packages/requests/sessions.py", line 533, in request
    resp = self.send(prep, **send_kwargs)
  File "/home/venv/lib/python3.6/site-packages/requests/sessions.py", line 646, in send
    r = adapter.send(request, **kwargs)
  File "/home/venv/lib/python3.6/site-packages/requests/adapters.py", line 498, in send
    raise ConnectionError(err, request=request)
requests.exceptions.ConnectionError: ('Connection aborted.', OSError("(104, 'ECONNRESET')",))

Intente ver en las observaciones de la validacion pero al ser transaccional el metodo que llama a validate no registro errores.
Tenes idea que puede ser?

Error al generar Nota de crédito C

Hugo,

Tengo un error al generar una NC C, indicando del lado de AFIP:

Error 10197: Si el comprobante es Debito o Credito, enviar estructura CbteAsoc o PeriodoAsoc.

Sin embargo, el comprobante tiene asignado un related_receipts (comprobado en la DB que se generó y está OK).

¿Qué puede estará pasando?

Esto es en modo testing, no lo he probado en producción.

EDIT: agrego, si lo hago a un cliente mediante CUIT (no probé otros tipos de documento), no me dá error al generar NC-C, el problema se presenta con Consumidor Final (yo uso el valor 0 como DNI para Consumidor Final, por las dudas lo menciono).

Gracias.

Migracion AFIP (TLS 1.2)

Nos llego un informe desde AFIP informando que discontinuarian las versiones de TLS (v 1.0 y 1.1), siendo reemplazadas por la version 1.2.
Hay algun cambio necesario que se deba realizar? Dejo el cronograma de migracion por las dudas, si hay que aplicar cambios para el servicio servicios1.afip.gob.ar tenemos tiempo hasta el 11/04.

Validacion comprobantes

FeCabReq: La cabecera del comprobante o lote de comprobantes de ingreso está compuesta por
los siguientes campos:

CbteTipo I: Tipo de comprobante que se está informando. Si se informa más de un comprobante, todos deben ser del mismo tipo.

Si se validan diferentes tipos de comprobantes no checkea esa condición y puede generar comprobantes con el tipo invalido

Metadata as fixtures

The initial implementation of this library included a management command to fetch all metadata from AFIP's servers.

This fetched things like currency types, document types, etc. It sounded like a great idea, and would have made developer's life much easier each time AFIP changed these.

Experience and time have proven the contrary: AFIP seldom changes this data, and the management command confuses developers and adds complexity for setting up new applications and even new environments. The most annoying part, is needing a TaxPayer before fetching the data, which means that an empty environment can't have metadata.

This issue will track work that needs to be done to refine this, and make this a lot simpler:

  • Remove management command.
  • Remove function to programatically populate all.
  • Create a script to generate YAML fixtures with all metadata.
  • Update docs to indicate that these fixtures should be imported. This can be done right after migrations, and requires no extra steps.
  • Review how this affects existing tests -- a helper to load fixtures would be great since this can be used by downstream apps too.
  • Make sure changelog and docs are up to date for v8.0.0.

Código en vat_condition

Hugo,

Te escribo esta vez en español.

Mi consulta esta vez (o sugerencia): ¿No sería mejor que la selección de VAT_CONDITION (y posiblemente CLIENT_VAT_CONDITION) posea el código (code) de referencia que otorga AFIP?

Ejemplo, para el caso de "Responsable Monotributo" sería el código "6".

Menciono esto porque por ejemplo, yo estoy filtrando que tipo de comprobantes, siguiendo el ejemplo del caso de Responsable Monotributo, puede emitir.
Actualmente, si no lo estoy haciendo mal, no me queda otra que filtrar por el nombre "Responsable Monotributo" (o bien consultar en el TaxPayerProfile el tipo de vat_condition) y creo yo sería mejor un código.

Por supuesto nada demasiado importante, solo un detalle que me surgió consultar.

Muchas Gracias.

Failure to authenticate with cryptography==3.1

Attempting to authenticate with AFIP with cryptography==3.1 will fail due to internal interfaces being dropped. A solution to this is being discussed upstream.

Latest master has cryptography<3.1 pinned, but for developers using older releases, make sure you add this pin to your dependencies.

Error 10015

Hi, I have an error when validate with a particular CUIT from a client, which is a CUIT Nº and document type (CUIT) that does not gives me errors when generate the receipt on AFIP website platform RCEL:

Error 10015: Comprobante C (CbteDesde igual a CbteHasta), DocTipo: 80, DocNro 30715772511 no se encuentra registrado en los padrones de AFIP y no corresponde a una cuit pais.

Any ideas? Thanks.

PD: all this in sandbox, did not tried in production.

Error al asignar certificado (Homologación)

Hola,

Subiendo un certificado (modo de prueba/homologación), me está dando este error:

requests.exceptions.SSLError: HTTPSConnectionPool(host='wsaahomo.afip.gov.ar', port=443): Max retries exceeded with url: /ws/services/LoginCms?wsdl (Caused by SSLError(SSLError(1, '[SSL: DH_KEY_TOO_SMALL] dh key too small (_ssl.c:1108)')))

Al parecer algo cambió en AFIP . He regenerado el Key y la Solicitud por las dudas pero el error persiste. No lo he probado en Producción dado que ya lo tengo corriendo en una plataforma.

¿Cómo se puede resolver?

Muchas Gracias.

Python v3.8.2
Django v3.1.0
Django_afip v7.1.1

Dudado sobre el nombre de algunos verbose_name

Ejemplo, en el model Receipt, tenemos "Punto de ventas" con nombre del campo y del modelo PointOfSales.

Ahora, para ser más sencillo mi pregunta: ¿No sería mejor "Punto de venta"?.

Tipo de ConceptType.code

Hola,

Tengo una consulta, y por el que al pensar que era algo lógico, no podía resolver un tema con el código al comparar el code de una instancia de ConcepType: me dí cuenta luego que es un un varchar en vez de int (en la base de datos por ende lo mismo en el modelo).

Hay algún motivo en particular de porque algo que es numérico se trata como string?

Transaction management

Validating recepts handles DB transactions by itself just fine.

Using this can be dangerous:

with transaction.atomic()
    receipt.validate()

If there's a failure during this call, the can be irrecoverable data loss. validate() should internally check that no transaction is ongoing, and raise ProgramingError() if it is being run inside a transaction.

DocumentType should have code as natural key

AFIP has changed the description of this, so when re-fetching metadata, one ends up with two different DocumentTypes that have the same code (code 99).

code should probably be the natural key for this table, and metadata updates should just overwrite.

ReceiptPDF.save() o ReceiptPDF.save_pdf()

Hola Hugo, disculpá las molestias.

Tengo un problema. Cuándo cargo el receipt y quiero hacer el PDF, si uso el .save(), lanza el siguiente error:

receipts/code_1.html

Y si utilizo el .save_pdf(), lanza el siguiente error:

ReceiptPDF matching query does not exist.

¿Tendrás idea de que será?

Revalidar comprobantes

Aveces pasa que mandamos facturas al AFIP, y el sistema muere (corte de luz, crash, etc) antes de persistir el CAE en la base de datos.

Necesitamos un mecanismo para completar los datos faltantes. #81 agregó integración con el endpoint correcto para hacer esto, pero faltaría exponer una API más amigable.

Lo idea sería un método revalidate (el nombre puede cambiar):

class Receipt(models.Model):
    ...
    def validate(self) -> Optional[ReceiptValidation]:
        ...
  • El método devolvería None si el comprobante no existe en el AFIP.
  • El método guarda y devuelve un ReceiptValidation con los datos de CAE correctos.

En cuanto a tests, sería cuestión de:

  • Caso 1:

    • Crear un comprobante.
    • Validarlo
    • Borrar el ReceiptValidation
    • Llamar al método
    • Corroborar que ReceiptValidation coincida con los datos que obtuvimos al validar.
  • Caso 2:

    • Crear un comprobante
    • Asignarle un número inexistente (último + 1) y fecha
    • Llamar al método
    • Corroborar que devuelve None
  • Caso 2:

    • Crear un comprobante
    • No asignarle un número
    • Llamar al método
    • Corroborar que devuelve None

Code field in ReceiptEntry

I am asking this before subclass ReceiptEntry to add this "missing" field: does not all invoices have a code field/column in the entries details? Because I see this is missing in the corresponding Model.

Thanks.

Agregar validaciones de valores dentro de la validacion de comprobantes

Hace poco tuvimos un inconveniente con la generacion de Notas de credito donde los valores de los Vat no coincidian con los totales de la Receipt, al parecer AFIP no reboto esas notas de credito y genero inconsistencias en la base de datos de ellos.

Dejo un ejemplo de lo que esta registrado en AFIP, como podras observar la BaseImp de la AlicIva es igual al total_amount de la Receipt.

{
    'Concepto': 1,
    'DocTipo': 80,
    'DocNro': XXXXXXXXX,
    'CbteDesde': 19,
    'CbteHasta': 19,
    'CbteFch': '20210802',
    'ImpTotal': 2039.08,
    'ImpTotConc': 0.0,
    'ImpNeto': 1685.19,
    'ImpOpEx': 0.0,
    'ImpTrib': 0.0,
    'ImpIVA': 353.89,
    'FchServDesde': None,
    'FchServHasta': None,
    'FchVtoPago': None,
    'MonId': 'PES',
    'MonCotiz': 1.0,
    'CbtesAsoc': {
        'CbteAsoc': [
            {
                'Tipo': 6,
                'PtoVta': 4,
                'Nro': 321,
                'Cuit': None,
                'CbteFch': None
            }
        ]
    },
    'Tributos': None,
    'Iva': {
        'AlicIva': [
            {
                'Id': 5,
                'BaseImp': 2039.08,
                'Importe': 353.89
            }
        ]
    },
    'Opcionales': None,
    'Compradores': None,
    'PeriodoAsoc': None,
    'Resultado': 'A',
    'CodAutorizacion': 'xxxxxxxxxxxx',
    'EmisionTipo': 'CAE',
    'FchVto': '20210812',
    'FchProceso': '20210802091051',
    'Observaciones': None,
    'PtoVta': 4,
    'CbteTipo': 8
}

No se si es viable implementar alguna especie de validacion ya que es muy variable y depende del estado tributario del emisor y receptor.
Por lo pronto estoy necesitando extraer (cito de mail de afip) lo siguiente.

los XMLs de request/response (incluyendo todo el envoltorio SOAP) de una transaccion que exhiba el comportamiento que Ud. nos reporta para analizar en detalle que estan enviando a la AFIP, y que es lo que la AFIP les devuelve

Hay alguna forma de llegar al xml que recibe Zeep? De momento logre obtener el xml de la request con Client.create_message(), pero no consigo el de la response. Alguna idea?

Error 602: Sin Resultados: - Metodo FEParamGetPtosVenta

Hola! Gracias por contestar mis dudas. Me surgió un problema. Tengo cargados puntos de venta en afip, pero cuando hago el fetch_points_of_sales() me tira el error cargado en el titulo.

Datos que a lo mejor sirven:
*A la key y al certificado los generé antes de cargar los puntos de venta.
*Estoy intentando hacer el método desde el servidor de homologación.

Espero que puedas encontrar una respuesta. Gracias.

Initial Update

The bot created this issue to inform you that pyup.io has been set up on this repo.
Once you have closed it, the bot will open pull requests for updates as soon as they are available.

Eliminando TaxPayerProfile

Move los campos así:

TaxPayer

  • issuing_name
  • vat_condition
  • gross_income_conditoin
  • logo

PointOfSales

  • issuing_address
  • issuing_email
  • sales_terms

Problemas con load_metadata y loaddata

Hola! Actualicé el módulo django-afip a la nueva versión. Lo que implicó cambiar el método populate_all() por load_metadata(). El problema es que en este método no me toma la base de datos correspondiente a AFIP (porque mi sistema utiliza múltiples bases de datos). Por lo que vi, el método load_metadata() llama al comando "loaddata". El tema es que el comando loaddata pide un argumento "--database" y en el caso en que no le mando ese argumento, toma la base de datos por default. Eso hace que se me rompa el sistema. Yo hice un routers.py que redirecciona la base de datos cada vez que se trabaja con los models de afip. El tema, es que el comando loaddata no lo hace porque le asigna la base de datos por defecto, y me tira problemas con el transaction.atomic(using=bd). El problema es que en el método load_metadata() no me permite enviarle la base de datos para que la utilice el método "loaddata".

Gracias

Draft receipts and validation helpers

  • Add a is_draft field to receipts, to allow distinguishing receipts that are "ready to validate" from those that are not.

  • raise when trying to validate a receipt where is_draft=True.

  • Merge celery tasks [that do validations] from different apps and move the resulting one into this repository.

  • Bonus: Allow rendering a PDF for any receipt -- however, not-yet-validated receipts should show "DRAFT" as a number.

Locking

Locking is expected to happen externally.

Do it explicitly, remove the assumption, and document the situation.

validate() raises exceptions when it shouldn't

validate() is raising an exception even with raise_=False.

In this case (juanpsenn@5645421) I'm testing validating an older receipt (older than the last successfully validated receipt), this should fail but also raises an exception when it shouldn't.

I remember this #31 (comment) and I think that validate() can easily be transactional. Otherwise, this causes integrity issues in the database if the transaction is not handled outside.

Some questions:

  • Why errors are handled differently?
  • Should validate() be transactional itself?

Facturas a consumidor final mayores a $5000

Desde lo que me explica el contador, las facturas que superen los $5000 en efectivo y $10000 con tarjeta deben ir acompanadas por los datos del cliente, numero y tipo de documento, nombre y domicilio.
La factura que se valida desde django_afip solo se guarda el numero y tipo de documento. Mi pregunta: es suficiente para validar la factura? Visualmente modifique el pdf para que se muestren los datos pero solo es visual.

Token de acceso al WNS

El CEE ya posee un TA valido para el acceso al WSN solicitado

Is there any way to take control of the request for a new token? I don't know why this happen from time to time.
I found that this error appears when you are trying to get a new token when there is an other valid token. How can i get that valid token and used it intead of asking for a new one?

¿Steps to create a Receipt, validate, etc. not using Admin interface?

Hi,

Since I am not using the Admin interface (and to avoid reading the entire admin code), I would like to know which are the steps to follow for generating a Receipt (or many), validate them and generate the corresponding PDF Receipt.

I ask this because the docs "assumes" that we are going to use the Admin interface to achieve this (and for me is not the case, I am not using Admin interface and I am coding all the views).

So, I think the docs lacks of a proper guide to follow this steps; thats why my question.

Thanks in advance.

Factura A - Generar PDF

Buenas tardes,

Estuve generando facturas B sin inconvenientes, pero al momento de hacer una factura a otro responsable inscripto intento generar una A y me sucede lo siguiente:
-- La factura se crea y se valida adecuadamente (recibe CAE y la veo en mi portal de AFIP).
-- No se genera el PDF correspondiente.

Este es el codigo que obtengo de error:
receipts/30716576376/pos_2/code_1.html, receipts/30716576376/code_1.html, receipts/code_1.html, receipts/1.html

error_a

Desde ya muchas gracias, la herramienta es muy clara de utilizar

No hay tests que chequeen como parseamos observaciones

El único tests acá está comentado:

@skip("Currently not working -- needs to get looked at.")
def test_validation_with_observations(self):
receipt = factories.ReceiptFactory(
document_number=20291144404,
document_type__code=80,
point_of_sales=models.PointOfSales.objects.first(),
receipt_type__code=1,
)
factories.VatFactory(vat_type__code=5, receipt=receipt)
factories.TaxFactory(tax_type__code=3, receipt=receipt)
errs = models.Receipt.objects.all().validate()
assert len(errs) == 0
assert receipt.validation.result == models.ReceiptValidation.RESULT_APPROVED
assert models.ReceiptValidation.objects.count() == 1
assert models.Observation.objects.count() == 1
assert receipt.validation.observations.count() == 1

Habría que buscar un caso que sepamos con certeza siempre devuelve observaciones, y crear un test de ese.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.