Pular para o conteúdo
getnextpdf.com

Enterprise edição

Compliance — Referência Profunda

O módulo Compliance encaminha um PDF finalizado a um sidecar de validação externo e retorna um resultado normalizado. O ComplianceGateway resolve o sidecar responsável a partir de um ComplianceProfile, aplica uma política de disponibilidade fail-closed e envolve cada veredito de ferramenta em um ExternalValidationResult. Há pontes para veraPDF (PDF/A, PDF/UA, PDF 2.0 Arlington), EU DSS (níveis PAdES), o sidecar combinado Mustang/KoSIT (ZUGFeRD, Factur-X, EN 16931) e um daemon KoSIT autônomo. O módulo também fornece o carimbo de prontidão AiReadyCertifier e um executor para a suíte de testes oficial KoSIT XRechnung.

Esse recurso é distribuído no NextPDF Enterprise (nextpdf/enterprise) e é ativado por um envelope de licença de nível Enterprise. Uma implantação sem esse direito de uso não carrega as classes do recurso. Compare as edições e obtenha uma licença.

A superfície Compliance/Evidence é licenciada pela capacidade enterprise.compliance.evidence. Um direito de uso ausente ou expirado nega o recurso; ele não rebaixa silenciosamente o comportamento.

EdiçãoSuperfície de compliance
CoreVerificações de fluxo de bytes e de gramática em processo; sem delegação a sidecar externo.
ProValidação EN 16931 / Factur-X / ZUGFeRD em processo; sem sidecar externo.
EnterpriseGateway de validadores externos (este módulo) com um resultado unificado e uma política fail-closed.

O validador de fatura eletrônica em processo do Pro e o sidecar ZUGFeRD externo do Enterprise são superfícies distintas. O gateway de validadores externos é distribuído apenas no pacote nextpdf/enterprise.

Terminal window
composer require nextpdf/enterprise:^3
SímboloParâmetrosComportamento padrãoRetornaLança ou falha comNotas
ComplianceGateway::__constructlist<ExternalValidator> $validators, LoggerInterface $logger, bool $optional = falseIndexa os validadores por nome de ferramentaO modo opcional rebaixa a verificação de disponibilidade a apenas aviso
ComplianceGateway::validatestring $pdfContent, ComplianceProfile $profile, array $options = []Resolve o validador por ComplianceProfile::toolName(), verifica a disponibilidade, delega?ExternalValidationResultComplianceSidecarUnavailableException; InvalidArgumentException (nenhum validador registrado para a ferramenta)Retorna null apenas no modo opcional com o sidecar inativo
ComplianceGateway::validateAllProfilesstring $pdfContent, string $toolNameValida todos os perfis mapeados para a ferramentalist<ExternalValidationResult>Igual a validate()Ignora resultados null (modo opcional)
ComplianceGateway::healthCheckSonda o endpoint de saúde de cada sidecar registradoarray<string, bool>Informa a acessibilidade; não valida documento algum
ComplianceGateway::buildComplianceMatrix (estático)list<ExternalValidationResult> $results, string $commitShaReduz os resultados a uma matriz versionada por esquemaarray<string, mixed>Versão do esquema 1.0; registra a saída da ferramenta, não afirma nada
ComplianceProfile (enum)15 casos com backing de stringMapeia cada perfil para um rótulo de padrão e uma ferramentastandardReference(): string, toolName(): string
ExternalValidator (interface)Contrato de ponte de sidecar sobre PSR-18validate() lança ComplianceSidecarUnavailableException em falha de transportegetToolName(), isAvailable(), validate()
VeraPdfValidator::validateAssinatura da interfacePOST multipart ao sidecar REST do veraPDF; análise do relatório JSONExternalValidationResultComplianceSidecarUnavailableException; InvalidArgumentException (perfil não suportado)PDF/A, PDF/UA, Arlington; analisa apenas JSON, nunca XML
DssValidator::validateAssinatura da interfacePOST JSON em base64 ao sidecar REST do EU DSSExternalValidationResultComplianceSidecarUnavailableException; InvalidArgumentException (perfil não suportado)PAdES B-B até B-LTA; o construtor rejeita timeouts abaixo de um segundo
ZugferdExternalValidator::validateAssinatura da interfacePOST multipart ao sidecar combinado Mustang/KoSITExternalValidationResultComplianceSidecarUnavailableException (também em circuit breaker aberto); InvalidArgumentException (perfil não suportado)ZUGFeRD 2.4, Factur-X 1.08, EN 16931; circuit breaker injetado opcional
KoSitValidator::validateAssinatura da interfacePOST de XML bruto a um daemon KoSIT autônomoExternalValidationResultComplianceSidecarUnavailableException; InvalidArgumentException (perfil não suportado)Apenas EN 16931; analisa o relatório Schematron SVRL de forma fail-closed
ExternalValidationResultObjeto de valor readonlyVeredito de ferramenta normalizadopasses(), fails(), nonConformanceCount(), toComplianceMatrix()
NonConformanceObjeto de valor readonlyAchado único com id da regra, cláusula, severidade, localizaçãotoArray()
ComplianceSidecarUnavailableExceptionstring $toolName, string $endpoint, int $code = 0, ?Throwable $previous = nullSinal fail-closed de indisponibilidade do sidecartoolName e endpoint públicos readonly
AiReadyCertifier::certifystring $pdfBytesAvalia três critérios de prontidão; carimba a proveniência XMParray{0: AiReadyCertification, 1: string}InvalidArgumentException (o carimbo exige uma tabela de referências cruzadas clássica)O segundo elemento é igual à entrada quando o nível é not_certified
AiReadyCertificationObjeto de valor readonlyAvaliação de prontidão com nível, contagem de critérios, problemas, hash de origemRótulo de prontidão interno, não uma certificação de padrões
XRechnungTestSuiteRunner::__constructstring $suitePath, ExternalValidator $validator, bool $useCuratedNegativeFallback = trueResolve o diretório da suíte extraídaInvalidArgumentException (o diretório não existe)Tem como alvo a suíte de testes oficial KoSIT XRechnung
XRechnungTestSuiteRunner::runbool $stopOnFirstFailure = falseValida cada instância da suíte pela ponteXRechnungTestSuiteResultXRechnungTestSuiteException (validador indisponível; nenhum arquivo XML)Também isAvailable(), getSuitePath(), discoverTestFiles()
XRechnungTestSuiteResultObjeto de valor readonlyResultado agregado da suíteallPassed(), totalCount(), getFailures(), getErrors(), toSummary()
XRechnungTestCaseResultObjeto de valor readonlyResultado por casopassed(), hasError(), getFilename()
XRechnungTestSuiteExceptionConstrutores estáticosSinal de falha em tempo de execução da suíteselfvalidatorUnavailable(), noTestFilesFound(string $suitePath)
namespace NextPDF\Enterprise\Compliance;
final class ComplianceGateway
{
/** @param list<ExternalValidator> $validators */
public function __construct(
array $validators,
private readonly LoggerInterface $logger,
private readonly bool $optional = false,
);
/** @param array<string, mixed> $options */
public function validate(
string $pdfContent,
ComplianceProfile $profile,
array $options = [],
): ?ExternalValidationResult;
/** @return list<ExternalValidationResult> */
public function validateAllProfiles(string $pdfContent, string $toolName): array;
/** @return array<string, bool> */
public function healthCheck(): array;
/**
* @param list<ExternalValidationResult> $results
* @return array<string, mixed>
*/
public static function buildComplianceMatrix(array $results, string $commitSha): array;
}
interface ExternalValidator
{
public function getToolName(): string;
public function isAvailable(): bool;
/** @param array<string, mixed> $options */
public function validate(
string $pdfContent,
ComplianceProfile $profile,
array $options = [],
): ExternalValidationResult;
}
enum ComplianceProfile: string
{
case PdfA1b = 'pdfa-1b';
// PdfA2b, PdfA3b, PdfA4, PdfA4f, PdfUa1, PdfUa2, Pdf20Arlington,
// PadesBasic, PadesTimestamp, PadesLongTerm, PadesArchive,
// Zugferd24, FacturX108, En16931
public function standardReference(): string;
public function toolName(): string;
}
final class AiReadyCertifier
{
/** @return array{0: AiReadyCertification, 1: string} Tuple of [certification, stamped PDF bytes] */
public function certify(string $pdfBytes): array;
}

ComplianceGateway::validate() resolve o ExternalValidator registrado cujo getToolName() corresponde a ComplianceProfile::toolName(), verifica isAvailable(), delega e retorna um ExternalValidationResult normalizado. Regras observáveis externamente:

  • Padrão fail-closed. Quando o sidecar resolvido está indisponível e o modo opcional está desligado, a chamada lança ComplianceSidecarUnavailableException. O documento não é verificado; ele nunca é tratado como aprovado.
  • Modo opcional. Construir o gateway com optional: true (os operadores conectam isso a partir da variável de ambiente NEXTPDF_COMPLIANCE_OPTIONAL) rebaixa um sidecar indisponível a um aviso registrado e um retorno null. Os chamadores devem tratar null como “não verificado”. O modo opcional cobre apenas a sondagem de disponibilidade pré-execução; uma falha de transporte durante a própria chamada de validação lança ComplianceSidecarUnavailableException em ambos os modos.
  • Perfil desconhecido. Um perfil sem nenhum validador registrado lança InvalidArgumentException; ele nunca passa silenciosamente.
  • Semântica de aprovação. ExternalValidationResult::passes() exige que conformant seja verdadeiro e zero não conformidades. Cada resultado carrega o perfil, o nome e a versão da ferramenta, a contagem de asserções, os achados, o SHA-256 dos bytes validados, um carimbo de data/hora em UTC e a duração da chamada.
  • A matriz é um registro, não uma afirmação. buildComplianceMatrix() é um redutor estático que produz uma estrutura versionada por esquema com versões de ferramenta e um SHA de commit para rastreabilidade. Ele registra a saída da ferramenta; não afirma nada.
  • Fluxo de dados. O fluxo de bytes completo do PDF é transmitido ao sidecar configurado por meio de um cliente PSR-18. Cada validação é registrada via PSR-3 com perfil, ferramenta, aprovação/reprovação, contagem de asserções e duração.

Roteamento de perfil para ferramenta, conforme retornado por ComplianceProfile::standardReference() e ::toolName():

Casos de perfilReferência de padrãoFerramenta
pdfa-1b, pdfa-2b, pdfa-3b, pdfa-4, pdfa-4fISO 19005-1/-2/-3/-4 (Nível B; Nível F para 4f)veraPDF
pdfua-1, pdfua-2ISO 14289-1:2014, ISO 14289-2:2024veraPDF
pdf20-arlingtonISO 32000-2:2020 (modelo Arlington)veraPDF
pades-b-b, pades-b-t, pades-b-lt, pades-b-ltaETSI EN 319 142-1 B-B até B-LTAEU DSS
zugferd-2.4, factur-x-1.08, en-16931ZUGFeRD 2.4 / Factur-X 1.08 / EN 16931-1:2017Mustang/KoSIT

AiReadyCertifier::certify() avalia três critérios: presença de assinatura estrutural, saúde de LTV e ausência de criptografia. Três critérios aprovados resultam no nível certified; um ou dois resultam em partial; zero resulta em not_certified. Em certified ou partial, ele anexa uma atualização incremental que carrega um fluxo de proveniência XMP e uma sobreposição de Catalog; os bytes originais nunca são mutados. O nível “certified” é um rótulo de prontidão interno do NextPDF, não uma certificação de padrões.

VeraPdfValidator analisa apenas respostas JSON de sidecar (sem XML; livre de XXE por construção). KoSitValidator analisa o relatório XML SVRL do daemon com declarações DOCTYPE rejeitadas e acesso à rede desabilitado, e trata um relatório não analisável como uma falha da chamada.

  • Um timeout do sidecar ou erro de transporte se manifesta como ComplianceSidecarUnavailableException a partir da ponte; o padrão fail-closed se aplica.
  • Uma resposta de sidecar diferente de 200 produz um resultado reprovado com um achado específico da ferramenta (por exemplo VERAPDF-HTTP-ERROR); nunca é uma aprovação de conformidade.
  • Um corpo JSON ou XML de sidecar malformado é uma falha de validação da chamada, não uma aprovação de conformidade.
  • Resultados do EU DSS sem assinaturas falham com DSS-NO-SIGNATURES. Uma indicação diferente de TOTAL_PASSED falha com DSS-SIG-INVALID. Um nível de assinatura abaixo da baseline esperada falha com DSS-LEVEL-MISMATCH.
  • DssValidator publica seu orçamento de timeout por requisição em cada requisição por meio do cabeçalho X-NextPDF-Timeout-Seconds; o cliente PSR-18 do integrador deve honrá-lo para que um sidecar travado não possa bloquear indefinidamente a thread chamadora.
  • ZugferdExternalValidator opcionalmente roteia as chamadas de sidecar por um circuit breaker injetado; um breaker aberto mapeia para ComplianceSidecarUnavailableException (fail-fast, ainda fail-closed). O padrão é um breaker no-op.
  • KoSitValidator::isAvailable() aceita HTTP 200 e 405 da sondagem de saúde do daemon; o daemon responde a GET com 405 enquanto está saudável.
  • O carimbo do AiReadyCertifier falha de forma fail-closed com InvalidArgumentException quando o documento original carece de uma tabela de referências cruzadas clássica (por exemplo, fluxos de referências cruzadas).
  • XRechnungTestSuiteRunner::run() se recusa a executar quando o validador está indisponível ou a suíte não contém arquivos XML; com useCuratedNegativeFallback habilitado, ele substitui por um corpus negativo curado quando a suíte não traz instâncias inválidas.

Este módulo não realiza nenhuma assinatura nem custódia de chaves. A política de algoritmos do modo FIPS é regida pelos módulos Security e Signature. A conformidade de assinatura é delegada ao EU DSS, que faz a sua própria determinação.

O gateway delega o veredito de conformidade a uma ferramenta externa; o design reflete o próprio limite dos padrões: a conformidade é determinada em relação aos requisitos, não afirmada por um produtor.

ComportamentoReferência
Obrigação do processador conforme; conformidade determinada em relação ao padrãoISO 19005-4:2020 §5.2
Requisitos de arquivo PDF/A-4 vs. autoafirmação do produtorISO 19005-4:2020 §6.6.4
A conformidade PDF/UA-2 é uma propriedade do arquivoISO 14289-2:2024 §6
Níveis de assinatura PAdES baselineETSI EN 319 142-1 §5.4.3

A ferramenta externa produz o veredito. O NextPDF não detém nenhuma certificação e não concede nenhuma; dar suporte a um perfil não é estar em conformidade com ele. Os resultados de validação são registros técnicos de verificação de estrutura para referência, não parecer jurídico; consulte sua equipe de conformidade para julgar a suficiência regulatória.

  • O operador hospeda e opera os sidecars, faz o pinning de suas versões, restringe seu alcance de rede, valida seu TLS e controla o ambiente que habilita o modo opcional. Os endpoints dos sidecars são um limite de confiança; os controles de residência e retenção para documentos, resultados e logs são de responsabilidade do operador.
  • A saída de buildComplianceMatrix() é projetada para rastreabilidade de CI: fixe o SHA de commit e arquive a matriz junto aos artefatos de build.
  • O executor da suíte XRechnung espera a suíte de testes oficial extraída para um diretório local; a mensagem de seu construtor nomeia a fonte pública de download.
  • Detalhes de mecanismo interno permanecem na documentação interna do repositório de código-fonte e estão fora do escopo deste manual.

Esta página documenta apenas o comportamento observável externamente e a superfície pública de API suportada. Caminhos de namespace internos, classes auxiliares, tabelas de mecanismo, nomes de arquivos de runbook e prefixos de tíquete estão fora do escopo.