SRS: UC_5.1 — Flow 3A: Live Onboarding Initiation
| Field | Value |
|---|---|
| BA in Charge | linh.nguyen34 |
| Date Created | 2026-08-08 |
| Version | v2.2 |
| Last Updated | 2026-08-24 — Profit_Target_Pct changed from hardcoded 14% to dynamic SIM_target_percent read from Zapier Table C. Formula, parameter table, and example updated. |
| Document References | Zapier Integration V7.pdf (§Flow 3A: Live Onboarding Initiation, §Flow 2: Challenge Monitor) · RFQ_ Stack Trading Prop Tech V7.pdf (§2.2 MT5 Infrastructure, §Process Veriff Handoff) · RFQ_ Website and Dashboard Implementation V7.pdf (§Passing Associate Track modal) · Figma: Stack Trading Designs — Shared File 2 (node-id=1-25967) |
<a id="UC_5.1"></a>
UC_5.1 — Flow 3A: Live Onboarding Initiation
1. Overview
| Field | Content |
|---|---|
| ID | UC_5.1 |
| Use Case | Flow 3A — Live Onboarding Initiation |
| Description | When a trader passes the Simulation Challenge (Passed_Challenge), the system locks and flattens the SIM account, then routes by onboarding history: Branch A — New Trader (identity_status != 'Approved' OR dots_payee_id IS NULL OR contract_status != 'Signed'): generates a Veriff KYC link, dispatches the "Action Required: Complete Live Onboarding" email, resets compliance fields to 'Pending', and displays the full hard-lockout overlay. Dots payout setup link generated in Flow 3B after Veriff APPROVED. Branch B — Returnee Trader after Hard Breach (identity_status == 'Approved' AND dots_payee_id IS NOT NULL AND contract_status == 'Signed'): skips Flows 3B, 3C, 3D entirely. Middleware auto-sets payout_status = 'Approved' and resets setup_status = 'Pending'. Trader is routed directly to Flow 3F (Market Data Selection) — dashboard enters Phase 2 forced screen (market data must be repurchased). Flow 3H provisions a new Live account from the Ironbeam/Forex pre-provisioned pool at the level of the SIM just passed. (Source: STAGE3-055/H-07 — second-cycle Dots bypass; extended to full Flow 3A branch gate 2026-08-18) |
| Zapier Flow | Flow 3A (Live Onboarding Initiation) — triggered by Flow 2 on Passed_Challenge status |
| Zapier Table | — |
| 3rd Party | Veriff (POST /v1/sessions — KYC hosted page for ALL traders, both Futures and Forex) · Ironbeam (receives outbound compliance package via SFTP or Secure Shared Drive, end-of-day batch — confirmed M-02 2026-08-15) |
Wireframe: Figma — Stack Trading Designs Shared File 2, node-id 1-25967
Open in Figma
Screenshot provided by BA (2026-08-09): Dashboard in "Pending_Compliance" failed visual state — dark overlay, desaturated background, frosted glass effect visible. Modal not captured in this screenshot (modal appears on top of this background state). See §10 for full component inventory.
2. Trigger
Flow 3A fires when Flow 2.2 (Challenge Monitor — Pass Check) emits a PROFIT_TARGET_HIT state-change webhook to Zapier, indicating the trader's SIM equity has met or exceeded Profit_Target.
Architecture note (STAGE2-006 confirmed 2026-07-20): Flow 2 does NOT trigger on
Trade_Closed. Node.js middleware monitors SIM account balances server-side in real time. Zapier is only invoked when middleware emits binary state-change webhooks:PROFIT_TARGET_HIT(→ Flow 3A) orCHALLENGE_FAILED(→ Flow 7B).
Profit_Target formula:
Profit_Target_PnL = Starting_Capital × SIM_target_percent
Target_Equity_Trigger = Starting_Capital + Profit_Target_PnL| Parameter | Value | Source |
|---|---|---|
Starting_Capital | Account notional at the trader's evaluation level — e.g. $25,000 (Level 1), $50,000 (Level 2), $150,000 (Level 5) | Zapier Integration V7.pdf Table A (Forex), Table B (Futures) |
Profit_Target_Pct | SIM_target_percent (read from Zapier Table C) — applies to all SIM evaluation packages (Associate / Accelerated / Advanced) and all level-up scenarios within the SIM environment. Current configured value: 14%. Configurable via Table C; not hardcoded. Live environment has separate fixed profit target values per notional tier in Table A/B. | Client confirmed 2026-08-24 (Table C — SIM_target_percent) |
Example — $25,000 package (at current Table C value of 14%):
Profit_Target_PnL = $25,000 × SIM_target_percent (14%) = $3,500
Target_Equity_Trigger = $25,000 + $3,500 = $28,500Pass recorded when Net_Equity >= $28,500.
Pass condition check (Flow 2.2 — middleware):
IF Net_Equity >= Target_Equity_Trigger:
Action 1: Disable SIM account (POST /disable-sim-account — Lock Profit)
Action 2: UPDATE Users SET account_status = 'Passed_Challenge'
Action 3: Trigger Flow 3A (emit PROFIT_TARGET_HIT webhook to Zapier)
Action 4: POST /community/trigger-review-invite (delay_hours=0) — Trustpilot, concurrentPOST /community/trigger-review-invite — Middleware logic:
When called with delay_hours=0, Middleware executes the following steps sequentially:
- Delay scheduling: Schedules an internal task at
call_time + delay_hours. Withdelay_hours=0, the task executes immediately. - Suppression check: At task execution time, query the Users table. HALT if either condition is true:
trustpilot_reviewed_at < 15 days ago(trader reviewed within the last 15 days), ORtrustpilot_invited_at < 30 days ago(trader received an invite within the last 30 days).
- API dispatch: If suppression check passes, call Trustpilot Invitation API with
user_idasreferenceId. Trustpilot mapsreferenceIdto the trader's registered email and delivers the invitation directly. - State update:
UPDATE Users SET trustpilot_invited_at = NOW(). - Audit log: Write execution record to
BPS_Audit_Log.
Payload received by Flow 3A:
| Field | Type | Source |
|---|---|---|
user_id | UUID | Users table |
Asset_Class | Enum ('Futures', 'Forex') | Users table |
Billing_Country | String (ISO 3166-1 alpha-2) | Users table |
(Source: Zapier Integration V7.pdf §Flow 2: Challenge Monitor, §Flow 3A; STAGE2-006 confirmed 2026-07-20; MKT-26 confirmed 2026-07-24)
3. Pre-conditions
| ID | Condition |
|---|---|
| P-1 | account_status = 'Passed_Challenge' — trader has met Profit_Target and the SIM account is locked/flattened |
| P-2 | Asset_Class is set to 'Futures' or 'Forex' in the Users table |
| P-3 | Billing_Country is populated in the Users table |
| P-4 | Veriff API is reachable (Branch A — New Trader only) |
| P-5 | Branch gate: Middleware queries dots_payee_id, identity_status, contract_status from Users table before executing any compliance steps — result determines Branch A or Branch B. |
4. Post-conditions
Branch A — New Trader:
identity_status = 'Pending'institution_approval_status = 'Pending'payout_status = 'Pending'- "Action Required: Complete Live Onboarding" email dispatched (SES template:
Live_Onboarding_Compliance_Initiation) - Dashboard displays Phase 1 "Pending Compliance" hard-lockout overlay (computed state — not a DB write)
Branch B — Returnee Trader:
payout_status = 'Approved'— set directly by Middleware (no Veriff / Dots / Rippling re-processing — STAGE3-055/H-07)setup_status = 'Pending'— reset to force market data repurchase at Flow 3Fidentity_status,institution_approval_status,contract_statusremain'Approved'/'Signed'— NOT reset- No Veriff session created; no KYC email dispatched
- Dashboard enters Phase 2 (Market Data Setup) forced screen — trader must re-select and re-pay for market data
Note:
account_statusis NOT updated at Flow 3A. It is only updated at Flow 3H to'Active_L[N]_DMA'after full provisioning.'Pending_Compliance'is a frontend computed state, not a DB column value. (Source: STAGE3-010 — confirmed 2026-08-09)
Futures path additionally:
REMOVED (STAGE3-037 [CHR-46]) — Futures traders now use Veriff same as Forex.kyc_link= Ironbeam White Label Portal URLkyc_link= Veriffverification_urlfor all traders.- After Veriff APPROVED: backend bundles Veriff payload + PII documents + assigned Ironbeam sub-account number and transmits outbound to Ironbeam compliance team. Delivery method: SFTP or Secure Shared Drive, end-of-day batch (confirmed M-02 2026-08-15).
Forex path additionally:
kyc_link= Veriffverification_url(fromPOST /v1/sessions)
(Source: Zapier Integration V7.pdf §Flow 3A State Management; RFQ_ Website and Dashboard Implementation V7.pdf §Passing Associate Track modal)
5. Basic Flow
- Receive trigger payload. Zapier receives the internal webhook from Flow 2 with
user_id,Asset_Class,Billing_Country.
Step 0 — Returnee branch gate (runs before any compliance writes).
- Query Users table:
SELECT dots_payee_id, identity_status, contract_status FROM Users WHERE user_id = payload.user_id - IF
identity_status = 'Approved'ANDdots_payee_id IS NOT NULLANDcontract_status = 'Signed': → Branch B (Returnee Trader). Skip Steps 2–5. Proceed to Step 0B. - ELSE (any condition not met): → Branch A (New Trader). Continue from Step 2.
Step 0B — Returnee path: auto-approve payout, reset market data, route to Flow 3F. (Branch B only)
UPDATE Users
SET payout_status = 'Approved',
setup_status = 'Pending'
WHERE user_id = payload.user_id- Middleware fires internal webhook to trigger Flow 3F (Market Data Selection).
- Dashboard enters Phase 2 forced Market Data Setup screen (trader must re-select and pay for market data — same forced-navigation as post-Flow 3E).
- Flow 3H: After trader completes Market Data selection (Flow 3F/3G), Flow 3H provisions a new Live account (MT5/Rithmic) from the Ironbeam/Forex pre-provisioned pool at the level of the SIM just passed, and sets
account_status = 'Active_L[N]_DMA'. - HALT — Steps 2–5 do NOT execute. (Source: STAGE3-055/H-07 second-cycle Dots bypass — extended to full Flow 3A branch gate; setup_status reset confirmed 2026-08-18)
-
Update compliance status fields —
Pending_Complianceoverlay trigger. (Branch A only)UPDATE Users SET identity_status = 'Pending', institution_approval_status = 'Pending', payout_status = 'Pending' WHERE user_id = payload.user_idaccount_statusis NOT changed here.'Pending_Compliance'is a frontend computed state: Dashboard renders the Pending Compliance overlay whenidentity_status = 'Pending' OR institution_approval_status = 'Pending' OR payout_status = 'Pending'. It is not stored in theaccount_statuscolumn. (Source: STAGE3-010 — confirmed 2026-08-09)
🔄 CR — STAGE3-037 [CHR-46]: Universal Veriff replaces Ironbeam WLP branch. Ironbeam Compliance Handoff (outbound bundle) added.
-
Generate KYC link (Universal Veriff — all traders).
- All traders (Futures and Forex): Call Veriff API
POST /v1/sessions→ receiveverification_url. Setkyc_link = verification_url. DELETED (STAGE3-037 [CHR-46] 2026-08-12) — Ironbeam waived manual KYC applications for all traders. Universal Veriff flow replaces the Ironbeam WLP branch. Flow 3B.2 (UC_5.3) is also deleted (see STAGE3-039 [CHR-46]).IF Asset_Class == 'Futures': Setkyc_link = Ironbeam White Label Portal URL- Ironbeam Compliance Handoff (NEW — Futures only, post-Veriff): After Veriff APPROVED webhook (handled in Flow 3B/UC_5.2), backend must bundle the approved Veriff JSON payload, all supporting PII documents, the trader's
legal_nameandaddress, and the newly assigned Ironbeam sub-account number from the predefined bulk pool. Backend transmits this package directly to Ironbeam's compliance team via SFTP or Secure Shared Drive, end-of-day batch (confirmed M-02 2026-08-15). (Source: STAGE3-037 confirmed 2026-08-12)
- All traders (Futures and Forex): Call Veriff API
-
Send "Action Required: Complete Live Onboarding" email (SES template:
Live_Onboarding_Compliance_Initiation).- Recipient: trader's registered email address.
- Email contains:
kyc_link(Veriff hosted verification page URL) only. - Payout setup link: NOT included in this email. The personalized Dots payout setup flow link (
flow_link) is generated in Flow 3B (Process Veriff Handoff, UC_5.2) after Veriff APPROVED, and dispatched in a second email. - Note: Template key renamed from
Live_Onboarding_Level_1toLive_Onboarding_Compliance_Initiationto avoid collision withLive_Onboarding_Credentialsemail at Flow 3H (STAGE3-060 confirmed 2026-08-15). (Source: Zapier Integration V7.pdf §Flow 3A Compliance Initiation; STAGE3-050 / STAGE3-060; confirmed 2026-08-15)
-
Write compliance state to Users table.
UPDATE Users SET identity_status = 'Pending', institution_approval_status = 'Pending', payout_status = 'Pending' WHERE user_id = payload.user_id(Source: Zapier Integration V7.pdf §Flow 3A State Management; STAGE3-010 confirmed 2026-08-09)
-
Dashboard renders "Live Onboarding In Progress" hard lockout overlay. (STAGE3-048 2026-08-12)
- Trigger (computed state): Frontend evaluates
identity_status = 'Pending' OR institution_approval_status = 'Pending' OR payout_status = 'Pending'. This is NOT driven byaccount_statusDB column —'Pending_Compliance'is a frontend computed state only. - Overlay copy (confirmed from screenshot 2026-08-13):
- Headline:
Live Onboarding In Progress - Subtitle:
Congratulations on passing the Associate Track. To provision your live account, you must complete Identity Verification, Payout Setup, and sign your Trader Agreement. - Info box:
Please check your email. We have sent you secure links to complete these required steps. This dashboard will unlock once your live account is fully provisioned.
- Headline:
- Progress steps (dynamic — reflect DB state in real time):
- ○ Identity Verification →
identity_status - ○ Payout Setup →
payout_status - ○ Trader Agreement →
contract_status - Each circle transitions from empty (Pending) to filled/checked when its field reaches
'Approved'/'Signed'. institution_approval_statusis NOT shown as a separate circle — set simultaneously withidentity_statusper STAGE3-037 [CHR-46].
- ○ Identity Verification →
- "Back to Website" button: Only interactive exit. Routes to
www.stacktrading.com. - No close button. Overlay is a hard lockout — cannot be dismissed. Sidebar and Settings disabled. See BR_5.1.8.
- Hide condition: Overlay dismissed when
account_status = 'Active_L[N]_DMA'(Flow 3H write-back). (Source: STAGE3-048 confirmed 2026-08-12; screenshot confirmed 2026-08-13)
- Trigger (computed state): Frontend evaluates
-
Terminate Zap. Flow 3A ends. Downstream flows (3B,
3B.2(deprecated — STAGE3-039 [CHR-46]), 3C, 3D–3H) are triggered independently by their own events.
6. Alternative Flows
Alt-1 — Trader closes the modal and navigates the dashboard.
- Updated (STAGE3-048 2026-08-12): Trader cannot freely navigate. As long as
identity_status,payout_status, andinstitution_approval_statusare all'Pending'(Flows 3A–3E not yet complete), the trader is hard-locked to the "Live Onboarding In Progress" screen. Sidebar navigation and the standard Settings menu remain DISABLED. - The "Back to Website" button routes the trader OUT of the application to the public marketing site (www.stacktrading.com).
- The trader can re-read the email and act on the KYC link at any time, but cannot access other dashboard screens until onboarding is complete.
- Flow 3F transition: Once Flow 3E completes (contract signed —
contract_status = 'Signed'), the next login recognizes the DB state change and forces the trader to the native Market Data selection screen (Flow 3F). See UC_5.5. (Source: STAGE3-048 confirmed 2026-08-12)
Alt-2 — Trader loses or doesn't receive the KYC/Onboarding email.
- Trader contacts Operations.
- Step 1 — Check AWS SES: Dev checks SES console for Bounce, Spam/Complaint, or Suppression List entry for the trader's email address.
- Step 2 — BPS Manual Veriff Reset (Flow 3.1): BPS admin calls
POST /api/bps/kyc/reset(or equivalent admin UI).- Middleware clears
veriff_failed_flagand resetsveriff_attempts = 0in PostgreSQL RDS. - Middleware fires
VERIFF_MANUAL_RESETwebhook to Zapier Flow 3.1. - Zapier Flow 3.1 calls Veriff API to generate a new verification session link.
- AWS SES sends a new email:
"Action Required: Your ID Verification has been reset..."containing the new KYC link. - Slack alert pushed to Ops channel:
"⚠️ Veriff session manually reset for Trader [ID]".
- Middleware clears
- Step 3 — Freshdesk escalation (via Flow 38): If Trader complained via Discord (#the-pit / #verify), Discord Bot (Flow 38) auto-detects, removes public message, and creates a High Priority Freshdesk ticket under the trader's email. If L1 support cannot resolve →
POST /user_id/ticket_id(Escalate to L2) auto-tagsL2_EscalationandCompliance_Review.(Source: CR-20260720-004 — Freshdesk replaces Zendesk across all ticketing including Flow 38)
- Step 4 — Break-Glass (Veriff system outage): If Veriff API is unavailable system-wide, Ops activates "Manual KYC Exception Handling" from Ops Console. Admin bypasses KYC status via internal Middleware endpoints with mandatory Reason Code + evidence attachment. All overrides are permanently logged to the audit table for NFA/CFTC inspection.
Note:
POST /resend-welcome(Flow 41) is NOT used here. Flow 41 is for Stage 1 Welcome/Sim email resend only (re-sendsWelcome_Sim_Challengewith a newcredentials_claimed_at-gated token). Using Flow 41 for a Stage 3 KYC email is incorrect.
(Source: QnA STAGE3-001, STAGE3-006 — confirmed 2026-07-20; Ops runbook clarification 2026-08-09)
Alt-3 — Returnee Trader (Branch B): passes SIM after Hard Breach with prior KYC/Dots/ICA complete.
- Flow 2 emits
PROFIT_TARGET_HITa second (or later) time for the sameuser_id. - Step 0 gate detects:
identity_status = 'Approved'ANDdots_payee_id IS NOT NULLANDcontract_status = 'Signed'. - Branch B executes:
payout_statusset to'Approved'directly — no Dots API call.setup_statusreset to'Pending'— trader must re-purchase market data.- Flows 3B (Veriff), 3C (Dots webhook), 3D (ICA routing) are NOT triggered — entirely skipped.
- Flow 3E (ICA webhook) is NOT triggered —
contract_statusalready'Signed'. - Internal webhook fires → Flow 3F (Market Data Selection) triggered directly.
- Dashboard enters Phase 2 forced Market Data Setup screen.
- Flow 3H: provisions new Live account from pre-provisioned Ironbeam/Forex pool at the level of the SIM just passed (Level N =
Current_Levelat time ofPassed_Challenge). - Flow 3A terminates. No KYC email sent.
7. Exceptional Flows
Exc-1 — Veriff API non-200 (Forex path, Step 3).
- Veriff
POST /v1/sessionsreturns a non-200 or times out. - Retry: 3 attempts over 15 minutes via Redis BullMQ queue on Core Compute (30s → 5min → 15min).
- Rollback: Do NOT write
identity_status = 'Pending'. Trader state remainsPassed_Challengein DB. Cancel SES email dispatch. - Alerting: Log to
bps_audit_logs. Fire Severity-2 Slack alert to #ops-compliance. After 3 failed retries: auto-create Freshdesk ticket (tags:Compliance_Hold,Technical_Fault). (Source: STAGE3-012 — confirmed 2026-08-09; CR-20260720-004 — Freshdesk replaces Zendesk)
Exc-2 — Email dispatch failure (Step 4).
- AWS SES fails to send the "Action Required: Complete Live Onboarding" email.
- Retry: 5 automatic retries per AWS SES retry policy (or Middleware queue).
- Rollback: Do NOT rollback
identity_statusorpayout_status— the KYC link was already generated successfully and is saved in DB. Rollback would break the onboarding cycle. - Alerting: Log SES failure to CloudWatch. Alert #ops-support via Slack. Ops can use BPS Reset/Resend API (
POST /api/bps/kyc/reset) to resend the existing KYC link without regenerating a new Veriff session. (Source: STAGE3-012 — confirmed 2026-08-09)
Exc-3 — Users table write failure (Step 5).
UPDATE Users SET identity_status / institution_approval_status / payout_statusfails (DB connection error).- Retry: 3 immediate retries at connection pool level. If connection failure persists, task is frozen in memory queue.
- Rollback: Abort entire transaction — do NOT call Veriff API, do NOT dispatch SES email. Return HTTP 500 to client.
- Alerting: Severity-1 Slack alert to #dev-alerts. Trigger AWS CloudWatch Alarm (DB CPU/connection timeout) → SMS/PagerDuty to DevOps team. (Source: STAGE3-012 — confirmed 2026-08-09)
Exc-4 — Double-trigger (Flow 3A fires twice for same user_id).
- Cause: Flow 2 webhook fires twice due to a race condition (e.g., two
Trade_Closedevents near the profit target), or network retries replaying the same event. - Retry: 0 — rejected immediately at the webhook entry point.
- Idempotency Guard (3 layers):
- Middleware queries
provider_event_idbefore any processing. If already exists → HALT, return HTTP 200 No-Op. - State Machine Guard: if any of
{identity_status, payout_status, institution_approval_status}is already'Pending'or'Approved'→ Block; no Veriff call; no email re-send. - DB Constraint: UNIQUE INDEX on
provider_event_idin Users table — rejects concurrent second write and auto-Rollback.
- Middleware queries
- Alerting: Log Warning (Severity-3) to
bps_audit_logsto monitor webhook replay frequency. (Source: STAGE3-012 — confirmed 2026-08-09)
Exc-5 — Invalid or NULL Asset_Class (confirmed — QnA STAGE3-022, 2026-08-10):
- Cause: Trigger payload carries
Asset_Classvalue outside{'Futures', 'Forex'}(e.g.,'Crypto', empty string, NULL) — possibly a legacy record or upstream data error. - Behavior: Flow 3A MUST HALT immediately. No KYC API call (no Veriff). No DB writes. No email dispatched.
- Logging: Error logged to system log with
user_idand the invalidAsset_Classvalue received. - Rationale: System is designed exclusively for Futures and Forex. Flow 3A's KYC routing branch (
Route KYC Flow) cannot execute without a validAsset_Class. Global safety directive: "All Funding Zaps must filter by Asset_Class." (Source: QnA STAGE3-022; Zapier Integration V7.pdf — "All Funding Zaps must filter by Asset_Class")
8. Business Rules
🔄 CR — STAGE3-037 [CHR-46]: KYC routing changed. All traders now use Veriff. Ironbeam WLP branch deleted.
<a id="BR_5.1.1"></a>
BR_5.1.1: KYC routing by Asset_Class — UPDATED (STAGE3-037 [CHR-46] 2026-08-12)
Flow 3A routes the KYC link generation based on
Asset_Class:-
'Forex' → Veriff hosted verification page (dynamic URL per session via POST /v1/sessions)- 'Futures' → Ironbeam White Label Portal URL (static, pre-configured)
All traders — both Futures and Forex — now use Veriff for identity verification. Ironbeam confirmed that because traders are independent contractors trading corporate capital, their full manual KYC applications are waived. Flow 3A calls POST /v1/sessions for all traders regardless of Asset_Class. The Asset_Class field still determines downstream behavior (Rithmic vs MT5/TE provisioning at Flow 3H) but no longer determines the KYC link type.
(Source: STAGE3-037 [CHR-46] confirmed 2026-08-12; Zapier Integration V7.pdf §Flow 3A — superseded for Futures path)
🔄 CR — STAGE3-037 [CHR-46]: Universal Veriff for all traders. Ironbeam WLP branch removed.
<a id="BR_5.1.2"></a>
BR_5.1.2: Dots payout setup — triggered in Flow 3B after Veriff APPROVED, NOT at Flow 3A
Flow 3A does NOT call the Dots API. Flow 3A's email (SES template Live_Onboarding_Compliance_Initiation) contains the kyc_link only.
The full 3-step Dots payee creation process occurs inside Flow 3B (Process Veriff Handoff, UC_5.2) after Veriff returns APPROVED:
POST /v2/users— creates the Dots user with SIM registration data (first_name,last_name,email,country_code,phone_number,metadata.internal_id).- Submit Compliance Information — patches Veriff-extracted
legal_name+addressto pre-fill the W-9 (US) or W-8BEN (International) tax form. POST /v2/flows(manage-payouts step) → returnsflow_link(personalized, session-scoped).
The flow_link from step 3 is dispatched in a second email ("Payout Profile Setup") at Flow 3B. Tax form routing (W-9 vs W-8BEN) is determined by Billing_Country at step 2.
Separation of concerns:
- Dots payee creation uses SIM registration data (
first_name/last_name/emailetc. from Stage 1/2 registration) for the user identity record. - Dots compliance submission uses Veriff-extracted data (
legal_name,address) to pre-fill the authoritative tax form. - Ironbeam compliance handoff (Flow 3H) uses Veriff-extracted data separately — SFTP/Secure Shared Drive, end-of-day batch (confirmed M-02 2026-08-15).
(Source: Zapier Integration V7.pdf §Flow 3A, §Flow 3B; STAGE3-050 confirmed 2026-08-15; M-02 confirmed 2026-08-15)
<a id="BR_5.1.3"></a>
BR_5.1.3: Dashboard lockout state machine — three phases (STAGE3-048 2026-08-12)
The dashboard lockout progresses through three phases, each driven by backend DB state:
| Phase | Trigger condition | Dashboard behavior |
|---|---|---|
| Phase 1 — Full Lock | identity_status, payout_status, or institution_approval_status is 'Pending' (Flows 3A–3E in progress) | Hard lockout overlay displayed. Sidebar disabled. Settings disabled. Trading disabled. Three progress circles visible. "Back to Website" only exit. |
| Phase 2 — Market Data Setup | contract_status = 'Signed' AND asset_class = 'Futures' AND setup_status = 'Pending' | Phase 1 overlay dismissed. Dashboard forced to Market Data Setup screen. Trading still locked. Sidebar + Settings still disabled. |
| Phase 3 — Unlocked | account_status = 'Active_L[N]_DMA' (set by Flow 3H) | All locks removed. Sidebar, Settings, and trading fully active. Bento Grid career map unlocked. Credentials tab accessible. |
Forex traders skip Phase 2:
setup_status = 'N/A'is set by Flow 3D. Forex goes directly Phase 1 → Phase 3.
Pending_Compliance is a frontend computed state — it is NOT stored as an account_status value in the DB at Flow 3A. Dashboard evaluates identity_status = 'Pending' OR institution_approval_status = 'Pending' OR payout_status = 'Pending' on every load.
⚠️ Note: The original RFQ_ Website and Dashboard Implementation V7.pdf §Passing Associate Track (lines 866–879) described a closable modal with a "Continue to Dashboard" CTA. This spec has been superseded by STAGE3-048 which mandates a hard lockout with no close button. The closable modal spec must NOT be implemented.
(Source: STAGE3-048 confirmed 2026-08-12; RFQ_ Website and Dashboard Implementation V7.pdf §Passing Associate Track — superseded)
BR_5.1.3a: Progress circles — dynamic DB state reflection
Each circle in the Phase 1 overlay reflects the real-time DB value of its corresponding field:
| Circle label | DB field | Pending | Completed |
|---|---|---|---|
| Identity Verification | identity_status | 'Pending' → empty ○ | 'Approved' → filled ● |
| Payout Setup | payout_status | 'Pending' → empty ○ | 'Approved' → filled ● |
| Trader Agreement | contract_status | 'Pending' → empty ○ | 'Signed' → filled ● |
institution_approval_status is not shown as a separate circle — it is set simultaneously with identity_status at Veriff APPROVED (STAGE3-037).
Frontend must update circles on WebSocket push or page refresh. DB is authoritative.
(Source: STAGE3-048 confirmed 2026-08-12)
<a id="BR_5.1.4"></a>
BR_5.1.4: SIM account lock precedes Flow 3A
Flow 3A must only fire after Flow 2 has already locked and flattened the SIM account (execution disabled, positions closed). Flow 3A does not itself call the Lock & Liquidate endpoint — that is Flow 2's responsibility.
(Source: Zapier Integration V7.pdf §Flow 2 — Action 1: Disable Sim Account; Action 2: Update SQL Database Status = 'Passed_Challenge'; Action 3: Trigger Flow 3)
<a id="BR_5.1.5"></a>
BR_5.1.5: Status fields written only after links are generated
The state management write (identity_status, institution_approval_status, payout_status all set to 'Pending') occurs in Step 6, after KYC link and Dots onboarding link are successfully generated (Steps 3–4) and the email is dispatched (Step 5). If any earlier step fails, the status fields MUST NOT be written. ⚠️ [ASSUMPTION — BA to confirm exact atomicity scope]
<a id="BR_5.1.6"></a>
BR_5.1.6: Downstream flow independence — UPDATED (STAGE3-037/039 2026-08-12)
Flow 3A does not trigger Flows 3B or 3C directly. Each downstream flow has its own independent trigger:
- Flow 3B: triggered by Veriff webhook (ALL traders — Futures and Forex; confirmed STAGE3-037)
Flow 3B.2: triggered by Zapier Email Parser (Futures traders,DELETED — UC_5.3 / Flow 3B.2 deprecated. Ironbeam inbound email parser removed from scope. (STAGE3-039 [CHR-46])FCM_approvals@stacktrading.com)- Flow 3C: triggered by Dots Active/Payable webhook (all traders)
(Source: Zapier Integration V7.pdf §Flow 3B; STAGE3-037/039 confirmed 2026-08-12)
<a id="BR_5.1.7"></a>
BR_5.1.7: MT5 profit-lock mechanism (Forex platform note)
For Forex traders on MT5, the SIM account profit-lock (Profit Target trigger, position flatten) is handled by the YourBourse Contest Stop Out server-side plugin on the MT5 White Label server — not by Middleware directly. When the plugin fires, Middleware detects the state change and fires the webhook to initiate Level-Up / Flow 3A activities.
(Source: RFQ_ Stack Trading Prop Tech V7.pdf §2.2 MT5 Infrastructure)
BR_5.1.8: Dashboard hard lockout during Flows 3A–3E (STAGE3-048 2026-08-12)
While any of identity_status, payout_status, or institution_approval_status is 'Pending' (i.e., Flows 3A–3E are not fully complete), the trader dashboard MUST enforce a hard lockout:
- Sidebar navigation: DISABLED
- Standard Settings menu: DISABLED
- Trader is locked to the "Live Onboarding In Progress" screen only
- "Back to Website" button is the only exit — routes to
www.stacktrading.com(public marketing site)
This lockout prevents any possibility of a trader bypassing onboarding flows or accessing execution modules before compliance is complete.
(Source: STAGE3-048 confirmed 2026-08-12 — "the intent is that the user can't access the standard Settings menu during this phase")
BR_5.1.9: "Back to Website" button routing (STAGE3-048 2026-08-12)
The "Back to Website" button present on the "Live Onboarding In Progress" lockout screen routes the user out of the application to the public Stack Trading marketing site: www.stacktrading.com. It does NOT navigate to another dashboard screen.
(Source: STAGE3-048 confirmed 2026-08-12)
<a id="BR_5.1.10"></a>
BR_5.1.10: POST /provision-in-house-trader — BPS admin in-house provisioning bypass (STAGE3-044)
POST /provision-in-house-trader is a BPS admin-only endpoint that provisions a trader directly into the live onboarding phase (Flow 3) without requiring the standard Associate Track checkout flow. Used for traders hired directly as in-house staff.
Input parameters:
| Parameter | Type | Description |
|---|---|---|
user_id | String | Target trader's user ID |
target_level | Integer | Entry level (1, 2, or 5) |
Desk fee logic (sourced from Table J):
| Fee type | Amount | Timing |
|---|---|---|
| Default desk fee | $800/month | From Table J |
| Upfront charge | 2× desk fee = $1,600 | Charged at provisioning |
| Recurring from Month 3 | 1× desk fee = $800/month | Monthly recurring |
After payment of the upfront 2× desk fee, the trader is pushed into Flow 3A. All subsequent flows (3B–3H) execute identically to a standard checkout trader.
Authorization: BPS admin RBAC only. Audit log required (Admin ID, Action, Timestamp, user_id, target_level, desk fee charged).
⚠️ PENDING CONFIRMATION (STAGE3-044):
target_level— restricted to Level 1 only, or can admin provision at Level 2/5?- Payment method for upfront desk fee — NMI Customer Vault or manual invoice?
- Month 3 recurring — same payment gateway as standard or separate billing?
- Does provisioned trader go through full KYC/Veriff/Dots/Rippling (Flows 3A–3G), or does admin attest compliance directly?
(Source: STAGE3-044 pending confirmation; Zapier Integration V7.pdf Table J desk fee)
<a id="BR_5.1.11"></a>
BR_5.1.11: Returnee Trader bypass — Branch B (STAGE3-055/H-07 extended, 2026-08-18)
When Flow 3A fires and the trader satisfies all three conditions simultaneously:
identity_status = 'Approved'dots_payee_id IS NOT NULLcontract_status = 'Signed'
…the system MUST execute Branch B and MUST NOT execute Branch A. Specifically:
- DO NOT create a new Veriff session (
POST /v1/sessionsmust NOT be called). - DO NOT reset
identity_status,institution_approval_status, orcontract_statusto'Pending'. - DO NOT dispatch the
Live_Onboarding_Compliance_InitiationKYC email. - DO NOT trigger Flows 3B, 3C, or 3D.
- DO set
payout_status = 'Approved'directly in Users table (atomic write with Step 6 below). - DO reset
setup_status = 'Pending'in the same atomic write — trader must repurchase market data. - DO fire internal webhook to trigger Flow 3F (Market Data Selection) immediately.
- Flow 3H provisions a new Live account from the Ironbeam/Forex pre-provisioned pool at
Current_Level(level of SIM just passed).
Rationale: Trader has already completed KYC, Dots tax form, and ICA in a prior cycle. Re-running compliance flows is unnecessary, creates compliance data duplication, and degrades UX. Market data must be repurchased because the prior subscription is terminated by Flow 7.
(Source: STAGE3-055/H-07 second-cycle Dots bypass — extended to full Flow 3A branch gate; setup_status reset confirmed 2026-08-18)
9. NFRs
| Area | Requirement |
|---|---|
| Availability | Veriff API availability is a prerequisite for successful execution. Flow 3A has no fallback mechanism if Veriff is unavailable. Dots API is NOT called at Flow 3A — Dots payee creation occurs in Flow 3B (UC_5.2) after Veriff APPROVED. (STAGE3-046) |
| Latency | ⚠️ No SLA documented for Flow 3A total execution time (Veriff session generation + email dispatch). BA to confirm acceptable range. |
| Idempotency | 3-layer guard: (1)provider_event_id check at Middleware API layer; (2) State Machine Guard on compliance status fields; (3) UNIQUE INDEX on provider_event_id in DB. See Exc-4. (Source: STAGE3-012) |
| Security | kyc_link must be included in the email body as a secure HTTPS URL and must NOT be logged in plaintext application logs. dots_onboarding_linkflow_link is dispatched in a separate "Payout Profile Setup" email from Flow 3B. (STAGE3-046/STAGE3-050) |
| Audit | Zapier execution log must capture user_id, Asset_Class, timestamp, and outcome (success/failure) for each Flow 3A run. All idempotency rejections logged to bps_audit_logs (Severity-3 Warning). |
10. Screen / UI References
Figma — Live Onboarding overlay (Shared File 2): Stack Trading Designs — Shared File 2, node-id 1-25967
Figma — Dashboard background (Finalized Asset Designs): Stack Trading Finalized Asset Designs, node-id 1767-361033 — Dashboard state sau khi trader bắt đầu Stage 3 (desaturated/dark overlay background visible behind Live Onboarding In Progress modal)
Full-flow wireframe:
- Phase 1 (all pending):
References/Wireframe/Stage 3/Stage 3: Total wireframe/Flow 3A: Dashboard.png - Phase 1A (KYC Approved):
References/Wireframe/Stage 3/Stage 3: Total wireframe/Flow 3B: Dashboard.png - Phase 1B (Contract Expired):
References/Wireframe/Stage 3/Stage 3: Total wireframe/Flow 3E: Contract's link expired.png
Phase 1 — "Live Onboarding In Progress" hard lockout overlay (confirmed from screenshot 2026-08-13; screenshot confirmed 2026-08-17):
Screenshot:
References/Wireframe/Stage 3/UC_5.1_Live_Onboarding_Initiation/Phase_1_Live_Onboarding_In_Progress.pngFull-flow ref:References/Wireframe/Stage 3/Stage 3: Total wireframe/Flow 3A: Dashboard.png
| Element | Spec |
|---|---|
| Headline | "Live Onboarding In Progress" |
| Subtitle | "Congratulations on passing the Associate Track. To provision your live account, you must complete Identity Verification, Payout Setup, and sign your Trader Agreement." |
| Info box | "Please check your email. We have sent you secure links to complete these required steps. This dashboard will unlock once your live account is fully provisioned." |
| Progress step 1 | ○ Identity Verification — empty circle + dashed connector |
| Progress step 2 | ○ Payout Setup — empty circle + dashed connector |
| Progress step 3 | ○ Trader Agreement — empty circle |
| CTA | "Back to Website" — full-width gold/tan pill button, full-width, routes to www.stacktrading.com |
| Close button | Not present — hard lockout, no dismiss |
| Modal style | Rounded card, dark frosted background, centered on screen |
| Background | Dashboard desaturated/dark — sidebar icons visible but inaccessible |
| Sidebar | Disabled / not accessible |
| Settings | Disabled / not accessible |
The original Dashboard V7 spec (§Passing Associate Track lines 866–879) described a closable modal with "Continue to Dashboard" CTA. Superseded by STAGE3-048. Do not implement the closable modal.
Phase 1A — "Live Onboarding In Progress" — KYC Approved sub-state (confirmed from screenshot 2026-08-17):
Triggered when identity_status = 'Approved' AND payout_status still 'Pending' AND contract_status still 'Pending'. Same hard lockout overlay as Phase 1, with Identity Verification step checked.
Screenshot:
References/Wireframe/Stage 3/UC_5.1_Live_Onboarding_Initiation/Phase_1A_KYC_Approved.pngFull-flow ref:References/Wireframe/Stage 3/Stage 3: Total wireframe/Flow 3B: Dashboard.png
| Element | Spec |
|---|---|
| Headline | "Live Onboarding In Progress" — unchanged |
| Subtitle | "Congratulations on passing the Associate Track. To provision your live account, you must complete Identity Verification, Payout Setup, and sign your Trader Agreement." — unchanged |
| Info box | "Please check your email. We have sent you secure links to complete these required steps. This dashboard will unlock once your live account is fully provisioned." — unchanged |
| Progress step 1 | ✅ Identity Verification — green filled checkmark + dashed connector |
| Progress step 2 | ○ Payout Setup — empty circle + dashed connector |
| Progress step 3 | ○ Trader Agreement — empty circle |
| CTA | "Back to Website" — full-width gold/tan pill button — unchanged |
| Close button | Not present — hard lockout, no dismiss |
| Background | Dashboard desaturated/dark — unchanged |
| Sidebar | Disabled / not accessible |
| Settings | Disabled / not accessible |
Phase 1B — "Live Onboarding In Progress" — Contract Expired sub-state (confirmed from screenshot 2026-08-14):
Triggered when identity_status = 'Approved' AND payout_status = 'Approved' AND contract_status = 'Expired' (signing link TTL of 7 days elapsed — per BR_5.5.10). Same hard lockout overlay as Phase 1, with the following differences:
Full-flow ref:
References/Wireframe/Stage 3/Stage 3: Total wireframe/Flow 3E: Contract's link expired.png
| Element | Spec |
|---|---|
| Headline | "Live Onboarding In Progress" —unchanged |
| Subtitle | "Your agreement link has expired. Please request a new link to complete your onboarding." |
| Info box | "Please check your email. We have sent you secure links to complete these required steps. This dashboard will unlock once your live account is fully provisioned." —unchanged |
| Progress step 1 | ✅ Identity Verification — green filled checkmark + dashed connector |
| Progress step 2 | ✅ Payout Setup — green filled checkmark + dashed connector |
| Progress step 3 | ⏳ Trader Agreement —hourglass/expired icon (red-orange) + inline text link: "🔄 Request New Contract Link" |
| CTA | "Back to Website" — full-width button, routes to www.stacktrading.com —unchanged |
| Close button | Not present — hard lockout, no dismiss |
| Background | Dark overlay covering dashboard content |
| Sidebar | Disabled / not accessible |
| Settings | Disabled / not accessible |
"Request New Contract Link" interaction:
- Trader clicks the inline link next to the Trader Agreement step.
- Frontend calls the backend endpoint to generate a new Rippling ICA signature request.
contract_statustransitions back from'Expired'→'Pending'.- Trader Agreement circle reverts from hourglass icon → empty circle (pending state).
- Subtitle reverts to standard Phase 1 subtitle.
- New signing link email dispatched to trader.
(Source: screenshot confirmed 2026-08-14; BR_5.5.10 — QnA STAGE3-034 confirmed 2026-08-12)
Phase 2 — Market Data Setup forced screen (Futures only):
Native Stack Trading dashboard screen. Activated when contract_status = 'Signed' AND setup_status = 'Pending'. Dashboard forces navigation to this screen — trader cannot navigate away. Option A (Standard, firm-paid) / Option B (Premium, trader-paid with native checkout). Confirmed platform: Stack Trading frontend (STAGE3-042). Full spec in UC_5.5 §9 Wireframe.
Phase 3 — Unlocked dashboard:
Standard Bento Grid layout. Career map, trading data, all navigation accessible. Connections & Credentials tab in Settings shows live platform login credentials. Activated when account_status = 'Active_L[N]_DMA' (Flow 3H).
11. Acceptance Criteria
| ID | Scenario | Expected Result |
|---|---|---|
| AC-5.1-01 | Flow 2 triggers Flow 3A with Asset_Class = 'Forex' and Billing_Country = 'US' | Veriff POST /v1/sessions called; kyc_link = verification_url; onboarding email dispatched with kyc_link only (SES template Live_Onboarding_Compliance_Initiation); identity_status = institution_approval_status = payout_status = 'Pending'; Dots payee creation deferred to Flow 3B after Veriff APPROVED |
| AC-5.1-02 | Asset_Class = 'Futures' and Billing_Country = 'US' | kyc_link = Ironbeam White Label Portal URL; Dots API called (Path A) |
| AC-5.1-03 | Flow 2 triggers Flow 3A with Asset_Class = 'Forex' and Billing_Country = 'GB' | Veriff POST /v1/sessions called; onboarding email dispatched with kyc_link only; Dots payee creation (W-8BEN path) deferred to Flow 3B after Veriff APPROVED |
| AC-5.1-04 | Flow 2 triggers Flow 3A with Asset_Class = 'Futures' and Billing_Country = 'AU' | Veriff POST /v1/sessions called (STAGE3-037 — all traders use Veriff); onboarding email dispatched with kyc_link only; Dots payee creation (W-8BEN path) deferred to Flow 3B after Veriff APPROVED |
| AC-5.1-05 | Trader logs into dashboard after Flow 3A completes (all compliance statuses ='Pending') | Hard lockout overlay renders with headline "Live Onboarding In Progress", three empty progress circles (Identity Verification / Payout Setup / Trader Agreement), "Back to Website" button. No close button. Sidebar and Settings disabled. |
| AC-5.1-06 | identity_status transitions to 'Approved' while overlay is visible | Identity Verification circle fills/checks in real time. Overlay remains. |
| AC-5.1-06b | payout_status transitions to 'Approved' | Payout Setup circle fills/checks. Overlay remains. |
| AC-5.1-06c | contract_status transitions to 'Signed' | Trader Agreement circle fills/checks. If asset_class = 'Futures': overlay dismissed; forced to Market Data Setup screen. If asset_class = 'Forex': overlay remains until account_status = 'Active_L[N]_DMA'. |
| AC-5.1-06e | contract_status = 'Expired' (signing link TTL elapsed — 7 days) while identity_status = 'Approved' AND payout_status = 'Approved' | Overlay subtitle changes to "Your agreement link has expired. Please request a new link to complete your onboarding." Trader Agreement circle changes from empty → hourglass/expired icon (red-orange). Inline "🔄 Request New Contract Link" link appears next to Trader Agreement step. Identity Verification and Payout Setup circles remain green checkmarks. "Back to Website" button unchanged. |
| AC-5.1-06f | Trader clicks "Request New Contract Link" (Phase 1B expired state) | Frontend calls backend to generate new Rippling ICA request.contract_status transitions 'Expired' → 'Pending'. Trader Agreement circle reverts to empty circle. Subtitle reverts to standard Phase 1 text. New signing link email dispatched. |
| AC-5.1-06d | Trader clicks "Back to Website" during hard lockout | Routed to www.stacktrading.com. Dashboard session preserved. |
| AC-5.1-07 | Trader logs in after account_status = 'Active_L[N]_DMA' (Flow 3H provisioning complete) | Overlay does NOT appear |
| AC-5.1-08 | Veriff POST /v1/sessions returns non-200 (any trader) | Flow 3A does NOT dispatch the onboarding email; error logged; Operations alerted |
| AC-5.1-09 | Dots API returns non-200 (Flow 3B — Step 4A-1 POST /v2/users) | Dots failure handled in UC_5.2 (Flow 3B). Flow 3A is not affected — Dots is not called at Flow 3A. |
| AC-5.1-10 | BPS admin triggers POST /api/bps/kyc/reset (Flow 3.1) for a trader whose KYC email was not received | veriff_failed_flag cleared; veriff_attempts = 0; new Veriff session created; reset email dispatched via AWS SES; Ops Slack alert fired. POST /resend-welcome (Flow 41) must NOT be used for this case. |
| AC-5.1-11 | Onboarding email content verified | Email contains kyc_link (Veriff hosted verification URL) only (SES template Live_Onboarding_Compliance_Initiation). Dots payout setup flow_link is sent in a second email from Flow 3B after Veriff APPROVED. (STAGE3-050 / STAGE3-060) |
| AC-5.1-12 | Flow 3A fires twice for the same user_id (double-trigger) | Second trigger rejected by 3-layer idempotency guard: (1)provider_event_id check → HTTP 200 No-Op; (2) State Machine Guard on compliance fields; (3) DB UNIQUE INDEX. No duplicate Veriff session, no duplicate email. Warning logged to bps_audit_logs. (Source: STAGE3-012) |
| AC-5.1-13 | Flow 3A receives trigger payload where Asset_Class is NULL or an invalid value (e.g., 'Crypto') | Flow 3A halts immediately. No Veriff call, no DB writes, no email dispatched. Error logged to system log with user_id and invalid Asset_Class value. (Source: QnA STAGE3-022, confirmed 2026-08-10) |
| AC-5.1-14 | BPS admin calls POST /provision-in-house-trader with valid user_id + target_level | Upfront 2× desk fee ($1,600) charged. Trader pushed into Flow 3A. Audit log entry created with Admin ID, Action, Timestamp,user_id, target_level. |
| AC-5.1-15 | Non-admin calls POST /provision-in-house-trader | Request rejected with 403. No charge. No provisioning. |
| AC-5.1-16 | Flow 3A fires for a Returnee Trader: identity_status='Approved', dots_payee_id IS NOT NULL, contract_status='Signed' | Branch B executes: no Veriff call; no KYC email; compliance fields NOT reset; payout_status='Approved' + setup_status='Pending' written atomically; internal webhook fires Flow 3F; dashboard enters Phase 2 Market Data Setup screen. (BR_5.1.11) |
| AC-5.1-17 | Flow 3A fires for a New Trader: dots_payee_id IS NULL (any other Branch A condition) | Branch A executes: Veriff session created; identity_status = institution_approval_status = payout_status = 'Pending'; Live_Onboarding_Compliance_Initiation email dispatched; Phase 1 hard-lockout overlay rendered. |
| AC-5.1-18 | Returnee Trader completes Market Data selection (Flow 3F/3G) and Flow 3H triggers | New Live account provisioned from pre-provisioned pool at Current_Level (level of SIM just passed); account_status = 'Active_L[N]_DMA' set. |
12. Update History
| Date | Version | Updated item | Before | After | Notes |
|---|---|---|---|---|---|
| 2026-08-21 | v2.0 → v2.1 | B1: STAGE3-037 tags (L132, L189, L194, L226, L328, L332, L340) · A34: CR-20260813-001 refs (L189, L328, L344) · B2: STAGE3-039 tags (L194, L231, L433) | STAGE3-037 bare · CR-20260813-001 date-ref · STAGE3-039 bare | STAGE3-037 [CHR-46] · [CHR-46] · STAGE3-039 [CHR-46] | CHR tag standardization per CHR_Tag_Change_Plan_20260822_v4.md |
| 2026-08-24 | v2.1 → v2.2 | Profit_Target_Pct — formula, parameter table, example | Hardcoded 14% (Static, MKT-26) | SIM_target_percent read from Zapier Table C; current value 14% but configurable | Client confirmed 2026-08-24 |