Panel de cumplimiento antifraude con los requisitos R1 a R16

El SIF Antifraude es un prototipo de Sistema Informático de Facturación que implementa los requisitos de la normativa antifraude española (RD 1007/2023 y Orden HAC/1177/2024) en su modo NO Veri*Factu, el universal y obligatorio para cualquier sistema de facturación. Está escrito en PHP 8.1 puro sobre SQLite, sin librerías intermediarias: la firma XAdES, el encadenamiento por huella y el registro de eventos están programados a mano usando las extensiones nativas de PHP (OpenSSL, DOM, hash, PDO SQLite). El objetivo es demostrar, de forma verificable y auditable, cómo un sistema garantiza integridad, conservación, trazabilidad e inalterabilidad de los registros de facturación.

El sistema cubre el ciclo completo de un registro: alta y anulación de facturas, rectificativas, huella SHA-256 encadenada (cada registro incorpora la huella del anterior), firma XAdES Enveloped con certificado cualificado, un libro de eventos del SIF también encadenado y firmable, un proceso de detección de anomalías que recalcula la cadena y valida las firmas, y exportación a XML. Una pantalla de cumplimiento evalúa los requisitos legales (R1 a R16), varios de ellos en vivo contra el estado real de la base de datos.

Es un prototipo de referencia con fines de demostración y aprendizaje, no un SIF certificado: la firma XAdES es funcional a nivel de perfil BES y, según indica la propia documentación, debe validarse contra el perfil exacto de la AEAT antes de producción. Sin certificado configurado el sistema funciona igual, pero deja los registros sin firmar y marca ese requisito (R5) como pendiente.

  1. Arranque y sesión de funcionamiento En cada petición, el front controller invoca SesionSif::controlar(), que registra el evento INSTALACION la primera vez, detecta el ARRANQUE al primer acceso sin sesión activa o tras inactividad superior al timeout (1800 s por defecto) y actualiza un heartbeat en cada petición. La PARADA se registra de forma explícita (botón Detener SIF) o se infiere retroactivamente cuando, al volver, la sesión anterior había superado el tiempo de inactividad. El estado de la sesión se guarda en una tabla 'estado' de SQLite.
  2. Emisión y encadenamiento del registro Al emitir una factura, LibroRegistros::emitir() toma la huella del último registro guardado, marca si es el primer registro y calcula la huella SHA-256 del nuevo registro. La huella se obtiene concatenando los campos en el orden oficial de la AEAT (IDEmisorFactura, NumSerieFactura, FechaExpedicionFactura, TipoFactura, CuotaTotal, ImporteTotal, la huella anterior y FechaHoraHusoGenRegistro en formato ISO 8601) como pares clave=valor unidos por '&', y aplicando SHA-256 en mayúsculas hexadecimales. Así cada registro queda enlazado al anterior formando una cadena.
  3. Generación del XML y firma XAdES RegistroFacturacion::toXml() construye el XML del registro con DOMDocument. Si hay certificado cargado, Firma::firmar() le añade una firma XAdES Enveloped: calcula el digest del documento con canonicalización C14N exclusiva, construye SignedInfo con dos referencias (el documento y SignedProperties), incrusta el certificado X509 en KeyInfo, añade SignedProperties con SigningTime y SigningCertificate (digest e issuer/serial del certificado), y firma el SignedInfo canonicalizado con openssl_sign (RSA-SHA256). El XML firmado se guarda en la columna firma_xml. Si no hay certificado, el registro se guarda sin firmar.
  4. Registro de eventos Cada acción relevante (generación de registro, lanzamiento de detección, exportación, instalación, arranque, parada) se anota en LibroEventos con su propia huella encadenada (calculada sobre tipo de evento, detalle, fecha-hora con huso y huella anterior) y, si hay certificado, su firma XAdES. El catálogo de tipos de evento (Catalogo::EVENTOS) reproduce los exigidos por el art. 9 de la Orden HAC/1177/2024.
  5. Verificación y detección de anomalías VerificadorIntegridad recalcula la huella de cada registro desde los campos almacenados y la compara con la guardada, comprueba el enlace de la cadena (que la huella anterior coincida con la del registro previo), valida cada firma XAdES con Firma::verificar() (que reconstruye el documento sin la firma y verifica el digest del documento y el SignatureValue) y detecta huecos o duplicados en la numeración. El lanzamiento se anota como evento LANZA_DET_FACT/LANZA_DET_EVENTO y, si hay problemas, como ANOMALIA_FACT/ANOMALIA_EVENTO.
  6. Exportación y cotejo Exportador genera un XML legible de todos los registros o de todos los eventos, lo guarda en la carpeta storage y anota el evento de exportación (EXPORTACION_FACT/EXPORTACION_EVENTO). Al emitir una factura se construye además la URL de cotejo de la AEAT (NIF, número/serie, fecha e importe; apunta al endpoint de validación de la sede) que se almacena y se muestra como código QR en el detalle del registro.

Registro de alta y anulación

Genera un registro de facturación de alta por cada factura y un registro de anulación independiente cuando se anula; el alta original se marca como anulada (anulada=1) pero nunca se borra, cumpliendo la conservación.

Huella SHA-256 encadenada

Calcula la huella de cada registro (alta, anulación o evento) sobre sus campos concatenados en el orden oficial como pares clave=valor, incorporando la huella del registro anterior para formar una cadena cuya rotura es detectable.

Firma electrónica XAdES Enveloped

Firma cada registro y cada evento con un certificado cualificado en formato .p12, implementando el perfil XAdES-BES (SignedInfo, SignatureValue, KeyInfo X509 y SignedProperties con SigningTime y SigningCertificate) con OpenSSL y canonicalización C14N exclusiva, sin librerías externas.

Libro de eventos del SIF

Mantiene una bitácora encadenada y firmable con los eventos exigidos: instalación, arranque, parada, generación de registro, lanzamiento y detección de anomalías, restauración y exportación, según el catálogo del art. 9.

Detección de anomalías e inalterabilidad

Recalcula toda la cadena de huellas y valida las firmas; si alguien altera un importe directamente en la base de datos, la verificación lo detecta como huella no coincidente o firma inválida y lo anota como evento de anomalía.

Numeración correlativa sin huecos

Agrupa las altas por prefijo de serie y comprueba que los sufijos numéricos sean consecutivos, reportando huecos y duplicados; además sugiere el siguiente número correlativo al preparar una emisión.

Rectificativas y trazabilidad del ciclo de vida

Permite corregir una factura mediante rectificativa (por sustitución o por diferencias) sin editar el original, marca la factura origen como rectificada y reconstruye el ciclo de vida completo (alta, rectificativas, anulación) consultando los registros enlazados por número/serie.

Subsanación y rechazo previo

Incluye los campos Subsanacion y RechazoPrevio del XSD de la AEAT en el registro de alta, para marcar reenvíos de registros con errores o rechazados previamente; ambos quedan reflejados en el XML firmado cuando aplican.

Exportación a XML

Exporta registros y eventos a ficheros XML legibles guardados en disco (carpeta storage), anotando el evento de exportación correspondiente para dejar traza de la operación.

Panel de cumplimiento y QR de cotejo

Evalúa los 16 requisitos legales y muestra su estado; varios se comprueban en vivo contra el estado real del sistema (integridad de la cadena, validez de las firmas, disponibilidad del certificado, eventos registrados, huecos de numeración) y otros reflejan capacidades soportadas por diseño. Genera además el código QR con la URL de cotejo de cada factura.

  • PHP 8.1 (puro, sin framework): Lenguaje único del prototipo; toda la lógica de SIF, firma, encadenamiento y la interfaz web se implementan sin framework ni dependencias de Composer, con un autoload propio.
  • SQLite vía PDO: Almacena de forma local y portable los dos libros (registros y eventos) y la tabla de estado; las migraciones crean el esquema con consultas parametrizadas y no existe ninguna operación DELETE, garantizando la conservación.
  • OpenSSL (extensión PHP): Lee el certificado cualificado .p12 (openssl_pkcs12_read), firma el SignedInfo con RSA-SHA256 (openssl_sign) y verifica las firmas con la clave pública del certificado incrustado (openssl_verify).
  • DOM y C14N: Construyen el XML del registro y la estructura ds:Signature de XAdES, y aplican la canonicalización exclusiva (C14N) necesaria para calcular digests y firmar de forma reproducible.
  • hash (SHA-256): Calcula la huella SHA-256 en mayúsculas hexadecimales de cada registro y evento, base del encadenamiento y de la detección de alteraciones.
  • XAdES Enveloped (perfil BES): Es el formato de firma exigido por el art. 14 de la Orden HAC/1177/2024 para el modo NO Veri*Factu; se implementa a mano con SignedProperties, SigningTime y SigningCertificate.
  • qrcodejs (CDN, lado cliente): Librería JavaScript cargada por CDN que renderiza en el navegador el código QR a partir de la URL de cotejo de la factura mostrada en la pantalla de detalle.
  • Front controller PHP + sesiones: Un index.php enruta todas las acciones (emitir, anular, rectificar, verificar, exportar, configurar certificado) sobre sesiones PHP; el certificado se puede definir por config.php o subirlo desde la web, y su contraseña se mantiene en la sesión sin escribirla en el fichero de configuración.
  • Protección CSRF y escapado HTML: Todas las acciones POST validan un token CSRF con hash_equals (devolviendo 419 si falla) y la salida se escapa con htmlspecialchars, mitigando CSRF y XSS en la interfaz de demostración.
  • Desarrolladores de software de gestión o ERP que necesitan entender, de forma concreta, cómo cumplir la normativa antifraude (huella encadenada, firma XAdES y registro de eventos) antes de integrarla en su producto.
  • Asesorías y despachos que quieren mostrar a sus clientes, con una demo tangible, qué significa la obligación de tener un SIF conforme y cómo se detecta cualquier manipulación de los registros.
  • Pymes y autónomos que evalúan proveedores de facturación y quieren un banco de pruebas para comprobar qué requisitos legales cubre realmente una solución antes de contratarla.
  • Equipos de auditoría y cumplimiento que necesitan verificar la inalterabilidad de una serie de facturas: recalcular la cadena de huellas, validar firmas y exportar registros y eventos para su revisión.
  • Formación técnica y demostraciones sobre la diferencia entre el modo NO Veri*Factu (firma local obligatoria) y Veri*Factu (envío en tiempo real a la AEAT), usando un sistema funcional en vez de diapositivas.
  • Dominio criptográfico aplicado: implementación propia de firma XAdES Enveloped y de encadenamiento por huella SHA-256 sobre OpenSSL y DOM, sin recurrir a librerías de terceros.
  • Traducción de normativa a software verificable: cada requisito del RD 1007/2023 y la Orden HAC/1177/2024 se documenta como criterio de aceptación y varios se comprueban en vivo contra el estado real del sistema.
  • Diseño orientado a la inalterabilidad: ausencia total de borrado, conservación en SQLite y un verificador que detecta cualquier alteración como anomalía registrada.
  • Modelado de eventos del ciclo de vida del sistema: instalación, arranque y parada inferidos por una sesión de funcionamiento con heartbeat en un entorno web sin proceso residente.
  • Buenas prácticas de seguridad web básicas: protección CSRF con hash_equals, escapado de salida contra XSS y consultas parametrizadas con PDO.
  • Arquitectura limpia y autocontenida en PHP puro: separación clara entre dominio (Hash, Firma, libros, verificador), persistencia y capa web, ejecutable también por CLI mediante scripts de ejemplo.

Capturas con datos de demostración. Los certificados y datos fiscales reales nunca se publican.

De prototipo a producción

Si algo de esto encaja con un problema real de tu negocio, lo convertimos en una solución mantenible y con control total.

Hablemos de tu proyecto

Diagnóstico gratuito — Detecta dónde se pierden horas y qué automatización tiene más retorno

Pedir diagnóstico