Przejdź do głównej zawartości

Rozwiązywanie problemów z compat-legacy

Większość problemów z migracją mieści się w niewielkiej liczbie wzorców. Każda pozycja poniżej opisuje objaw, przyczynę i rozwiązanie. Jeśli nie masz pewności co do konkretnej metody, sprawdź /integrations/tcpdf-compat/method-coverage/ oraz miarodajną macierz w repozytorium docs/TCPDF_COVERAGE.md.

Proces wcześniej zatrzymywał się przy błędzie PDF; teraz wyjątek propaguje się na zewnątrz

Dział zatytułowany „Proces wcześniej zatrzymywał się przy błędzie PDF; teraz wyjątek propaguje się na zewnątrz”

Objaw. Kod, który wcześniej zatrzymywał się przy błędzie renderowania, teraz rzuca nieprzechwycony RuntimeException, a żądanie lub zadanie kończy się błędem.

Przyczyna. Wywołania Error() w starszej bibliotece TCPDF wywołują die(). Adapter celowo rzuca zamiast tego RuntimeException, aby błędy były widoczne.

Rozwiązanie. Opakuj punkty wejścia renderowania w blok try/catch i odwzoruj wyjątek na własny kontrakt obsługi błędów. Nie przywracaj zachowania die(). Zobacz /integrations/tcpdf-compat/production-usage/ § Obsługa błędów.

new \TCPDF() nadal odwołuje się do prawdziwej biblioteki TCPDF

Dział zatytułowany „new \TCPDF() nadal odwołuje się do prawdziwej biblioteki TCPDF”

Objaw. Włączono LegacyBootstrap::enableAliases(), ale wynik nadal wygląda jak z starszej biblioteki TCPDF albo zachowanie się nie zmieniło.

Przyczyna. enableAliases() rejestruje alias tylko wtedy, gdy klasa o tej nazwie jeszcze nie istnieje. Jeśli tecnickcom/tcpdf pozostaje dostępny dla autoloadera, a jego klasa \TCPDF ładuje się jako pierwsza, alias zostaje pominięty, a kod nadal używa starszej biblioteki TCPDF.

Rozwiązanie. Podczas migracji używaj jawnych importów w poszczególnych plikach (use NextPDF\Compat\Tcpdf\TCPDF;), aby każde miejsce wywołania było jednoznaczne. Usuń tecnickcom/tcpdf po pomyślnym audycie (zobacz /integrations/tcpdf-compat/migration/ Etap 5). Nie uruchamiaj obu bibliotek z włączonymi aliasami globalnymi w tym samym procesie.

Metoda „działa”, ale przekazany parametr jest ignorowany

Dział zatytułowany „Metoda „działa”, ale przekazany parametr jest ignorowany”

Objaw. Wywołanie kończy się powodzeniem i tworzy plik w formacie Portable Document Format (PDF), ale przekazana opcja (odnośnik obrazu, wyrównanie, liczba punktów na cal (DPI), kolor zakładki, …) nie ma żadnego efektu.

Przyczyna. Metoda należy do grupy metod po cichu ignorujących parametry. Przyjmuje parametr dla zgodności na poziomie kodu źródłowego, a następnie go odrzuca. To udokumentowane zachowanie, a nie błąd; zobacz /integrations/tcpdf-compat/method-coverage/ §2.

Rozwiązanie. Uruchom audyt w trybie ścisłym, aby znaleźć każde takie wywołanie:

examples/troubleshoot-strict.php
<?php
declare(strict_types=1);
require __DIR__ . '/vendor/autoload.php';
use NextPDF\Compat\Tcpdf\Exception\TcpdfNotImplementedException;
use NextPDF\Compat\Tcpdf\TCPDF;
$pdf = new TCPDF();
$pdf->setStrictMode(true);
$pdf->AddPage();
$pdf->SetFont('helvetica', '', 12);
try {
$pdf->Image('logo.png', 10, 10, 50, 0, '', 'https://example.com');
} catch (TcpdfNotImplementedException $e) {
// Message lists every ignored parameter and a migration hint.
echo $e->getMessage(), "\n";
}

Następnie usuń parametr albo odwzoruj jego intencję w nowoczesnym interfejsie API ($pdf->getDocument()), jak pokazano w /integrations/tcpdf-compat/migration/ Etap 4.

Objaw. Kod, który rozgałęzia się na podstawie wartości zwracanej przez MultiCell() (na przykład w celu obliczenia wykorzystanej wysokości lub liczby wierszy), działa nieprawidłowo.

Przyczyna. Metoda MultiCell() w adapterze zwraca zastępczą wartość zgodności 1, a nie wyrenderowaną liczbę komórek ani liczbę wierszy. Podobnie Write() zwraca 0.

Rozwiązanie. Nie rozgałęziaj kodu na podstawie tych wartości zwracanych. Jeśli potrzebna jest wyrenderowana wysokość, oblicz ją na podstawie getStringHeight() / getNumLines() albo przenieś tę logikę do nowoczesnego interfejsu API.

Objaw. Zażądano starszej wersji formatu PDF; wynikiem nadal jest PDF 2.0.

Przyczyna. Adapter zawsze generuje PDF 2.0 (ISO 32000-2). setPDFVersion() należy do grupy metod, które nie mają tu zastosowania; adapter zgłasza powiadomienie i kontynuuje działanie.

Rozwiązanie. Usuń to wywołanie. Jeśli dalszy konsument w przepływie wymaga starszej wersji formatu PDF, obsłuż ten wymóg osobno; adapter nie potrafi obniżyć wersji docelowej.

setSignature() nic nie zrobiło — plik PDF nie jest podpisany

Dział zatytułowany „setSignature() nic nie zrobiło — plik PDF nie jest podpisany”

Objaw. Wywołano setSignature() z certyfikatem; wynikowy plik PDF nie zawiera podpisu.

Przyczyna. Silnik podstawowy nie implementuje setSignature() przez ten adapter. W trybie domyślnym jest to brak operacji; w trybie ścisłym zgłaszany jest wyjątek.

Rozwiązanie. Podpisywanie wymaga komercyjnej edycji NextPDF oraz nowoczesnego interfejsu API podpisu. Zobacz /integrations/tcpdf-compat/security-and-operations/ § Podpisy cyfrowe. Nie należy oczekiwać, że starsze wywołanie setSignature() cokolwiek podpisze.

Output() uszkodziło odpowiedź HTTP lub wynik procesu roboczego

Dział zatytułowany „Output() uszkodziło odpowiedź HTTP lub wynik procesu roboczego”

Objaw. Bajty PDF pojawiają się w odpowiedzi protokołu Hypertext Transfer Protocol (HTTP) albo trafiają do dziennika procesu roboczego.

Przyczyna. Użyto miejsca docelowego wyniku, które zapisuje na wyjście (I/D), mimo że odpowiedzią sterujesz samodzielnie. Adapter nie wypisuje danych do bufora w sposób, w jaki robi to starsza biblioteka TCPDF, jednak I/D nadal sterują wynikiem silnika.

Rozwiązanie. W procesach roboczych i obsługach, którymi sterujesz, użyj Output($path, 'F'), aby zapisać plik, lub Output($name, 'S'), aby uzyskać bajty i samodzielnie je wyemitować. tests/Unit/Compat/Tcpdf/Bridge/OutputBridgeTest.php potwierdza, że odwzorowanie miejsca docelowego ignoruje wielkość liter i białe znaki na krańcach:

KodZwracaEfekt uboczny
Sbajty PDF (%PDF…)brak
Fpusty ciągzapisuje plik
Etreść MIME w base64brak
FI / FDpusty ciągzapisuje plik, a następnie wynik silnika
I / D / nieznanepusty ciągwynik silnika (wbudowany/pobranie)

Asercje dokładnych bajtów pliku PDF zawodzą po przełączeniu

Dział zatytułowany „Asercje dokładnych bajtów pliku PDF zawodzą po przełączeniu”

Objaw. Testy migawkowe porównujące surowe bajty PDF zawodzą wszędzie.

Przyczyna. Silnik korzysta z niezależnej implementacji PDF 2.0. Delegowane metody dają zgodny wynik widoczny dla użytkownika, ale bajty się różnią. Jest to oczekiwane.

Rozwiązanie. Ustal na nowo punkt odniesienia testów tak, aby sprawdzały wyrenderowaną treść (wyodrębniony tekst), strukturę (liczba stron, rozmiar strony) lub kontrolę wstępną (str_starts_with($bytes, '%PDF')). Zobacz /integrations/tcpdf-compat/migration/ Etap 4.

Starsza stała K_* / PDF_* ma nieprawidłową wartość

Dział zatytułowany „Starsza stała K_* / PDF_* ma nieprawidłową wartość”

Objaw. Niestandardowa ścieżka lub wartość domyślna ustawiona za pomocą stałej nie odnosi skutku.

Przyczyna. Adapter automatycznie definiuje stałą tylko wtedy, gdy nie jest ona jeszcze zdefiniowana, i robi to podczas tworzenia pierwszej instancji. Jeśli define() wykona się po skonstruowaniu pierwszego adaptera, domyślna wartość adaptera już obowiązuje.

Rozwiązanie. Zdefiniuj każdą niestandardową stałą K_* / PDF_* w kodzie rozruchowym, przed utworzeniem jakiejkolwiek instancji adaptera. Zobacz /integrations/tcpdf-compat/configuration/ § Kolejność rozwiązywania konfiguracji.

Objaw. Konstrukcja zawodzi lub zachowanie zmienia się nieoczekiwanie po aktualizacji zależności.

Przyczyna. Adapter wymaga nextpdf/core ^3.0. Wersja silnika podstawowego rozwiązana poza tym zakresem nie jest obsługiwana.

Rozwiązanie. Uruchom composer show nextpdf/core i przypnij silnik do ^3.0. Zobacz /integrations/tcpdf-compat/install/ § Zweryfikuj wersję silnika.

PytanieGdzie szukać
Co metoda X właściwie tutaj robi?/integrations/tcpdf-compat/method-coverage/, docs/TCPDF_COVERAGE.md
Które wywołania tracą parametry?Audyt w trybie ścisłym (ta strona; /integrations/tcpdf-compat/migration/)
Dlaczego proces nie zatrzymał się przy błędzie?/integrations/tcpdf-compat/security-and-operations/ § Zachowania utwardzone
Dlaczego wynik nie jest podpisany / nie jest w formacie PDF/A?/integrations/tcpdf-compat/security-and-operations/
Jak obsłużyć konflikt aliasu z jawnym importem?Ta strona; /integrations/tcpdf-compat/boot-and-discovery/
  • /integrations/tcpdf-compat/migration/ — migracja etapowa, która zapobiega większości powyższych problemów
  • /integrations/tcpdf-compat/method-coverage/ — opis zachowania poszczególnych metod
  • /integrations/tcpdf-compat/boot-and-discovery/ — rejestracja aliasów i unikanie konfliktów
  • docs/TCPDF_COVERAGE.md — miarodajna macierz pokrycia