Encadenamiento criptográfico de facturas
Encadenamiento criptográfico de facturas
Cómo funciona el sistema de encadenamiento VeriFactu y por qué garantiza la integridad de tus facturas.
¿Qué es el encadenamiento?
El encadenamiento es un mecanismo que vincula cada factura con la anterior mediante un hash criptográfico, creando una cadena inmutable similar a blockchain.
Objetivo: Impedir que se eliminen, modifiquen o inserten facturas sin que la AEAT lo detecte.
Cómo funciona
Primera factura del año
La primera factura (ej. 2025/0001) genera su hash a partir de sus propios datos:
Datos de la factura:
├─ NIF emisor: B12345678
├─ Número: 2025/0001
├─ Fecha: 2025-01-02
├─ Base: 1000.00
├─ IVA: 210.00
├─ Total: 1210.00
│
└─ SHA-256(datos) = Hash: a3f5d8e234c1b9f8e7a6d5c4b3a2f1e0...
Hash resultado: a3f5d8e234c1b9f8e7a6d5c4b3a2f1e0d9c8b7a6f5e4d3c2b1a0987654321fedcba
Segunda factura
La segunda factura incluye el hash de la anterior:
Factura 2025/0002
├─ Hash anterior: a3f5d8e234c1b9f8...
├─ NIF emisor: B12345678
├─ Número: 2025/0002
├─ Fecha: 2025-01-05
├─ Base: 500.00
├─ IVA: 105.00
├─ Total: 605.00
│
└─ SHA-256(hash_anterior + datos) = b9c4f1a765e8d3c2...
Tercera y siguientes
Cada factura repite el proceso:
Factura 2025/0001
└─ Hash: a3f5d8e2...
│
├─> Factura 2025/0002
│ └─ Hash: b9c4f1a7...
│ │
│ ├─> Factura 2025/0003
│ │ └─ Hash: d2e8a3c5...
│ │ │
│ │ ├─> Factura 2025/0004
│ │ │ └─ Hash: f7b6c9d4...
│ │ │
│ │ └─> ...
Resultado: Cadena criptográfica ininterrumpida.
Algoritmo SHA-256
¿Qué es SHA-256?
SHA-256 (Secure Hash Algorithm 256 bits) es un algoritmo criptográfico que:
- ✅ Genera un hash de 64 caracteres hexadecimales
- ✅ Es unidireccional (no se puede revertir)
- ✅ Es determinista (mismo input = mismo hash)
- ✅ Cualquier cambio mínimo en el input cambia completamente el hash
- ✅ Es resistente a colisiones (prácticamente imposible que dos inputs den el mismo hash)
Ejemplo:
Input: "Factura 2025/0001 - 1210.00€"
SHA-256: a3f5d8e234c1b9f8e7a6d5c4b3a2f1e0d9c8b7a6f5e4d3c2b1a0987654321fedcba
Input: "Factura 2025/0001 - 1210.01€" (¡solo 1 céntimo más!)
SHA-256: 7d8f3a9b12e4c5f6a8b7d9e0f1a2b3c4d5e6f7a8b9c0d1e2f3a4b5c6d7e8f9a0b1c2
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Completamente diferente
¿Por qué SHA-256?
Es el mismo algoritmo usado en:
- Bitcoin y criptomonedas
- Certificados SSL/TLS
- Firma digital de documentos
- Verificación de integridad de software
Seguridad: Prácticamente imposible de romper con tecnología actual (necesitarías 2^256 intentos).
Datos incluidos en el hash
Según el RD 1007/2023, el hash debe incluir:
Datos obligatorios
const datosParaHash = {
// Identificación
nif_emisor: "B12345678",
numero_factura: "2025/0001",
// Fechas
fecha_expedicion: "2025-01-02",
// Tipo
tipo_factura: "F1", // F1=Completa, F2=Simplificada, F3=Rectificativa
// Importes
base_imponible: "1000.00",
tipo_iva: "21",
cuota_iva: "210.00",
importe_total: "1210.00",
// Encadenamiento
hash_anterior: "0000000000..." // Solo en facturas posteriores a la primera
}
Formato de serialización
Los datos se serializan en una cadena de texto siguiendo este orden:
<NIF><NumFactura><Fecha><TipoFactura><Base><TipoIVA><CuotaIVA><Total><HashAnterior>
Ejemplo factura 2025/0002:
B123456782025/00022025-01-05F1500.00210105.00605.00a3f5d8e234c1b9f8e7a6d5c4b3a2f1e0d9c8b7a6f5e4d3c2b1a0987654321fedcba
Después se aplica SHA-256 a esta cadena.
Por qué es inmutable
Caso 1: Intentas eliminar una factura
Factura 2025/0001 (Hash: a3f5d8e2...)
↓
Factura 2025/0002 (Hash anterior: a3f5d8e2...) ← Eliminas esta
↓
Factura 2025/0003 (Hash anterior: b9c4f1a7...) ← ¡El hash no existe!
Resultado: La AEAT detecta que falta un eslabón en la cadena.
Caso 2: Intentas modificar una factura
Original:
Factura 2025/0002: 500€ → Hash: b9c4f1a7...
↓
Factura 2025/0003: (usa b9c4f1a7...) → Hash: d2e8a3c5...
Modificas 2025/0002 a 600€:
Factura 2025/0002: 600€ → Hash: NUEVO_HASH_DIFERENTE (ej. x8k3m9p2...)
↓
Factura 2025/0003: (usa b9c4f1a7...) ← ¡Hash incorrecto!
Resultado: La AEAT detecta que el hash de 2025/0003 no coincide con el nuevo hash de 2025/0002.
Caso 3: Intentas insertar una factura
Factura 2025/0001 → Hash: a3f5d8e2...
↓
[Insertas factura 2025/0001bis]
↓
Factura 2025/0002 → Hash anterior: a3f5d8e2... (no incluye 0001bis)
Resultado: La factura insertada no aparece en la cadena oficial registrada en la AEAT.
Implementación en VERIFACTURING
Generación automática
VERIFACTURING genera el hash automáticamente al crear cada factura:
// Pseudocódigo simplificado
function generarHashFactura(factura: Factura, hashAnterior: string): string {
// 1. Obtener datos normalizados
const datos = [
factura.nif_emisor,
factura.numero,
factura.fecha_expedicion,
factura.tipo,
formatear_importe(factura.base_imponible),
factura.tipo_iva.toString(),
formatear_importe(factura.cuota_iva),
formatear_importe(factura.importe_total),
hashAnterior || "0".repeat(64) // Primera factura: 64 ceros
].join("");
// 2. Aplicar SHA-256
const hash = sha256(datos);
return hash;
}
Validación continua
Cada vez que se crea una factura, VERIFACTURING:
- ✅ Obtiene el hash de la última factura
- ✅ Genera el nuevo hash incluyendo el anterior
- ✅ Guarda ambos hashes en la base de datos
- ✅ Envía a la AEAT para registro oficial
- ✅ Marca la factura como "encadenada correctamente"
Logs de auditoría
VERIFACTURING mantiene logs inmutables:
{
"evento": "factura_creada",
"timestamp": "2025-10-01T10:32:15.123Z",
"factura_id": "uuid-1234",
"numero": "2025/0042",
"hash_generado": "a3f5d8e234...",
"hash_anterior": "b9c4f1a765...",
"usuario": "usuario@empresa.com",
"ip": "192.168.1.100"
}
Estos logs nunca se pueden modificar o eliminar y sirven como evidencia en inspecciones.
Primera factura del sistema
Hash de la "factura cero"
La primera factura no tiene factura anterior, por lo que usa un hash especial:
Hash anterior (primera factura):
0000000000000000000000000000000000000000000000000000000000000000
64 ceros indican que es el inicio de la cadena.
¿Qué pasa si reseteas la numeración?
Si empiezas un nuevo año con nueva serie (ej. 2026/0001), tienes dos opciones:
Opción 1: Continuar la cadena (recomendado)
...
├─ Factura 2025/9999 → Hash: x8k3m9p2...
│
└─> Factura 2026/0001 → Hash anterior: x8k3m9p2...
La cadena no se rompe aunque cambies de serie.
Opción 2: Nueva cadena
Nueva serie: 2026A/0001
Hash anterior: 0000000000... (nuevo inicio)
Empiezas una cadena nueva, independiente de la anterior.
⚠️ Importante: Consulta con tu asesor fiscal antes de romper la cadena.
Series de facturación
¿Las series comparten cadena?
Depende de tu configuración. Puedes:
Opción A: Cadena única para todas las series
Serie A:
├─ 2025A/0001 → Hash: a3f5d8e2...
│
Serie B:
├─ 2025B/0001 → Hash anterior: a3f5d8e2... (de serie A)
│
Serie A:
├─ 2025A/0002 → Hash anterior: b9c4f1a7... (de serie B)
Opción B: Cadena independiente por serie
Serie A:
├─ 2025A/0001 → Hash: a3f5d8e2...
├─ 2025A/0002 → Hash anterior: a3f5d8e2...
Serie B:
├─ 2025B/0001 → Hash: x8k3m9p2... (independiente)
├─ 2025B/0002 → Hash anterior: x8k3m9p2...
Recomendación: Cadena única (Opción A) para máxima transparencia.
Facturas rectificativas
¿Cómo se encadenan?
Las facturas rectificativas se encadenan normalmente en la secuencia:
2025/0001 (Hash: a3f5d8e2...)
↓
2025/0002 (Hash: b9c4f1a7...) ← Error aquí
↓
2025/0003 (Hash: d2e8a3c5...) ← Rectificativa de 2025/0002
↓
2025/0004 (Hash: f7b6c9d4...)
Datos adicionales en rectificativa:
{
tipo_factura: "F3", // Rectificativa
factura_rectificada: "2025/0002", // Referencia
motivo: "Error en importe",
// ... resto de datos normales
}
La rectificativa tiene su propio hash que incluye:
- Hash de la factura anterior (2025/0002)
- Referencia a la factura que rectifica
- Nuevos datos correctos
Verificación del encadenamiento
Verificación automática de VERIFACTURING
VERIFACTURING verifica automáticamente:
- ✅ Al crear factura: Que el hash anterior existe y es correcto
- ✅ Al enviar a AEAT: Que la cadena es válida
- ✅ Diariamente: Auditoría completa del encadenamiento
- ✅ En cada inicio: Integridad de la base de datos
Verificación manual
Puedes verificar el encadenamiento desde:
Panel de facturas > Herramientas > Verificar encadenamiento
El sistema comprobará:
- ✅ Todos los hashes son correctos
- ✅ No hay facturas faltantes
- ✅ El orden es correcto
- ✅ No hay duplicados
Resultado:
✅ Encadenamiento correcto
📋 3.482 facturas verificadas
🔗 Cadena ininterrumpida desde 2025-01-02
🔒 Hash final: f7b6c9d4e8a3f5c2...
Verificación en la AEAT
La AEAT verifica automáticamente:
- Cada factura que le envías
- Que el hash coincida con el anterior registrado
- Que no haya "saltos" en la secuencia
Si detecta inconsistencias, rechaza la factura y te notifica.
Problemas y soluciones
Problema: "Hash incorrecto"
Causa: La cadena se ha roto (factura eliminada, modificada, o error técnico).
Solución:
- Contactar con soporte inmediatamente
- No crear más facturas hasta resolver
- Investigar la causa (¿error técnico? ¿manipulación?)
- Restaurar desde backup si es necesario
Problema: "Factura faltante en cadena"
Causa: Se eliminó una factura de la base de datos.
Solución:
- Restaurar factura desde backup
- Si no es posible, contactar AEAT para notificar
- Puede requerir auditoría completa
Problema: "Orden de facturas incorrecto"
Causa: Se crearon facturas con fechas/números fuera de orden.
Solución:
- El encadenamiento se basa en orden de creación, no en número de factura
- Si el hash es correcto, no hay problema técnico
- Ajusta la numeración para próximas facturas
Preguntas frecuentes
¿Puedo cambiar mi software de facturación?
Sí, pero debes:
- Exportar todas las facturas con sus hashes
- Importarlas al nuevo software
- Continuar la cadena desde el último hash
VERIFACTURING facilita este proceso con importación automática.
¿Qué pasa si hay un error en el hash?
Si el error es técnico (bug del software):
- Contactar soporte
- Investigar la causa
- Corregir el software
- Posiblemente reenviar facturas a la AEAT
Si el error es por manipulación:
- Posible sanción de la AEAT
- Auditoría completa
- Responsabilidad legal
¿La AEAT puede recalcular los hashes?
Sí. La AEAT tiene todos tus datos y puede verificar independientemente que los hashes son correctos.
¿Puedo tener dos cadenas simultáneas?
Técnicamente sí (con series independientes), pero no es recomendable.
Lo normal es mantener una única cadena para toda tu facturación.
¿El hash incluye los datos del cliente?
No. Solo incluye:
- NIF emisor (tu NIF)
- Número de factura
- Fechas
- Importes (base, IVA, total)
- Hash anterior
No incluye nombre del cliente, descripción detallada, etc.
Recursos técnicos
Especificaciones oficiales
📄 AEAT - Especificación XML VeriFactu https://sede.agenciatributaria.gob.es/verifactu/docs
Herramientas
🔧 Calculadora SHA-256 online https://emn178.github.io/online-tools/sha256.html
Código de ejemplo
// Ejemplo simplificado en JavaScript
import crypto from 'crypto';
function calcularHashFactura(factura, hashAnterior) {
const datos = [
factura.nif,
factura.numero,
factura.fecha,
factura.tipo,
factura.base.toFixed(2),
factura.iva.toString(),
factura.cuotaIva.toFixed(2),
factura.total.toFixed(2),
hashAnterior || "0".repeat(64)
].join("");
return crypto.createHash('sha256').update(datos).digest('hex');
}
// Ejemplo de uso
const factura1 = {
nif: "B12345678",
numero: "2025/0001",
fecha: "2025-01-02",
tipo: "F1",
base: 1000.00,
iva: 21,
cuotaIva: 210.00,
total: 1210.00
};
const hash1 = calcularHashFactura(factura1, null);
console.log("Hash factura 1:", hash1);
// Output: a3f5d8e234c1b9f8e7a6d5c4b3a2f1e0d9c8b7a6f5e4d3c2b1a0987654321fedcba
¿Necesitas ayuda?
Si tienes dudas sobre el encadenamiento:
- 💬 Chat IA: Pregunta al asistente
- 📧 Email: soporte@verifacturing.es
- 📞 Teléfono: 900 123 456 (L-V 9-18h)
- 🔧 Soporte técnico: soporte-tecnico@verifacturing.es
Más información:
¿Te ha resultado útil este artículo?