Encadenamiento criptográfico de facturas

1 de octubre de 2025
verifactu

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:

  1. ✅ Obtiene el hash de la última factura
  2. ✅ Genera el nuevo hash incluyendo el anterior
  3. ✅ Guarda ambos hashes en la base de datos
  4. ✅ Envía a la AEAT para registro oficial
  5. ✅ 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:

  1. Al crear factura: Que el hash anterior existe y es correcto
  2. Al enviar a AEAT: Que la cadena es válida
  3. Diariamente: Auditoría completa del encadenamiento
  4. 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:

  1. Contactar con soporte inmediatamente
  2. No crear más facturas hasta resolver
  3. Investigar la causa (¿error técnico? ¿manipulación?)
  4. Restaurar desde backup si es necesario

Problema: "Factura faltante en cadena"

Causa: Se eliminó una factura de la base de datos.

Solución:

  1. Restaurar factura desde backup
  2. Si no es posible, contactar AEAT para notificar
  3. 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:

  1. Exportar todas las facturas con sus hashes
  2. Importarlas al nuevo software
  3. 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):

  1. Contactar soporte
  2. Investigar la causa
  3. Corregir el software
  4. Posiblemente reenviar facturas a la AEAT

Si el error es por manipulación:

  1. Posible sanción de la AEAT
  2. Auditoría completa
  3. 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?

¿Aún tienes dudas?

Contacta con nuestro equipo de soporte