ข้ามไปยังเนื้อหา

คู่มือสำหรับนักพัฒนา Laravel

แพ็กเกจ Laravel ทำให้ NextPDF สอดคล้องกับแนวทางปฏิบัติของ Laravel โดยไม่เปลี่ยนวงจรชีวิตของเอกสารในแกนหลัก คอนเทนเนอร์เป็นผู้ดูแลรีจิสทรีและแฟกทอรีที่ใช้ร่วมกัน เอกสาร PDF แต่ละชุดเป็นแบบใช้ครั้งเดียวแล้วทิ้ง ดังนั้นควรสร้าง ส่งคืน สตรีม หรือบันทึกเพียงครั้งเดียว

ใช้คู่มือนี้เมื่อออกแบบบริการของแอปพลิเคชัน งานคิว ขั้นตอนการตอบสนอง หรือความครอบคลุมของการทดสอบสำหรับ nextpdf/laravel

เลเยอร์เป็นเจ้าของโดยความรับผิดชอบไม่ควรใส่ที่นี่
Controllerแอปพลิเคชันตรวจสิทธิ์คำขอ เลือกตัวสร้างเอกสาร และส่งคืนการตอบสนองกฎเค้าโครง PDF ที่ใช้ร่วมกันข้ามหลายกรณีการใช้งาน
บริการของแอปพลิเคชันแอปพลิเคชันรวบรวมข้อมูลโดเมนและเรียกโค้ดสร้างเอกสารตรรกะการบูตคอนเทนเนอร์หรือการกำหนดค่าแพ็กเกจ
ตัวสร้างเอกสารแอปพลิเคชันแปลงข้อมูลโดเมนเป็นการเรียกใช้เอกสารของ NextPDFออบเจ็กต์คำขอ ตรรกะการสืบค้นของ Eloquent หรือรายละเอียดการขนส่งคิว
การผสานรวมกับ Laravelnextpdf/laravelผูกแฟกทอรี รีจิสทรี ตัวลงนาม ไคลเอนต์ TSA facade การตอบสนอง และงานคิวเส้นทางที่เก็บข้อมูลเฉพาะธุรกิจหรือนโยบายผู้เช่า
เอนจินแกนหลักnextpdf/nextpdfสร้าง PDF และทำให้เป็นอนุกรมนโยบายการตอบสนอง คิว หรือระบบไฟล์ของ Laravel
ขั้นตอนพฤติกรรมการดำเนินการของนักพัฒนา
การลงทะเบียน Service providerNextPdfServiceProvider::register() ลงทะเบียนรีจิสทรีที่ใช้ร่วมกัน แฟกทอรีเอกสาร การผูกเอกสาร ไคลเอนต์ HTTP ไคลเอนต์ผู้ออกการประทับเวลา (TSA) ตัวลงนาม และสัญญา e-invoice แบบเลือกใช้ได้เผยแพร่และตรวจสอบ config/nextpdf.php ก่อนนำขึ้นใช้งานจริง
การกำหนดเอกสารfacade Pdf และการผูก PdfDocumentInterface กำหนดเอกสารใหม่ผ่าน DocumentFactoryInterfaceกำหนดเอกสารหนึ่งครั้งต่อหนึ่งคำขอ คำสั่ง หรืองานคิว
การเขียนเอกสารโค้ดของแอปพลิเคชันเรียก API เอกสารในแกนหลักผ่าน facade หรือเอกสารที่ฉีดเข้ามาเก็บการดึงข้อมูลโดเมนไว้นอกตัวสร้างเอกสาร
เอาต์พุตปลายทางPdfResponse ส่งเอาต์พุต HTTP หรือบันทึกเอกสารลงดิสก์เลือกเส้นทางเอาต์พุตปลายทางเพียงเส้นทางเดียวต่อเอกสารหนึ่งชุด
การประมวลผลในคิวGeneratePdfJob สร้างเอกสารใหม่ใน worker และตรวจสอบเส้นทางเอาต์พุตซ้ำส่งบริบทแบบสเกลาร์และทำให้คอลแบ็กเป็น idempotent
เส้นทางวัตถุประสงค์
app/Pdf/Builders/*ตัวสร้างเอกสารแบบบริสุทธิ์ รับข้อมูลและส่งคืนเอกสารที่สมบูรณ์แล้ว
app/Pdf/Data/*ออบเจ็กต์ถ่ายโอนข้อมูล (DTO) ขนาดเล็กที่ส่งต่ออินพุตเอกสารซึ่งผ่านการอนุญาตแล้ว
app/Services/*การประสานงานของแอปพลิเคชัน การสืบค้น การส่งต่อการตรวจสิทธิ์ และการเลือกเส้นทางที่เก็บข้อมูล
app/Jobs/*ตัวห่อหุ้มแบบเลือกใช้ได้รอบ GeneratePdfJob เมื่อแอปพลิเคชันต้องการงานที่มีชื่อเฉพาะ
tests/Feature/Pdf/*การทดสอบการตอบสนอง HTTP การส่งงานเข้าคิว และการอนุญาต
tests/Unit/Pdf/*การทดสอบตัวสร้างด้วยอินพุตขนาดเล็กที่ให้ผลลัพธ์แน่นอน

รักษาตัวสร้างให้เป็นอิสระจากออบเจ็กต์คำขอของ Laravel ควรเรียกใช้ตัวสร้างจาก controller คำสั่ง การทดสอบ หรือ queue worker ด้วยอินพุตเดียวกันได้

<?php
namespace App\Pdf\Builders;
use App\Pdf\Data\InvoicePdfData;
use NextPDF\Contracts\PdfDocumentInterface;
final readonly class InvoicePdfBuilder
{
public function build(PdfDocumentInterface $pdf, InvoicePdfData $data): PdfDocumentInterface
{
$pdf->setTitle($data->title)
->addPage()
->setFont('dejavusans', '', 12)
->writeHtml($data->html);
return $pdf;
}
}

ใช้การฉีดผ่านคอนสตรักเตอร์เมื่อขั้นตอน PDF เป็นส่วนหนึ่งของตรรกะแอปพลิเคชัน ใช้ facade เฉพาะในขั้นตอน controller แบบสั้นซึ่งรูปแบบสแตติกอ่านง่ายกว่า

<?php
namespace App\Http\Controllers;
use App\Pdf\Builders\InvoicePdfBuilder;
use App\Pdf\Data\InvoicePdfData;
use NextPDF\Contracts\PdfDocumentInterface;
use NextPDF\Laravel\Http\PdfResponse;
final readonly class DownloadInvoiceController
{
public function __invoke(
PdfDocumentInterface $pdf,
InvoicePdfBuilder $builder,
) {
$document = $builder->build(
$pdf,
InvoicePdfData::fromInvoiceId(1234),
);
return PdfResponse::download($document, 'invoice-1234.pdf');
}
}

ตัวช่วยการตอบสนองจะสร้างไบต์เอกสารจริงก่อนสร้างการตอบสนองของ Laravel ตัวช่วยเหล่านี้เป็นตัวช่วยด้านการตอบสนอง ไม่ใช่ตัวเรนเดอร์เบื้องหลัง

GeneratePdfJob รับ callable ของตัวสร้างและเส้นทางเอาต์พุต งานนี้ตรวจสอบเส้นทางที่ไม่ปลอดภัยระหว่างการประมวลผล โค้ดของแอปพลิเคชันยังควรเลือกรากที่เก็บข้อมูลที่ปลอดภัยสำหรับผู้เช่าก่อนส่งงาน

<?php
use App\Pdf\Builders\QueuedInvoiceBuilder;
use NextPDF\Laravel\Jobs\GeneratePdfJob;
GeneratePdfJob::dispatch(
outputPath: storage_path('app/pdfs/invoice-1234.pdf'),
builder: [QueuedInvoiceBuilder::class, 'build'],
)->onQueue(config('nextpdf.queue.queue', 'pdf'));

ทำให้คอลแบ็กของคิวมีขนาดเล็ก ควรเขียนสถานะถาวรจาก job listener ของแอปพลิเคชันแทนการเก็บ closure ที่ซับซ้อนไว้ใน payload ของคิว

จุดต่อขยายใช้สำหรับข้อจำกัด
PdfDocumentInterface การผูกแทนที่หรือตกแต่งการสร้างเอกสารสำหรับค่าเริ่มต้นระดับแอปพลิเคชันต้องส่งคืนอินสแตนซ์เอกสารใหม่
DocumentFactoryInterfaceสร้างเอกสารใหม่อย่างชัดเจนในบริการและการทดสอบอย่าแคชเอกสารที่ส่งคืน
config/nextpdf.phpค่าเริ่มต้น การตั้งค่าคิว การตั้งค่าตัวเรนเดอร์ Chrome ฮุกการลงนาม TSA แคช OCSPปฏิบัติต่อตัวแปรสภาพแวดล้อมเป็นการกำหนดค่าการปรับใช้ ไม่ใช่อินพุตของคำขอ
GeneratePdfJob ตัวสร้างสร้างเอกสารแบบอะซิงโครนัสcallable ต้องทำให้เป็นอนุกรมได้ผ่านการขนส่งคิวของ Laravel
คอลแบ็กสำเร็จ/ล้มเหลวการแจ้งเตือนหรือการล้างข้อมูลหลังการสร้างทำให้คอลแบ็กเป็น idempotent และคำนึงถึงผลข้างเคียง
สัญญา Premium แบบเลือกใช้ได้ตัวฝัง ตัวตรวจสอบ โปรไฟล์ e-invoice และตัวรัน Schematronกำหนดเฉพาะเมื่อมีการติดตั้งและได้รับสิทธิ์ใช้งานแพ็กเกจแบบเลือกใช้ได้แล้วเท่านั้น
  1. สร้างเอกสารฉบับแรกแบบซิงโครนัสใน controller หรือการทดสอบฟีเจอร์
  2. ย้ายโค้ดเค้าโครงไปไว้ในคลาสตัวสร้างภายใต้ app/Pdf/Builders
  3. ย้ายตรรกะการสืบค้นและการอนุญาตไปไว้ในบริการของแอปพลิเคชัน
  4. เพิ่มการทดสอบ PdfResponse สำหรับส่วนหัวและชื่อไฟล์
  5. ย้ายการสร้างที่ช้าหรือมีปริมาณสูงไปยัง GeneratePdfJob
  6. เพิ่มการทดสอบคิวสำหรับบริบทที่ทำเป็นอนุกรม นโยบายเส้นทางเอาต์พุต และการจัดการความล้มเหลว
  7. วัดหน่วยความจำและเวลาเรนเดอร์ด้วยข้อมูลที่เป็นตัวแทนของการใช้งานจริง
ความล้มเหลวควรจัดการที่ใดการตอบสนองที่แนะนำ
คำขอที่ไม่ถูกต้องหรือเอกสารที่ไม่ได้รับอนุญาตController หรือนโยบายส่งคืนการตอบสนองด้านการอนุญาตหรือการตรวจสอบความถูกต้องตามปกติของแอปพลิเคชัน
ฟอนต์ที่หายไปหรือรูปภาพที่ไม่ถูกต้องการทดสอบตัวสร้างและการบันทึกล็อกของแอปพลิเคชันให้คำขอหรืองานล้มเหลว อย่าส่งออก PDF ที่ไม่สมบูรณ์
เส้นทางเอาต์พุตที่ไม่ปลอดภัยบริการที่เก็บข้อมูลของแอปพลิเคชันและ GeneratePdfJobปฏิเสธก่อนส่งงานและใช้การตรวจสอบฝั่ง worker เป็นการป้องกันเชิงลึก
ความล้มเหลวของการลงนามหรือ TSAขอบเขตของบริการการลงนามพิจารณาว่าเอกสารสามารถไม่มีลายเซ็นได้หรือไม่ ค่าเริ่มต้นคือ fail closed สำหรับเอกสารที่อยู่ภายใต้การกำกับดูแล
คิวหมดเวลาการกำหนดค่าและการสังเกตการณ์ของ queue workerลองใหม่เฉพาะเมื่อตัวสร้างให้ผลแน่นอนและเส้นทางเอาต์พุตเขียนทับได้อย่างปลอดภัย
ประเด็นที่เกี่ยวข้องค่าเริ่มต้นเมื่อใดควรแทนที่
ชื่อคิวpdfใช้คิวเฉพาะเมื่อการสร้างแย่งทรัพยากรจากงานที่ผู้ใช้กำลังรอ
งานหมดเวลา120 วินาทีเพิ่มเฉพาะหลังจากวัดขนาดเอกสารและความสามารถของ worker แล้ว
ชื่อไฟล์ของการตอบสนองdocument.pdfใช้ตัวระบุทางธุรกิจที่ผ่านการทำความสะอาดแล้ว
รีจิสทรีฟอนต์ใช้ร่วมกันและถูกล็อกหลังการอุ่นเครื่องเพิ่ม preload_fonts สำหรับฟอนต์ที่ใช้ในเส้นทางที่ถูกเรียกใช้บ่อย
รีจิสทรีรูปภาพแคชแบบมีขอบเขตที่ใช้ร่วมกันลด image_cache_mb สำหรับ worker ที่มีหน่วยความจำจำกัด
การแบ่งส่วนของการตอบสนองแบบสตรีมส่วนขนาด 64 KBอย่าพึ่งพาขอบเขตของส่วนข้อมูล เพราะเป็นรายละเอียดของเอาต์พุต
  • การทดสอบ controller ยืนยัน Content-Type Content-Disposition และส่วนหัวเชิงป้องกัน
  • การทดสอบตัวสร้างใช้ DTO ที่ให้ผลลัพธ์แน่นอนและไม่สืบค้นฐานข้อมูล
  • การทดสอบคิวยืนยันว่าตัวสร้างได้รับเอกสารใหม่
  • การทดสอบเส้นทางครอบคลุมการเดินผ่านไดเรกทอรี stream-wrapper null-byte และการปฏิเสธไฟล์ที่ไม่ใช่ .pdf
  • การทดสอบ worker เรนเดอร์เอกสารที่เป็นตัวแทนภายใต้ขีดจำกัดหน่วยความจำเดียวกับการใช้งานจริง
  • การทดสอบการลงนามแบบเลือกใช้ได้ครอบคลุมใบรับรองที่หายไป รหัสผ่านที่ไม่ถูกต้อง TSA ที่ไม่พร้อมใช้งาน และระดับลายเซ็นที่กำหนดค่าไว้