← Back to demo

📐 Architecture & Pipeline Diagrams

Iter 7 current state · 2026-05-28 · Rendered with Mermaid.js

1. System Architecture (Production)

Cloudflare edge + serverless GPU + Shopify storefront. Green = Foxetales side, orange = Vendor (em build), blue = 3rd party.

🟢 Foxetales 🟠 Vendor (Paul/Weaverse build) 🔵 3rd party
graph TB subgraph Foxetales["🟢 Foxetales (Customer-facing)"] ST[Shopify Storefront
foxetales.com] ADMIN[Foxetales Admin
order management] end subgraph Vendor["🟠 Vendor — Paul/Weaverse"] WORKER[Cloudflare Worker
/api/generate-page
/api/preview] QUEUE[Cloudflare Queue
job orchestration] R2[(Cloudflare R2
customer photos
rendered pages)] KV[(Workers KV
job status
session state)] end subgraph GPU["🟠 GPU Worker"] RUNPOD[RunPod Serverless
A100 80GB
FLUX+PuLID+LoRA] end subgraph ThirdParty["🔵 3rd party"] STRIPE[Stripe
payments] SENTRY[Sentry
error tracking] PRINT[Print fulfillment
vendor TBD] end CUST([👤 Customer]) -->|upload photo| ST ST -->|POST /preview| WORKER WORKER -->|enqueue| QUEUE WORKER -->|store| R2 QUEUE -->|invoke| RUNPOD RUNPOD -->|read assets| R2 RUNPOD -->|write result| R2 RUNPOD -->|update status| KV WORKER -->|poll status| KV WORKER -->|return URL| ST ST -->|preview shown| CUST CUST -->|checkout| STRIPE STRIPE -->|webhook| WORKER WORKER -->|trigger full book| QUEUE WORKER -->|order fulfilled| PRINT PRINT -->|ship| CUST WORKER -.->|errors| SENTRY ADMIN -->|regen / approve| WORKER classDef fox fill:#d3f9d8,stroke:#2f9e44,stroke-width:2px classDef vendor fill:#ffe8cc,stroke:#e8590c,stroke-width:2px classDef gpu fill:#fff3bf,stroke:#f59f00,stroke-width:2px classDef third fill:#e7f5ff,stroke:#1971c2,stroke-width:2px class ST,ADMIN fox class WORKER,QUEUE,R2,KV vendor class RUNPOD gpu class STRIPE,SENTRY,PRINT third

2. End-to-End Sequence (Customer Journey)

Từ lúc customer upload đến khi nhận sách in: chia 2 giai đoạn — preview (immediate ~20s) và full book gen (background ~10 min) sau khi thanh toán.

sequenceDiagram actor C as Customer participant SF as Shopify Storefront participant W as CF Worker API participant Q as CF Queue participant GPU as RunPod GPU participant R2 as R2 Storage participant S as Stripe participant P as Print Vendor Note over C,SF: Phase 1 — Preview (live, ~20s) C->>SF: Upload kid photo SF->>W: POST /preview {photo, book_id} W->>R2: Store photo W->>Q: Enqueue preview job (3 pages) Q->>GPU: Run pipeline × 3 GPU->>R2: Read template assets GPU->>R2: Write 3 preview pages GPU-->>W: Job done (status callback) W-->>SF: Preview URLs SF-->>C: Show 3 personalized pages Note over C,P: Phase 2 — Order fulfillment (background, ~10 min) C->>SF: Approve preview, checkout SF->>S: Process payment S-->>W: Webhook: order paid W->>Q: Enqueue full book (35 pages) Q->>GPU: Render all 35 pages GPU->>R2: Write all pages GPU-->>W: All done W->>P: Send book PDF + ship address P-->>C: Ship printed book (5-7 days)

3. AI Pipeline Detail (Iter 7 — Per Page)

Bước-by-bước xử lý 1 page cho 1 customer. Đây là pipeline đã validated trong iter 7, khác đáng kể với planning ban đầu (không còn ControlNet, có thêm skin shift postproc).

flowchart TB INPUT_PHOTO[📷 Customer Photo
kid face JPG/PNG] INPUT_TPL[🎨 Template Assets
background.png
character.png
person_mask.png] INPUT_PROMPT[📝 Ethnicity prompt
vd: 'Vietnamese Asian'] PULID[🎭 PuLID Identity Extraction
InsightFace + EVA-CLIP
→ identity embedding] MASK[🎯 Mask Prep
GrowMask +2
FeatherMask 12px] COND[🧠 Conditioning
CLIP-L + T5-xxl
+ ethnicity prompt
+ skin anchor] KS[⚡ FLUX KSampler
FLUX.1-dev 23GB
+ Foxetales LoRA v4 0.7
+ PuLID inject
denoise 0.55, steps 25] VAE[🔄 VAE Decode
latent → RGB 1024×1024] COMPOSITE[🖼️ Composite
blend char + background
via feathered person mask] DECISION{Black/dark
ethnicity?} SKIN[🌓 Skin Shift Postproc
YCbCr detection × person mask
RGB multiply per preset] OUTPUT[📤 Final Page
1024×1024 PNG ~1MB] INPUT_PHOTO --> PULID INPUT_TPL --> MASK INPUT_PROMPT --> COND PULID --> KS MASK --> KS COND --> KS INPUT_TPL --> KS KS --> VAE VAE --> COMPOSITE INPUT_TPL --> COMPOSITE COMPOSITE --> DECISION DECISION -->|yes| SKIN DECISION -->|no, Asian/Blonde| OUTPUT SKIN --> OUTPUT classDef input fill:#e7f5ff,stroke:#1971c2 classDef process fill:#fff3bf,stroke:#f59f00 classDef output fill:#d3f9d8,stroke:#2f9e44 classDef decision fill:#ffe8cc,stroke:#e8590c class INPUT_PHOTO,INPUT_TPL,INPUT_PROMPT input class PULID,MASK,COND,KS,VAE,COMPOSITE,SKIN process class OUTPUT output class DECISION decision

4. Tech Stack Layers

Component breakdown theo layer: UI → API → Orchestration → AI → Storage → External services. Layer thấp phục vụ layer cao hơn.

graph LR subgraph UI["UI Layer"] SHOPIFY[Shopify Theme
Hydrogen/Weaverse] DEMO[Demo page
Next.js] end subgraph API["API Layer (CF Workers)"] REST[REST endpoints] WS[WebSocket status] AUTH[Auth/JWT] end subgraph ORCH["Orchestration"] Q[CF Queue] SCHED[Cron triggers] end subgraph AI["AI Layer (RunPod)"] CFY[ComfyUI runtime] FLUX[FLUX.1-dev] PUL[PuLID-Flux] LORA[FoxeTales LoRA v4] POST[skin_shift.py] end subgraph DATA["Storage"] R2D[R2 — files] KVD[KV — state] D1[D1 — orders] end subgraph EXT["External"] STR[Stripe] PRT[Print vendor] MON[Sentry/PostHog] end UI --> API API --> ORCH ORCH --> AI AI --> DATA API --> DATA API --> EXT AI --> POST

5. Data Flow (Storage View)

Lifecycle của 1 file từ upload đến delivery.

flowchart LR UP[Customer upload
~5MB JPG] -->|store| RA[(R2: photos/
customer_id/
original.jpg)] RA -->|read| GPU1[GPU: PuLID extract] GPU1 -->|cache| KV1[(KV: pulid_emb/
customer_id
TTL 24h)] KV1 -->|reuse| GPU2[GPU: render N pages] GPU2 -->|store result| RB[(R2: pages/
order_id/
page_NN.png
~1MB each)] RB -->|read for PDF| PDF[PDF assembler] PDF -->|store| RC[(R2: books/
order_id/
full_book.pdf)] RC -->|download URL| PRT[Print vendor] RB -->|preview URL| ST[Shopify storefront]

6. Iter Evolution (How we got here)

timeline title FoxeTales AI Pipeline — Iter History section Phase 1 — Style training Iter 1-3 (2026-04) : Foxetales style LoRA v1-v3 : ~75 watercolor match Iter 4 (2026-05-15) : LoRA v4 (1000 steps) : 93 watercolor match : PRODUCTION section Phase 1 — Face swap Iter 5 (2026-05-20) : PuLID-Flux integration : zero-shot identity transfer Iter 6 (2026-05-25) : Face mask workflow : Halo + style fixed section Phase 1 — Polish Iter 7a (2026-05-26) : Polish tuning : Halo 68→82, Style 63→78 Iter 7b (2026-05-27) : Chi feedback : Full-character mask Iter 7c (2026-05-28) : Skin shift postproc : Black ethnicity workaround section Phase 2 — Production Phase 2 : ControlNet pose preservation : LoRA v5 diverse skin retrain : Worker API + demo storefront : RunPod serverless deploy