365 lines
5.9 KiB
Markdown
365 lines
5.9 KiB
Markdown
# Task P.7 - Document Assembly Framework
|
|
|
|
## Objective
|
|
|
|
Build a generic Document Assembly Framework that can merge generated CRM PDFs with static PDF documents from the Document Library.
|
|
|
|
Primary use case:
|
|
|
|
```text
|
|
Quotation PDF
|
|
+ SLA PDF
|
|
+ Warranty PDF
|
|
+ Datasheet PDF
|
|
= Final Customer PDF
|
|
```
|
|
|
|
This task must be generic and reusable for future document types.
|
|
|
|
---
|
|
|
|
# Prerequisites
|
|
|
|
Completed:
|
|
|
|
* P.4 PDF Runtime
|
|
* P.5 Document Template Management
|
|
* P.5.1 Production Hardening
|
|
* P.6 Document Library Foundation
|
|
* P.6.1 Document Sequence Scope Refactor
|
|
|
|
---
|
|
|
|
# Scope
|
|
|
|
Included:
|
|
|
|
* Generic assembly engine
|
|
* PDF merge using pdfme manipulator or approved merge library
|
|
* Assembly policy model
|
|
* Document source resolution
|
|
* Document ordering
|
|
* Storage of final assembled artifact
|
|
* Quotation integration
|
|
* Audit and regression checks
|
|
|
|
Excluded:
|
|
|
|
* Render Configuration UI
|
|
* User-selectable append options
|
|
* Template Designer
|
|
* New PDF template design
|
|
* Editing SLA/Warranty contents
|
|
|
|
---
|
|
|
|
# Core Concept
|
|
|
|
The framework must not be hardcoded to Quotation only.
|
|
|
|
Design around:
|
|
|
|
```text
|
|
Input Documents
|
|
↓
|
|
Assembly Policy
|
|
↓
|
|
Assembly Engine
|
|
↓
|
|
Merged PDF
|
|
↓
|
|
Final Artifact
|
|
```
|
|
|
|
---
|
|
|
|
# Supported Input Sources
|
|
|
|
The assembly engine must support these sources:
|
|
|
|
## 1. Generated Document
|
|
|
|
Example:
|
|
|
|
* Quotation PDF generated from PDF Runtime
|
|
|
|
## 2. Document Library PDF
|
|
|
|
Example:
|
|
|
|
* SLA
|
|
* Warranty
|
|
* Company Profile
|
|
* Datasheet
|
|
* Drawing
|
|
* Certificate
|
|
|
|
## 3. Future External Attachment
|
|
|
|
Reserved for later phases.
|
|
|
|
---
|
|
|
|
# Assembly Policy
|
|
|
|
Create an assembly policy model.
|
|
|
|
Example:
|
|
|
|
```ts
|
|
interface AssemblyPolicy {
|
|
documentType: string;
|
|
organizationId: string;
|
|
productType?: string;
|
|
brand?: string;
|
|
language?: string;
|
|
sources: AssemblySourcePolicy[];
|
|
}
|
|
```
|
|
|
|
```ts
|
|
interface AssemblySourcePolicy {
|
|
sourceType: 'generated' | 'document_library';
|
|
role: 'main' | 'sla' | 'warranty' | 'datasheet' | 'drawing' | 'appendix';
|
|
required: boolean;
|
|
order: number;
|
|
libraryCode?: string;
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
# Default Quotation Assembly
|
|
|
|
Initial quotation policy:
|
|
|
|
```text
|
|
1. Generated Quotation PDF
|
|
2. SLA PDF
|
|
3. Warranty PDF
|
|
4. Datasheet / Drawing if configured
|
|
```
|
|
|
|
Do not make append documents user-selectable yet.
|
|
|
|
Use default policy only.
|
|
|
|
---
|
|
|
|
# Document Resolution
|
|
|
|
The engine must resolve Document Library versions by:
|
|
|
|
* organization
|
|
* brand
|
|
* product type
|
|
* language
|
|
* document type
|
|
* active version
|
|
|
|
Resolution must be deterministic.
|
|
|
|
If multiple candidates exist, apply clear priority rules.
|
|
|
|
---
|
|
|
|
# Missing Document Behavior
|
|
|
|
If a required append document is missing:
|
|
|
|
* assembly must fail with a business-readable error
|
|
|
|
If an optional append document is missing:
|
|
|
|
* skip and record warning
|
|
|
|
---
|
|
|
|
# PDF Merge
|
|
|
|
Use pdfme manipulator merge capability or an approved server-side PDF merge utility.
|
|
|
|
Requirements:
|
|
|
|
* preserve page order
|
|
* preserve all pages
|
|
* support multiple input PDFs
|
|
* return final merged PDF bytes
|
|
* avoid mutating source PDFs
|
|
|
|
---
|
|
|
|
# Final Artifact
|
|
|
|
Store the assembled PDF as a new artifact.
|
|
|
|
Metadata should include:
|
|
|
|
* id
|
|
* organizationId
|
|
* sourceDocumentType
|
|
* sourceDocumentId
|
|
* sourceDocumentCode
|
|
* assemblyPolicy
|
|
* sourceArtifacts
|
|
* finalFileName
|
|
* storageKey
|
|
* checksum
|
|
* fileSize
|
|
* pageCount
|
|
* generatedAt
|
|
* generatedBy
|
|
|
|
Do not overwrite approved quotation PDF artifact.
|
|
|
|
The assembled artifact is a separate output.
|
|
|
|
---
|
|
|
|
# Quotation Integration
|
|
|
|
Add quotation-level service support:
|
|
|
|
```text
|
|
generate quotation PDF
|
|
↓
|
|
resolve assembly policy
|
|
↓
|
|
resolve append documents
|
|
↓
|
|
merge
|
|
↓
|
|
persist final assembled artifact
|
|
↓
|
|
return preview/download
|
|
```
|
|
|
|
Recommended API endpoints:
|
|
|
|
```text
|
|
GET /api/crm/quotations/[id]/assembled-pdf
|
|
POST /api/crm/quotations/[id]/assembled-pdf/generate
|
|
GET /api/crm/quotations/[id]/assembled-pdf/download
|
|
```
|
|
|
|
---
|
|
|
|
# Storage
|
|
|
|
Reuse existing storage abstraction.
|
|
|
|
Do not store merged PDF binary in database.
|
|
|
|
Store:
|
|
|
|
* storage key
|
|
* checksum
|
|
* file size
|
|
* page count
|
|
* metadata
|
|
|
|
---
|
|
|
|
# Audit Logging
|
|
|
|
Record audit logs for:
|
|
|
|
* assembly started
|
|
* source document resolved
|
|
* source document missing
|
|
* merge completed
|
|
* artifact stored
|
|
* assembly failed
|
|
* assembled artifact downloaded
|
|
|
|
---
|
|
|
|
# Validation
|
|
|
|
Validate before merge:
|
|
|
|
* generated main PDF exists
|
|
* append PDF exists
|
|
* file is PDF
|
|
* file can be read
|
|
* page count can be determined
|
|
* source order is valid
|
|
* required source documents exist
|
|
|
|
---
|
|
|
|
# Testing Requirements
|
|
|
|
Add tests for:
|
|
|
|
* generated-only assembly
|
|
* quotation + SLA
|
|
* quotation + SLA + Warranty
|
|
* optional missing document
|
|
* required missing document
|
|
* invalid source PDF
|
|
* page order
|
|
* page count
|
|
* checksum generation
|
|
* artifact persistence metadata
|
|
|
|
Run:
|
|
|
|
```bash
|
|
npm run typecheck
|
|
npm run build
|
|
npm run audit:pdf
|
|
```
|
|
|
|
---
|
|
|
|
# Regression Requirements
|
|
|
|
Verify:
|
|
|
|
* legacy quotation PDF still works
|
|
* approved quotation PDF still works
|
|
* Document Library preview/download still works
|
|
* product template PDF still works
|
|
* assembled PDF does not replace source PDF
|
|
* assembled PDF artifact is stored separately
|
|
|
|
---
|
|
|
|
# Acceptance Criteria
|
|
|
|
* Generic assembly engine exists.
|
|
* Engine supports generated PDF + Document Library PDFs.
|
|
* Quotation can generate assembled PDF.
|
|
* SLA can be appended after quotation.
|
|
* Document order is deterministic.
|
|
* Missing required documents fail clearly.
|
|
* Missing optional documents warn and continue.
|
|
* Final merged artifact is stored through storage abstraction.
|
|
* Source PDFs are not mutated.
|
|
* Existing PDF runtime remains unchanged.
|
|
* System is ready for future Render Configuration.
|
|
|
|
---
|
|
|
|
# Out of Scope
|
|
|
|
## P.8
|
|
|
|
* User-selectable append documents
|
|
* Optional section UI
|
|
* Per-customer render preferences
|
|
* Per-quotation assembly choices
|
|
|
|
## P.9
|
|
|
|
* Template Designer
|
|
* Visual PDF editor
|
|
* Upload/import template designer
|
|
|
|
---
|
|
|
|
# Final Success Condition
|
|
|
|
Task P.7 is complete when ALLA OS can generate a final assembled quotation PDF by merging the generated quotation PDF with active Document Library PDFs such as SLA or Warranty, store the merged result as a separate artifact, and keep all existing PDF runtime behavior unchanged.
|