Salta ai contenuti

Support: utilità trasversali + Clock + Sleeper

Il modulo Support raccoglie le utilità trasversali usate internamente dal motore. Espone inoltre una piccola superficie pubblica: il clock di sistema PSR-20, la pipeline di raccolta degli avvisi e le primitive di serializzazione PDF. La maggior parte del namespace è costituita da infrastruttura interna. Questa pagina documenta le parti su cui i chiamanti esterni possono fare affidamento e indica quelle riservate all’uso interno.

Terminal window
composer require nextpdf/core:^3

Clock (PSR-20). SystemClock implementa Psr\Clock\ClockInterface. Il metodo now() restituisce l’ora corrente come DateTimeImmutable. Il modello PSR-20 definisce un’interfaccia di clock con un’unica operazione di lettura. Tale operazione restituisce l’ora corrente come valore data-ora immutabile (PSR-20 psr_20_clock#2.1). SystemClock è l’implementazione predefinita. Il motore la utilizza quando non viene iniettato alcun clock. Per ottenere un’ora fissa nei test, iniettare invece un clock congelato, che deve implementare la stessa interfaccia. Abbinare il clock a Config::deterministic per un output identico a livello di byte.

Pipeline degli avvisi. WarningCollector è il canale principale in memoria per i problemi di rendering non fatali. Il motore aggiunge un Warning per ogni degradazione deterministica. Esempi tipici sono una colonna di tabella compressa, un font non risolto o un glifo mancante. Il chiamante li legge dopo la generazione tramite Document::getWarnings(). Un Warning è un value object immutabile. Contiene un WarningCode, una WarningSeverity (warning o degraded), la pagina, il tipo di elemento, l’id della funzionalità, un flag di parità degradata, un messaggio, un DegradationImpact e un id di capability opzionale. WarningCode è un enum con backing string e identificatori stabili. Gli identificatori hanno il prefisso NEXTPDF_W_ (ad esempio NEXTPDF_W_FONT_UNRESOLVED). Il prefisso consente corrispondenze sicure nei test. addWithPolicy() applica la DegradationPolicy attiva. Con una policy strict, un impatto di conformità, semantico o bloccante genera DegradedException. Con una policy balanced, solo un impatto bloccante genera un’eccezione. Una policy permissive non genera mai eccezioni.

Primitive PDF. PdfStringEscaper è l’unica fonte di verità per l’escaping di stringhe e nomi PDF. escapeLiteral() applica l’escaping ai caratteri richiesti da una stringa letterale PDF (reverse solidus, parentesi, CR, LF, HT, BS, FF) e rimuove NUL. escapeName() codifica in esadecimale, per un name object, i byte esterni all’ASCII stampabile e al set di delimitatori PDF. BinaryBuffer è un accumulatore binario ottimizzato per la scrittura. Costruisce oggetti e flussi PDF. La modalità di streaming riversa i dati su un handle php://temp per i documenti di grandi dimensioni. Supporta inoltre le operazioni su intervalli di byte necessarie per incorporare la firma. PdfOperators contiene le stringhe di formato degli operatori del content stream (path, testo, stato grafico, font). I livelli di disegno e parsing le condividono.

BinaryBuffer, PdfOperators e gran parte del resto di NextPDF\Support\ sono infrastruttura interna. Sono utilizzati dai livelli writer e di disegno. Sono documentati qui per completezza e a fini di audit. Non fanno parte della superficie pubblica supportata dell’API. Fare invece affidamento sulla façade Document e sul namespace Contracts. SystemClock, WarningCollector, Warning, WarningCode, WarningSeverity e DegradationImpact sono i membri della superficie pubblica.

SimboloTipoVisibilitàMembri principali
NextPDF\Support\SystemClockfinal classpublicnow(): DateTimeImmutable (PSR-20 ClockInterface)
NextPDF\Support\WarningCollectorfinal classpublicadd(), emit(), addWithPolicy(), getWarnings(), hasWarnings(), hasDegradedParity(), clear()
NextPDF\Support\Warningfinal readonly classpublic$code, $severity, $page, $elementType, $featureId, $degradedParity, $message, $impact, $capabilityId
NextPDF\Support\WarningCodestring enumpublicidentificatori NEXTPDF_W_* stabili
NextPDF\Support\WarningSeveritystring enumpublicWarning, Degraded
NextPDF\Support\DegradationImpactstring enumpublicCosmetic, LayoutRisk, SemanticLoss, ComplianceRisk, Blocking
NextPDF\Support\PdfStringEscaperfinal readonly classinternalescapeLiteral(), escapeName() (statici)
NextPDF\Support\BinaryBufferfinal classinternalwrite(), writeStream(), replaceAt(), extract(), enableStreaming(), getContents()
NextPDF\Support\PdfOperatorsfinal classinternalcostanti di stringa di formato per gli operatori del content stream

Leggere gli avvisi raccolti dopo la generazione.

<?php
declare(strict_types=1);
use NextPDF\Support\WarningCollector;
$collector = new WarningCollector();
// The engine appends warnings during rendering. After generation:
if ($collector->hasWarnings()) {
foreach ($collector->getWarnings() as $warning) {
\printf(
"[%s] page %d: %s\n",
$warning->code->value,
$warning->page,
$warning->message,
);
}
}

Iniettare un clock per ottenere un’ora deterministica e trattare un avviso di parità degradata come un errore di build.

<?php
declare(strict_types=1);
use NextPDF\Support\SystemClock;
use NextPDF\Support\WarningCollector;
use Psr\Clock\ClockInterface;
// Production uses the real system clock.
$clock = new SystemClock();
$now = $clock->now(); // DateTimeImmutable
$epoch = $now->getTimestamp(); // int
// In tests, swap in any ClockInterface that returns a fixed instant
// (the parameter is typed to the PSR-20 interface, not SystemClock).
function buildReport(ClockInterface $clock): \DateTimeImmutable
{
return $clock->now();
}
$collector = new WarningCollector();
// ... run generation ...
if ($collector->hasDegradedParity()) {
throw new \RuntimeException('Output parity degraded; failing the build.');
}
  • SystemClock::now() restituisce un nuovo DateTimeImmutable a ogni chiamata. Non presumere che due chiamate restituiscano lo stesso istante. Per un’ora fissa, iniettare un clock congelato.
  • WarningCollector è in memoria e per istanza. È il canale principale. Il sidecar JSON e lo STDERR della CLI vengono emessi al confine dell’output, non dal collector stesso.
  • addWithPolicy() può generare DegradedException durante il rendering quando è attiva una policy strict. Catturarla al confine della generazione se si desidera un output parziale.
  • WarningCode ha valori costituiti da stringhe stabili: verificare la corrispondenza sul case dell’enum, non sul testo del messaggio, che è leggibile dall’utente e può cambiare.
  • BinaryBuffer::getLength() è un alias intenzionale di getOffset() per mantenere la parità con l’interfaccia stream. Entrambi restituiscono lo stesso numero di byte.
  • Considerare PdfStringEscaper, BinaryBuffer e PdfOperators come interni. Non sono coperti dalla promessa di stabilità dell’API pubblica.

SystemClock::now() equivale alla costruzione di un singolo oggetto, O(1). Le aggiunte a WarningCollector sono push su lista con costo O(1) ammortizzato. getWarnings() restituisce la lista sottostante. BinaryBuffer in modalità di streaming limita la memoria alla soglia maxmemory (predefinita 2 MB) prima di riversare i dati su disco, mantenendo costante il picco di memoria per i documenti di grandi dimensioni. Il performance_budget predefinito per questa pagina di riferimento è wall_ms: 1500, peak_mb: 64.

La superficie del clock consente, iniettando un clock fisso insieme a Config::deterministic, di rimuovere il non determinismo dell’orologio di sistema dall’output firmato e con marca temporale. PdfStringEscaper è l’unico escaper verificabile per l’output di stringhe e nomi PDF. Instradare ogni emissione di stringhe attraverso di esso previene l’iniezione di contenuto tramite parentesi o delimitatori non sottoposti a escaping nel testo fornito dall’utente. Gli avvisi possono contenere dettagli derivati dal documento (tipi di elemento, id delle funzionalità). Ripulire l’output degli avvisi prima di inoltrarlo a un sink di log a bassa attendibilità.

SpecificaClausolaArgomento
PSR-20 (PHP-FIG)psr_20_clock#2.1L’operazione di lettura del clock restituisce una data-ora immutabile
ISO 32000-2:2020§7.3.4.2 / §7.3.5Escaping di stringhe letterali e name object (parafrasato; testo ISO non citato, nessun chunk fissato)

SystemClock implementa ClockInterface di PSR-20. L’escaper segue le regole sui caratteri PDF per le stringhe letterali e i name object. Il testo ISO è parafrasato secondo la policy di citazione del sito e non viene fissato alcun chunk letterale.

  • /modules/core/exception/DegradedException generata da addWithPolicy()
  • /modules/core/contracts/DegradationPolicy, Capability
  • /modules/core/observability/ — inoltro degli avvisi e metriche
  • /modules/core/config/Config::deterministic si abbina al clock
  • /modules/core/writer/ — consumatore interno di BinaryBuffer e PdfOperators

Glossario: PSR-20 · degradation policy · value object