معماری چندکسبوکاری، تجاری و تجارت الکترونیک · فصل ۸ — PWA و Native App Decision · 277
PWA: Install, Offline, Push, Camera Limits
workflow تجاری را به UI یا integration منفرد تقلیل میدهد و state، rights، approval و measurement را یکپارچه نمیکند. موضوع جاری: «PWA: Install, Offline, Push, Camera Limits». میتواند «PWA: Install, Offline, Push, Camera Limits» را برای یک workflow محدود با state/contract/approval و verification مناسب طراحی کند.
خلاصهٔ درس
workflow تجاری را به UI یا integration منفرد تقلیل میدهد و state، rights، approval و measurement را یکپارچه نمیکند. موضوع جاری: «PWA: Install, Offline, Push, Camera Limits».
میتواند «PWA: Install, Offline, Push, Camera Limits» را برای یک workflow محدود با state/contract/approval و verification مناسب طراحی کند.
خروجی این درس
میتواند «PWA: Install, Offline, Push, Camera Limits» را برای یک workflow محدود با state/contract/approval و verification مناسب طراحی کند.
پیشنیازها
اولین سؤال: «PWA-ready» دقیقاً برای کدام capability؟
یک manifest داریم، service worker هم register شده، پس تیم میگوید «PWA آماده است». بعد روی دستگاه واقعی push اجازه نمیگیرد، cache بعد از تغییر schema دادهی قدیمی نشان میدهد، یا camera API وجود دارد ولی permission/device state اجازهی capture نمیدهد. مشکل از اینجا شروع میشود که چند capability مستقل را به یک برچسب تبدیل کردهایم.
در این درس یک PWA Capability & Offline Readiness Matrix v1 میسازیم. install، offline، push و camera چهار قرارداد جدا هستند. برای هرکدام platform، runtime detection، permission/lifecycle، failure state، fallback و evidence را ثبت میکنیم. فقط وقتی evidence کافی است READY میدهیم؛ در غیر این صورت PARTIAL، FALLBACK، UNSUPPORTED یا HOLD را حفظ میکنیم.
مرز این درس
COM-036 مالک اثبات capability و readiness PWA است. این درس تصمیم «آیا native بسازیم؟» را نمیگیرد؛ آن متعلق به COM-037 است. همچنین notification policy و minimal PII متعلق به COM-035 است.
سه مرز سخت:
- وجود API مساوی usable capability نیست.
- وجود manifest یا service worker مساوی readiness کل PWA نیست.
- نتیجهی یک browser/OS را نمیتوان به platform دوم کپی کرد.
مدل ذهنی: Need → Probe → State → Contract → Fallback → Decision
| surface_id | capability_id | platform_family | user_agent_context | secure_context | manifest_present | manifest_scope | install_surface | service_worker_registration | service_worker_state | offline_data_class | cache_strategy | cache_version | network_state | push_api_available | push_permission_state | push_subscription_state | camera_api_available | camera_permission_state | camera_device_state | fallback_path | unsupported_reason | test_fixture | evidence_ref |
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| S1 | ALL | TARGET-A | HOME_SCREEN_APP | TRUE | TRUE | / | AVAILABLE | REGISTERED | ACTIVE | RECENT_ORDERS_READONLY | NETWORK_FIRST_WITH_CACHE | v8 | INTERMITTENT | TRUE | GRANTED | ACTIVE | TRUE | GRANTED | AVAILABLE | DECLARED | NONE | baseline_ready | E-BASE |
| S2 | PUSH | TARGET-A | HOME_SCREEN_APP | TRUE | TRUE | / | AVAILABLE | REGISTERED | ACTIVE | RECENT_ORDERS_READONLY | NETWORK_FIRST_WITH_CACHE | v8 | ONLINE | TRUE | DENIED | NONE | TRUE | GRANTED | AVAILABLE | ACCEPTABLE_INBOX_EMAIL | PERMISSION_DENIED | push_denied_fallback | E-PUSH-DENY |
| S3 | OFFLINE | TARGET-A | HOME_SCREEN_APP | TRUE | TRUE | / | AVAILABLE | REGISTERED | ACTIVE | RECENT_ORDERS_READONLY | CACHE_FIRST | v7 | OFFLINE | TRUE | GRANTED | ACTIVE | TRUE | GRANTED | AVAILABLE | BLOCK_OFFLINE_DATA | STALE_CACHE | stale_cache_schema_change | E-CACHE-STALE |
| S4 | ALL | TARGET-B | HOME_SCREEN_APP | TRUE | FALSE | UNKNOWN | AVAILABLE | REGISTERED | ACTIVE | RECENT_ORDERS_READONLY | NETWORK_FIRST_WITH_CACHE | v8 | INTERMITTENT | TRUE | DENIED | NONE | TRUE | GRANTED | AVAILABLE | ACCEPTABLE_INBOX_EMAIL | PUSH_PERMISSION_DENIED | transfer_platform_b | E-TRANSFER-B |
فلو اصلی:
workflow need → per-capability probe → permission/lifecycle state → offline/cache contract → positive + negative fixture → READY | PARTIAL | FALLBACK | UNSUPPORTED | HOLD
هر capability یک سؤال مستقل دارد: آیا surface نصب/launch موردنیاز وجود دارد؟ آیا offline data واقعاً مجاز و نسخهدار است؟ آیا push permission و subscription فعالاند؟ آیا camera permission و device state واقعاً capture را ممکن میکنند؟
FACT، INFERENCE و DESIGN را جدا نگه دار
FACT — Manifest. W3C manifest یک سند JSON برای metadata اپ وب است و خود spec هم میگوید user agent ممکن است برای استفاده از capabilityها شرایط خودش را داشته باشد. پس manifest_present=true بهتنهایی parity ایجاد نمیکند.
FACT — Service Worker. Service Worker میتواند event بگیرد، fetch را مدیریت کند و به ساخت تجربهی offline کمک کند. اما خودش تضمین نمیکند دادهی business شما با schema جدید، policy retention یا conflict rule درست بماند.
FACT — Push. Push permission و subscription state مستقلاند و subscription میتواند refresh/deactivate شود. PushManager موجود بودن به معنی active subscription نیست.
FACT — Camera. getUserMedia() تحت permission و constraint اجرا میشود. API presence بهتنهایی selected device، permission یا capture موفق را ثابت نمیکند.
INFERENCE. چون این capabilityها مکانیزم و state متفاوت دارند، readiness بهتر است capability-by-capability سنجیده شود.
DESIGN — MAKNOW. stateها، fieldهای matrix، ruleهای fallback و fail-closed این درس طراحی MAKNOW هستند.
قرارداد ۲۴بعدی Readiness Matrix
رکورد کاری ۲۴ field دارد:
surface_id, capability_id, platform_family, user_agent_context, secure_context, manifest_present, manifest_scope, install_surface, service_worker_registration, service_worker_state, offline_data_class, cache_strategy, cache_version, network_state, push_api_available, push_permission_state, push_subscription_state, camera_api_available, camera_permission_state, camera_device_state, fallback_path, unsupported_reason, test_fixture, evidence_ref.
Gate 1 — Surface و platform را قبل از capability بنویس
mobile-web، home-screen-web-app و desktop-browser یک context نیستند. platform_family و user_agent_context باید در evidence دیده شوند.
Gate 2 — Secure context را explicit کن
capabilityهای قدرتمند را در محیط ناامن فرض نکن. اگر prerequisite امنیتی برقرار نیست، نتیجه را با حدس READY نکن.
Gate 3 — Install را از manifest جدا کن
manifest_present، manifest_scope و install_surface سه چیز متفاوتاند. حتی رفتار install/home-screen در user agentها میتواند تغییر کند. evidence باید target platform را توصیف کند، نه یک تعریف بازاری از PWA.
Gate 4 — Offline فقط «cache داریم» نیست
سه سؤال: چه offline_data_class مجاز است؟ چه cache_strategy داریم؟ cache_version با schema/data contract فعلی همراستاست؟ اگر بعد از schema migration نسخهی cache قدیمی است، offline ممکن است خطرناکتر از online failure باشد.
Gate 5 — Service Worker lifecycle را ببین
REGISTERED, INSTALLING, ACTIVATING, ACTIVE, REDUNDANT وضعیت یکسان نیستند. اگر workflow به offline وابسته است، state انتقالی را success کامل اعلام نکن.
Gate 6 — Push = API + Permission + Subscription
سه field را جدا کن. push_api_available=true با push_permission_state=DENIED یا push_subscription_state=NONE هنوز push آماده نیست.
Gate 7 — Camera = API + Permission + Device
camera_api_available=true کافی نیست. permission ممکن است denied باشد یا device مناسب در دسترس نباشد. fallback مثل upload فایل یا manual entry باید از قبل تعریف شود.
Gate 8 — Fallback را business-level بنویس
fallback فقط «یک پیام خطا نشان بده» نیست. باید workflow را حفظ کند: مثلاً push→in-app inbox/email؛ camera→manual code entry؛ offline→read-only snapshot با badge واضح و sync بعد از reconnect.
Gate 9 — Unsupported reason و evidence_ref اجباریاند
اگر capability fail میشود، علت را typed ثبت کن: PERMISSION_DENIED, NO_DEVICE, NO_INSTALL_SURFACE, STALE_CACHE, UNSUPPORTED_API. بدون provenance، debugging تبدیل به حدس میشود.
Gate 10 — READY کوچکترین state است، نه پیشفرض
اگر evidence تعیینکننده UNKNOWN, DISPUTED یا STALE است، HOLD. اگر support transition است، PARTIAL. اگر مسیر اصلی fail ولی fallback قابلقبول است، FALLBACK. اگر capability لازم است و هیچ مسیر قابلقبول نداریم، UNSUPPORTED.
مثالهای حلشده
1. همهی چهار capability با evidence → READY
سطح هدف secure است؛ install surface روی target platform دیده شده؛ service worker ACTIVE است؛ cache version با schema فعلی match است؛ push permission GRANTED و subscription ACTIVE است؛ camera permission و device هر دو حاضرند. نتیجه READY.
2. Push denied، ولی fallback عملیاتی → FALLBACK
Order status باید به کاربر برسد. Push API وجود دارد اما user permission را رد کرده است. چون in-app inbox + email تاییدشده workflow را حفظ میکند، کل surface شکست نمیخورد؛ state این capability FALLBACK است، نه READY و نه دروغ «push works».
3. Cache قدیمی بعد از schema change → HOLD
Service worker active است اما cache_version=v7 در حالی که data contract v8 است. چون correctness دادهی offline اثبات نشده، HOLD تا migration/invalidating policy روشن شود.
4. Camera API حاضر، device نیست → UNSUPPORTED
permission قبلاً granted بوده ولی در kiosk هدف camera device قابل استفاده وجود ندارد و fallback مجاز هم نداریم. capability UNSUPPORTED است.
Failure modeهای متداول
- Manifest theater: فایل manifest را completion badge میدانیم.
- Service-worker magic: فرض میکنیم register شدن SW همهی state را offline-safe میکند.
- Cache forever: schema عوض شده ولی cache version و invalidation policy تغییر نکردهاند.
- Push optimism: API support را با permission/subscription فعال یکی میکنیم.
- Camera optimism:
getUserMediaرا با permission/device/capture موفق یکی میکنیم. - Browser-name detection: بهجای feature/runtime probe فقط اسم browser را میخوانیم.
- Silent fallback: fallback وجود دارد ولی کاربر نمیفهمد داده stale یا notification degraded است.
- Copied verdict: نتیجهی platform A به platform B منتقل میشود.
- Forced green: UNKNOWN/STALE را برای release pressure به READY تبدیل میکنیم.
Alternatives و trade-offها
Network-first برای دادهی حساس به تازگی مناسبتر است اما offline resilience کمتر میشود.
Cache-first برای assetهای immutable عالی است اما برای business data بدون version/expiry میتواند stale-data risk بسازد.
Stale-while-revalidate latency را کم میکند ولی باید UI freshness و data class اجازهی stale read را پشتیبانی کنند.
Push fallback مثل inbox/email continuity میدهد، اما latency و attention semantics متفاوت است؛ آن را «همان push» اعلام نکن.
Camera fallback مثل upload/manual entry availability را بالا میبرد ولی UX و error rate متفاوت است.
اصل تصمیم: strategy را از data class و business requirement انتخاب کن، نه از snippet محبوب.
Experienced bridge: در review چه میپرسی؟
- target surface و platform دقیقاً چیست؟
- کدام capability واقعاً required است؟
- probe در runtime چه چیزی نشان میدهد؟
- permission و lifecycle state چیست؟
- offline data class چیست و stale read مجاز است؟
- cache version چگونه با schema version قفل میشود؟
- fallback دقیقاً کدام business outcome را حفظ میکند؟
- کاربر degraded mode را میبیند یا نه؟
- negative fixture چه failureی را ثابت میکند؟
- چه تغییر platform/browser باعث recheck میشود؟
تمرین هدایتشده و مستقل
Lab آفلاین را اجرا کن:
python -B lab/COM-036-LAB1/learner/run_checks.py
baseline را ببین، سپس mutationها را بررسی کن: push permission را deny کن؛ cache version را عقب بینداز؛ service worker را در ACTIVATING بگذار؛ camera device را حذف کن؛ secure context را false کن؛ و در transfer یک platform جدید بده که install behavior و push state متفاوت دارد.
قانون transfer: verdict قبلی oracle نیست. matrix جدید باید از evidence همان platform ساخته شود.
Verification evidence
Evaluator باید حداقل این خطاها را بگیرد:
READYبا evidenceUNKNOWN/STALE/DISPUTED؛- offline READY با cache version ناسازگار؛
- push READY بدون permission یا subscription؛
- camera READY بدون permission یا device؛
- capability required و unsupported بدون fallback ولی verdict مثبت؛
- install verdict فقط از
manifest_presentبدون install-surface evidence؛ - transfer که baseline verdict را کپی میکند.
Oracle فقط fixture و ruleهای deterministic است؛ نه browser زنده، نه production push، نه hidden model reasoning.
Assessment و transfer
تکلیف نهایی چهار حرکت دارد: مرز COM-036 را توضیح بده؛ matrix baseline را کامل کن؛ mutation stale-cache یا denied-permission را تشخیص بده؛ سپس همان workflow را روی browser/OS دوم از صفر recompute کن.
پاسخ قوی فقط state نهایی را نمیگوید. نشان میدهد کدام field تعیینکننده بود، کدام evidence missing/stale بود، fallback چگونه business outcome را حفظ کرد، و چه چیزی recheck بعدی را trigger میکند.
منابع و freshness
W3C-APPMANIFEST— Web Application Manifest؛ بازبینی 2026-09-14.W3C-SERVICE-WORKERS— Service Workers؛ بازبینی 2026-09-14.W3C-PUSH— Push API؛ بازبینی 2026-09-14.W3C-MEDIA-CAPTURE— Media Capture and Streams؛ بازبینی 2026-09-14.WEBKIT-SAFARI26-WEBAPPS— رفتار Home Screen web app در Safari/iOS 26؛ منبع vendor و فقط برای مثال تفاوت implementation.LOCAL_DESIGN_AUTHORITY— Bible فریزشدهی COM-036 برای stateها و gateها.
این lesson عمداً از support table ثابت بهعنوان truth نهایی استفاده نمیکند. implementation behavior ممکن است تغییر کند؛ claimهای platform-sensitive باید تا 2026-12-31 یا زودتر پس از تغییر مهم browser/OS دوباره بررسی شوند.
ارزیابی
پاسخنامهی این درس در بستهی آموزش وجود ندارد؛ خودت جواب بده و صادقانه علامت بزن. «نیاز به مرور» درس را به صف تکرار میفرستد.
Q1 BOUNDARY
Why does manifest presence not prove whole-PWA readiness?
Q2 DIAGNOSIS
Push API exists, permission is denied, and an approved inbox/email fallback preserves the outcome. What state?
Q3 DIAGNOSIS
Service worker is active but cache version does not match current data schema. What should happen?
Q4 TRANSFER
A second platform exposes install without the first platform’s manifest assumption and has different push permission. What must be recomputed?
ملاکهای ارزیابی (rubric)
- PASS: keeps capability, permission, lifecycle, cache version and fallback separate; preserves non-success states; transfer is recomputed.
- REPAIR: correct final label but missing decisive evidence or fallback rationale.
- FAIL: treats “PWA”, manifest, service-worker registration, or API presence as universal readiness; copies baseline verdict to transfer.
منابع و تازگی
مطالعهٔ موارد (case studies)
فایلهای آزمایشگاه
python -B run_checks.py را اجرا کنید. fixtureها synthetic و deterministic هستند و readiness هر capability، stale cache، permission denial، lifecycle transition، device missing، secure-context failure، fallback و transfer بین platformها را میسنجند.