top of page
WhatsApp Image 2026-07-21 at 06.23.19.jpeg

import { ok, badRequest, forbidden } from 'wix-http-functions'; import { fetch } from 'wix-fetch'; import { getSecret } from 'wix-secrets-backend'; import wixData from 'wix-data'; /* Brooks V4A5.1 Execution Continuity Repair — coordinated Wix endpoint XAUUSD M5 / DEMO ONLY V4A5 contract: - STORY requests create/update strategic context and at most three decision areas. - cTrader locally owns WAIT, rejection/acceptance proof, frozen plan construction and M5/M1 execution. - No tactical new-entry request type is accepted by this endpoint. - Confidence / storyConfidence / opportunityQuality are 0-100 percentages. - The deterministic cBot owns executable R:R and all final execution gates. - Pre-armed outer-breakout fields remain in the strict schema only for wire compatibility; V4A4 keeps both prearmed Enabled flags FALSE and zero/empty/NONEs those fields. - Diagnostics retention is 7 days; diagnostic retries are idempotent by batchId. Required Wix Secrets: OPENAI_API_KEY BROOKS_BOT_SECRET BROOKS_DIAGNOSTICS_READ_KEY Required CMS collection: BrooksDiagnostics Planner jobs are stored in BrooksDiagnostics with botId=BROOKS_PLANNER_JOB. */ const VERSION = 'WIX_BROOKS_V4A5_1_EXECUTION_CONTINUITY_REPAIR'; const OPENAI_URL = 'https://api.openai.com/v1/responses'; const MODEL = 'gpt-5.6-terra'; // Planner jobs intentionally share BrooksDiagnostics. const DIAGS = 'BrooksDiagnostics'; const RETENTION_MS = 7 * 24 * 60 * 60 * 1000; const MAX_DIAG_EVENTS = 120; const REQUEST_TYPES = [ 'DAILY_CONTEXT','ASIA_TO_LONDON','LONDON_TO_US','STALE_SAFEGUARD', 'OPEN_TRADE_REVIEW','STRUCTURAL_BREAK' ]; const TARGET_BASES = [ 'PRIOR_SWING','MAJOR_SUPPORT_RESISTANCE','TRADING_RANGE_BOUNDARY','MEASURED_MOVE', 'BREAKOUT_TEST','SESSION_HIGH_LOW','HIGHER_TIMEFRAME_LEVEL','EMA_OR_CHANNEL_MAGNET', 'OTHER_BROOKS_STRUCTURAL','NONE' ]; const STOP_ANCHORS = [ 'SIGNAL_BAR_EXTREME','FAILED_BREAKOUT_EXTREME','RECENT_SWING','RECENT_HIGHER_LOW', 'RECENT_LOWER_HIGH','BREAKOUT_SPIKE_ORIGIN','OPENING_SECOND_TEST_EXTREME', 'RANGE_EDGE_STRUCTURE','OTHER_BROOKS_STRUCTURAL','NONE' ]; function nEnum(values) { return { type: 'string', enum: values }; } function num() { return { type: 'number' }; } function str() { return { type: 'string' }; } function bool() { return { type: 'boolean' }; } const P = { responseMode:nEnum(['STORY_MAP','STORY_UNCHANGED','EXECUTION_PLAN','LEVEL_CANCELLED','NO_ACTION','TRADE_MANAGEMENT']), requestTypeEcho:nEnum(REQUEST_TYPES), marketStory:str(), marketCycle:nEnum(['BULL_TREND','BEAR_TREND','BULL_CHANNEL','BEAR_CHANNEL','TRADING_RANGE','BREAKOUT_MODE','REVERSAL_ATTEMPT','UNCLEAR','NONE']), directionalBias:nEnum(['BULL','BEAR','TWO_SIDED','NEUTRAL','NONE']), keySupport:num(), keyResistance:num(), primaryScenario:str(), alternativeScenario:str(), storyConfidence:{type:'number',minimum:0,maximum:100}, activePlanCompatibility:nEnum(['COMPATIBLE','INCOMPATIBLE','NOT_APPLICABLE']), activePlanCompatibilityReason:str(), majorLevel1Low:num(), majorLevel1High:num(), majorLevel1Role:nEnum(['BUY_AREA','SELL_AREA','DECISION_ONLY','NONE']), majorLevel1Reason:str(), majorLevel2Low:num(), majorLevel2High:num(), majorLevel2Role:nEnum(['BUY_AREA','SELL_AREA','DECISION_ONLY','NONE']), majorLevel2Reason:str(), majorLevel3Low:num(), majorLevel3High:num(), majorLevel3Role:nEnum(['BUY_AREA','SELL_AREA','DECISION_ONLY','NONE']), majorLevel3Reason:str(), levelId:nEnum(['LEVEL1','LEVEL2','LEVEL3','NONE']), levelDecision:nEnum(['MAPPED_HYPOTHESIS','OPPOSITE_SIDE','TWO_SIDED_CHOICE','WAIT','CANCEL','STORY_REMAP','NONE']), preferredDirection:nEnum(['BUY','SELL','NONE']), setupFamily:nEnum(['BREAKOUT_PULLBACK','TREND_PULLBACK','RANGE_REVERSAL','FAILED_BREAKOUT','MAJOR_TREND_REVERSAL','WEDGE','DOUBLE_TOP_BOTTOM','SECOND_ENTRY','MEASURED_MOVE','OTHER_BROOKS','NONE']), setupName:str(), entryZoneLow:num(), entryZoneHigh:num(), triggerType:nEnum(['BULL_SIGNAL_BAR','BEAR_SIGNAL_BAR','BULL_BREAKOUT_ACCEPTANCE','BEAR_BREAKDOWN_ACCEPTANCE','FAILED_BREAKOUT_CONFIRMATION','FAILED_BREAKDOWN_CONFIRMATION','STRONG_REVERSAL_BAR','BULL_CLOSED_STRUCTURE_BREAK','BEAR_CLOSED_STRUCTURE_BREAK','NONE']), triggerDescription:str(), invalidationPrice:num(), stopLossPrice:num(), target1Price:num(), target2Price:num(), target1Basis:nEnum(TARGET_BASES), target1Reason:str(), target2Basis:nEnum(TARGET_BASES), target2Reason:str(), minimumRewardRisk:{type:'number',minimum:0,maximum:20}, confidence:{type:'number',minimum:0,maximum:100}, opportunityQuality:{type:'number',minimum:0,maximum:100}, expiryBars:{type:'integer',minimum:0,maximum:48}, dominantLegDirection:nEnum(['BULL','BEAR','BALANCED','NONE']), dominantLegStrength:nEnum(['STRONG','MODERATE','WEAK','MIXED','NONE']), secondLegExpectation:nEnum(['BULL_SECOND_LEG_LIKELY','BEAR_SECOND_LEG_LIKELY','BULL_SECOND_LEG_COMPLETED_OR_FAILED','BEAR_SECOND_LEG_COMPLETED_OR_FAILED','NO_CLEAR_SECOND_LEG','NONE']), secondLegResolutionType:nEnum(['SECOND_TEST_COMPLETED','STRONG_OPPOSITE_BREAKOUT_WITH_FOLLOWTHROUGH','CLEAR_ALWAYS_IN_FLIP','OPENING_CLIMAX_REVERSAL_WITH_FOLLOWTHROUGH','NONE']), secondLegResolutionEvidence:str(), probabilityBucket:nEnum(['PROB_40','PROB_50','PROB_60_PLUS','NONE']), stopAnchorPrice:num(), stopAnchorType:nEnum(STOP_ANCHORS), stopAnchorReason:str(), tradeContext:nEnum(['WITH_DOMINANT_LEG','COUNTERTREND','TRADING_RANGE_TWO_SIDED','BREAKOUT_CONTINUATION','NONE']), tradeManagementStyle:nEnum(['SCALP','SWING','RUNNER_CANDIDATE','NONE']), requiresClosedStructureConfirmation:bool(), structureConfirmationPrice:num(), managedPositionId:{type:'integer',minimum:0}, tradeAction:nEnum(['HOLD','PROTECT_PROFIT','EXIT','PROMOTE_RUNNER','NONE']), managementStopPrice:num(), managementTargetPrice:num(), managementTargetBasis:nEnum(TARGET_BASES), managementTargetReason:str(), managementReason:str(), continuationEvidence:str(), exhaustionEvidence:str(), proposalReason:str(), noTradeReason:str(), waitReasonCode:nEnum(['BLOCKED_BY_NEAREST_TARGET','AWAITING_STRUCTURE_CONFIRMATION','AWAITING_REJECTION_OR_ACCEPTANCE','NO_VALID_TRADER_EQUATION','OTHER','NONE']), resumeEventType:nEnum(['BULL_ACCEPTANCE_ABOVE_BOUNDARY','BEAR_ACCEPTANCE_BELOW_BOUNDARY','BULL_REJECTION_FROM_BOUNDARY','BEAR_REJECTION_FROM_BOUNDARY','FAILED_BULL_BREAKOUT_REENTRY','FAILED_BEAR_BREAKDOWN_REENTRY','NONE']), resumeBoundaryPrice:num(), resumeReason:str(), bullResumeEventType:nEnum(['BULL_ACCEPTANCE_ABOVE_BOUNDARY','BULL_REJECTION_FROM_BOUNDARY','FAILED_BEAR_BREAKDOWN_REENTRY','NONE']), bullResumeBoundaryPrice:num(), bullResumeReason:str(), bearResumeEventType:nEnum(['BEAR_ACCEPTANCE_BELOW_BOUNDARY','BEAR_REJECTION_FROM_BOUNDARY','FAILED_BULL_BREAKOUT_REENTRY','NONE']), bearResumeBoundaryPrice:num(), bearResumeReason:str(), blockingTargetPrice:num(), blockingTargetDirection:nEnum(['BUY','SELL','NONE']), blockingTargetBasis:nEnum(TARGET_BASES), blockingTargetReason:str(), hardStoryChange:bool(), hardStoryChangeReason:str(), brooksReasoning:{type:'array',items:{type:'string'},maxItems:8}, warnings:{type:'array',items:{type:'string'},maxItems:8}, demoOnly:{type:'boolean',enum:[true]}, // V4A4 wire-compatibility fields only. Keep disabled/zeroed on every response. prearmedL1UpEnabled:bool(), prearmedL1UpEntryZoneLow:num(), prearmedL1UpEntryZoneHigh:num(), prearmedL1UpTriggerDescription:str(), prearmedL1UpInvalidationPrice:num(), prearmedL1UpStopLossPrice:num(), prearmedL1UpTarget1Price:num(), prearmedL1UpTarget2Price:num(), prearmedL1UpTarget1Basis:nEnum(TARGET_BASES), prearmedL1UpTarget1Reason:str(), prearmedL1UpTarget2Basis:nEnum(TARGET_BASES), prearmedL1UpTarget2Reason:str(), prearmedL1UpMinimumRewardRisk:{type:'number',minimum:0,maximum:20}, prearmedL1UpConfidence:{type:'number',minimum:0,maximum:100}, prearmedL1UpOpportunityQuality:{type:'number',minimum:0,maximum:100}, prearmedL1UpExpiryBars:{type:'integer',minimum:0,maximum:48}, prearmedL1UpStopAnchorPrice:num(), prearmedL1UpStopAnchorType:nEnum(STOP_ANCHORS), prearmedL1UpStopAnchorReason:str(), prearmedL1UpReason:str(), prearmedL3DownEnabled:bool(), prearmedL3DownEntryZoneLow:num(), prearmedL3DownEntryZoneHigh:num(), prearmedL3DownTriggerDescription:str(), prearmedL3DownInvalidationPrice:num(), prearmedL3DownStopLossPrice:num(), prearmedL3DownTarget1Price:num(), prearmedL3DownTarget2Price:num(), prearmedL3DownTarget1Basis:nEnum(TARGET_BASES), prearmedL3DownTarget1Reason:str(), prearmedL3DownTarget2Basis:nEnum(TARGET_BASES), prearmedL3DownTarget2Reason:str(), prearmedL3DownMinimumRewardRisk:{type:'number',minimum:0,maximum:20}, prearmedL3DownConfidence:{type:'number',minimum:0,maximum:100}, prearmedL3DownOpportunityQuality:{type:'number',minimum:0,maximum:100}, prearmedL3DownExpiryBars:{type:'integer',minimum:0,maximum:48}, prearmedL3DownStopAnchorPrice:num(), prearmedL3DownStopAnchorType:nEnum(STOP_ANCHORS), prearmedL3DownStopAnchorReason:str(), prearmedL3DownReason:str() }; const RESPONSE_SCHEMA = { name:'brooks_v4a5_local_tactical_executor', strict:true, schema:{ type:'object', additionalProperties:false, properties:P, required:Object.keys(P) } }; const SYSTEM_PROMPT = ` You are the bigger-picture Al Brooks price-action strategist for XAUUSD in a DEMO-ONLY research/execution system. The deterministic cTrader robot owns all tactical waiting and new-entry execution. You supply strategy, not permission. V4A5 LOCAL TACTICAL EXECUTOR CONTRACT: Use Brooks sequence: context left -> market cycle -> breakout/spike -> channel/trend -> trading range -> support/resistance/magnets -> setup/location -> proof -> trader equation. ATR is measurement only. Never use ATR to choose direction. CONFIDENCE SCALE — HARD CONTRACT: storyConfidence, confidence and opportunityQuality are percentages from 0 to 100. Example: sixty-six percent MUST be 66, NEVER 0.66. STORY REQUESTS (DAILY_CONTEXT, ASIA_TO_LONDON, LONDON_TO_US, STALE_SAFEGUARD, STRUCTURAL_BREAK): Build/update at most three coherent strategic decision areas. A story request never fires a trade. Set all legacy and bull/bear resume fields to NONE/0/empty. Set both prearmed Enabled flags false and zero/empty/NONE every prearmed field. TACTICAL NEW-ENTRY REQUESTS ARE FORBIDDEN: Never act as an entry permission gate. LEVEL_ENGAGEMENT, LEVEL_APPROACH, LEVEL_TOUCH, LEVEL_MATERIAL_REASSESS and BLOCKING_MAGNET_BROKEN are not accepted request types. cTrader derives both acceptance and rejection playbooks from your scheduled map and waits locally. OPEN_TRADE_REVIEW: Manage only the supplied existing position. Return TRADE_MANAGEMENT with HOLD, PROTECT_PROFIT, EXIT or earned PROMOTE_RUNNER. Never widen risk, add size or reverse. Set resumeEventType=NONE, resumeBoundaryPrice=0 and resumeReason="". EXECUTION QUALITY: - Structure first, RR second. Never manufacture targets or squeeze stops to manufacture R:R. - The cBot owns the executable RR threshold. - T1 is the honest primary probable structural objective. T2 is optional extension context, never a rescue target. - Countertrend plans require closed structure confirmation; one opposite-colour bar is insufficient. - Strong legs normally create a second-leg expectation. Do not casually fade the first reversal against a strong leg. - BLOCKED_BY_NEAREST_TARGET is reserved for decision-grade structure, not a tiny M5 pivot, round number or standalone EMA. - demoOnly must always be true. For every response, all legacy and directional resume fields must be NONE/0/empty. For all non-STORY_MAP responses set both prearmed Enabled flags false and zero/empty/NONE every prearmed field. `; function jsonBody(x) { return { headers:{'Content-Type':'application/json'}, body:JSON.stringify(x) }; } function token(x) { return String(x ?? '').trim().toUpperCase(); } function requestIdOf(x) { return String(x?.plannerRequestId || x?.requestId || '').trim(); } function reasoning(type) { return token(type)==='OPEN_TRADE_REVIEW' ? 'low' : 'medium'; } function maxTokens(type) { type=token(type); if(type==='OPEN_TRADE_REVIEW') return 2200; return 5000; } async function secret(name) { try { return await getSecret(name); } catch(e) { return ''; } } async function authorised(request) { const expected=await secret('BROOKS_BOT_SECRET'); const got=String(request?.headers?.['x-bot-secret'] || request?.headers?.['X-Bot-Secret'] || ''); return !!expected && got===expected; } async function bodyJson(request) { try { return await request.body.json(); } catch(e) { try { return JSON.parse(await request.body.text()); } catch(_) { return null; } } } function buildInput(incoming) { const type=token(incoming?.requestType); let instruction='Follow the contract and return the strict schema only.'; if(['DAILY_CONTEXT','ASIA_TO_LONDON','LONDON_TO_US','STALE_SAFEGUARD','STRUCTURAL_BREAK'].includes(type)) instruction='V4A5 strategic story request. Build/update the session map and contingency narrative only if justified. Clear all tactical resume and prearmed fields. cTrader owns local execution.'; else if(type==='OPEN_TRADE_REVIEW') instruction='Manage only the supplied open demo position. No new entry.'; else instruction='V4A5 strategic request only. Return story context, never tactical entry permission.'; return `${instruction}\n\nMARKET PACKET JSON:\n${JSON.stringify(incoming)}`; } async function openAiSubmit(apiKey,incoming) { const payload={ model:MODEL, background:true, reasoning:{effort:reasoning(incoming?.requestType)}, max_output_tokens:maxTokens(incoming?.requestType), input:[ {role:'system',content:[{type:'input_text',text:SYSTEM_PROMPT}]}, {role:'user',content:[{type:'input_text',text:buildInput(incoming)}]} ], text:{format:{type:'json_schema',name:RESPONSE_SCHEMA.name,strict:true,schema:RESPONSE_SCHEMA.schema}} }; const r=await fetch(OPENAI_URL,{method:'post',headers:{Authorization:`Bearer ${apiKey}`,'Content-Type':'application/json'},body:JSON.stringify(payload)}); const raw=await r.text(); let data={}; try{data=JSON.parse(raw)}catch(e){} if(!r.ok) return {ok:false,status:r.status,error:'OPENAI_SUBMIT_FAILED',detail:raw.slice(0,1800)}; return {ok:true,data}; } async function openAiPoll(apiKey,id) { const r=await fetch(`${OPENAI_URL}/${encodeURIComponent(id)}`,{method:'get',headers:{Authorization:`Bearer ${apiKey}`}}); const raw=await r.text(); let data={}; try{data=JSON.parse(raw)}catch(e){} if(!r.ok) return {ok:false,status:r.status,error:'OPENAI_POLL_FAILED',detail:raw.slice(0,1800)}; return {ok:true,data}; } function outputText(resp) { if(typeof resp?.output_text==='string' && resp.output_text.trim()) return resp.output_text; for(const item of (resp?.output||[])) for(const c of (item?.content||[])) if((c?.type==='output_text'||c?.type==='text') && typeof c?.text==='string') return c.text; return ''; } function usage(resp) { const u=resp?.usage||{}; const out=Number(u.output_tokens||0); const reasoning=Number(u.output_tokens_details?.reasoning_tokens||0); return {inputTokens:Number(u.input_tokens||0),cachedInputTokens:Number(u.input_tokens_details?.cached_tokens||0),outputTokens:out,reasoningTokens:reasoning,nonReasoningOutputTokens:Math.max(0,out-reasoning),totalTokens:Number(u.total_tokens||0)}; } function plannerFromResponse(resp) { const text=outputText(resp); let proposal=null; try{proposal=JSON.parse(text)}catch(e){} const good=!!proposal; return { ok:good, model:MODEL, reasoningEffort:'medium', contractValid:good, semanticRetry:false, attempts:1, latencyMs:0, error:good?'':'MODEL_OUTPUT_NOT_JSON', upstreamStatus:200, upstreamCode:'', upstreamType:'', upstreamMessage:'', usage:usage(resp), proposal:proposal||{} }; } // V4A4 inherited durable planner storage: // Planner jobs share the existing BrooksDiagnostics collection with botId=BROOKS_PLANNER_JOB. async function findJob(id) { try { const item = await wixData.get(DIAGS, id, { suppressAuth: true, consistentRead: true }); if (!item || item.botId !== 'BROOKS_PLANNER_JOB') return null; let payload = {}; try { payload = JSON.parse(item.eventsJson || '{}'); } catch (_) { payload = {}; } return { ...payload, _id: item._id }; } catch (_) { return null; } } async function saveJob(job) { const id = String(job?._id || job?.requestId || '').trim(); if (!id) throw new Error('PLANNER_JOB_ID_MISSING'); const payload = { ...job }; delete payload._id; const item = { _id: id, botId: 'BROOKS_PLANNER_JOB', botVersion: VERSION, symbol: 'XAUUSD', timeframe: 'M5', sentUtc: new Date().toISOString(), eventCount: 0, eventsJson: JSON.stringify(payload) }; if (job._id) { const saved = await wixData.update(DIAGS, item, { suppressAuth: true }); return { ...payload, _id: saved._id }; } try { const saved = await wixData.insert(DIAGS, item, { suppressAuth: true }); return { ...payload, _id: saved._id }; } catch (error) { const existing = await findJob(id); if (existing) return existing; throw error; } } export async function get_brooksPlanHealth() { return ok(jsonBody({ok:true,version:VERSION,model:MODEL,mode:'V4A5_LOCAL_TACTICAL_EXECUTOR',diagnosticsRetentionDays:7,demoOnly:true,time:new Date().toISOString()})); } export async function post_brooksPlan(request) { if(!(await authorised(request))) return forbidden(jsonBody({ok:false,error:'FORBIDDEN'})); const incoming=await bodyJson(request); if(!incoming) return badRequest(jsonBody({ok:false,error:'INVALID_JSON'})); const type=token(incoming.requestType); if(!REQUEST_TYPES.includes(type)) return badRequest(jsonBody({ok:false,error:'INVALID_REQUEST_TYPE'})); const rid=requestIdOf(incoming); if(!rid) return badRequest(jsonBody({ok:false,error:'MISSING_PLANNER_REQUEST_ID'})); let job=await findJob(rid); if(job){ if(job.state==='COMPLETED' && job.plannerJson){ let planner; try{planner=JSON.parse(job.plannerJson)}catch(e){}; if(planner) return ok(jsonBody({ok:true,requestId:rid,asyncState:'COMPLETED',planner,duplicateProtected:true})); } if(job.state==='FAILED') return ok(jsonBody({ok:false,requestId:rid,asyncState:'FAILED',error:job.error||'FAILED'})); return ok(jsonBody({ok:true,requestId:rid,asyncState:job.state||'IN_PROGRESS',pollAfterMs:1200,duplicateProtected:true})); } const apiKey=await secret('OPENAI_API_KEY'); if(!apiKey) return ok(jsonBody({ok:false,requestId:rid,asyncState:'FAILED',error:'OPENAI_KEY_MISSING'})); const sub=await openAiSubmit(apiKey,incoming); if(!sub.ok) return ok(jsonBody({ok:false,requestId:rid,asyncState:'FAILED',error:sub.error,detail:sub.detail})); const state=token(sub.data?.status||'QUEUED'); job=await saveJob({requestId:rid,openAiId:String(sub.data?.id||''),state:state==='COMPLETED'?'COMPLETED':state,requestType:type,createdAt:new Date(),updatedAt:new Date(),plannerJson:'',error:''}); if(state==='COMPLETED'){ const planner=plannerFromResponse(sub.data); job.state=planner.ok?'COMPLETED':'FAILED'; job.plannerJson=JSON.stringify(planner); job.error=planner.error||''; job.updatedAt=new Date(); await saveJob(job); return ok(jsonBody({ok:planner.ok,requestId:rid,asyncState:job.state,planner})); } return ok(jsonBody({ok:true,requestId:rid,asyncState:state,pollAfterMs:1200})); } export async function post_brooksPlanResult(request) { if(!(await authorised(request))) return forbidden(jsonBody({ok:false,error:'FORBIDDEN'})); const incoming=await bodyJson(request); if(!incoming) return badRequest(jsonBody({ok:false,error:'INVALID_JSON'})); const rid=requestIdOf(incoming); if(!rid) return badRequest(jsonBody({ok:false,error:'MISSING_REQUEST_ID'})); let job=await findJob(rid); if(!job) return ok(jsonBody({ok:false,requestId:rid,asyncState:'FAILED',error:'JOB_NOT_FOUND'})); if(job.state==='COMPLETED' && job.plannerJson){let planner;try{planner=JSON.parse(job.plannerJson)}catch(e){};return ok(jsonBody({ok:true,requestId:rid,asyncState:'COMPLETED',planner,duplicateProtected:true}));} if(job.state==='FAILED') return ok(jsonBody({ok:false,requestId:rid,asyncState:'FAILED',error:job.error||'FAILED'})); const apiKey=await secret('OPENAI_API_KEY'); const polled=await openAiPoll(apiKey,job.openAiId); if(!polled.ok) return ok(jsonBody({ok:true,requestId:rid,asyncState:job.state||'IN_PROGRESS',pollAfterMs:1800,pollTransportRetry:true})); const state=token(polled.data?.status||'IN_PROGRESS'); if(['QUEUED','IN_PROGRESS'].includes(state)){job.state=state;job.updatedAt=new Date();await saveJob(job);return ok(jsonBody({ok:true,requestId:rid,asyncState:state,pollAfterMs:1200}));} if(state!=='COMPLETED'){job.state='FAILED';job.error=String(polled.data?.error?.message||polled.data?.incomplete_details?.reason||state);job.updatedAt=new Date();await saveJob(job);return ok(jsonBody({ok:false,requestId:rid,asyncState:'FAILED',error:job.error}));} const planner=plannerFromResponse(polled.data); job.state=planner.ok?'COMPLETED':'FAILED'; job.plannerJson=JSON.stringify(planner); job.error=planner.error||''; job.updatedAt=new Date(); await saveJob(job); return ok(jsonBody({ok:planner.ok,requestId:rid,asyncState:job.state,planner,duplicateProtected:true})); } async function cleanupDiagnostics() { const cutoff=new Date(Date.now()-RETENTION_MS); let q=await wixData.query(DIAGS).lt('_createdDate',cutoff).limit(100).find({suppressAuth:true}); for(const item of (q.items||[])) try{await wixData.remove(DIAGS,item._id,{suppressAuth:true})}catch(e){} } export async function post_brooksDiagnosticsIn(request) { if(!(await authorised(request))) return forbidden(jsonBody({ok:false,error:'FORBIDDEN'})); const incoming=await bodyJson(request); if(!incoming) return badRequest(jsonBody({ok:false,error:'INVALID_JSON'})); const events=Array.isArray(incoming.events)?incoming.events.slice(-MAX_DIAG_EVENTS):[]; const batchId=String(incoming.batchId||'').trim(); // V4A4 diagnostics reliability: a timed-out/stuck cBot push retries with the // SAME batchId. Store that ID as the CMS item _id so retries are idempotent. if(batchId){ try{ const existing=await wixData.get(DIAGS,batchId,{suppressAuth:true,consistentRead:true}); if(existing && existing.botId!=='BROOKS_PLANNER_JOB') return ok(jsonBody({ok:true,stored:Number(existing.eventCount||0),retentionDays:7,batchId,duplicateProtected:true})); }catch(_){} } const item={ botId:String(incoming.botId||'XAUUSD_M5_DEMO'), botVersion:String(incoming.botVersion||''), symbol:String(incoming.symbol||'XAUUSD'), timeframe:String(incoming.timeframe||'M5'), sentUtc:String(incoming.sentUtc||''), eventsJson:JSON.stringify(events), eventCount:events.length, receivedAt:new Date() }; if(batchId) item._id=batchId; try{ await wixData.insert(DIAGS,item,{suppressAuth:true}); }catch(error){ if(!batchId) throw error; try{ const existing=await wixData.get(DIAGS,batchId,{suppressAuth:true,consistentRead:true}); if(existing && existing.botId!=='BROOKS_PLANNER_JOB') return ok(jsonBody({ok:true,stored:Number(existing.eventCount||0),retentionDays:7,batchId,duplicateProtected:true})); }catch(_){} throw error; } await cleanupDiagnostics(); return ok(jsonBody({ok:true,stored:events.length,retentionDays:7,batchId,duplicateProtected:false})); } export async function get_brooksDiagnostics(request) { const key=String(request?.query?.key||''); const expected=await secret('BROOKS_DIAGNOSTICS_READ_KEY'); if(!expected || key!==expected) return forbidden(jsonBody({ok:false,error:'FORBIDDEN'})); const bot=String(request?.query?.bot||'XAUUSD_M5_DEMO'); const limit=Math.max(1,Math.min(100,Number(request?.query?.limit||40))); const q=await wixData.query(DIAGS).eq('botId',bot).descending('_createdDate').limit(limit).find({suppressAuth:true}); return ok(jsonBody({ok:true,version:VERSION,retentionDays:7,count:q.items?.length||0,items:(q.items||[]).map(x=>({batchId:x._id,createdDate:x._createdDate,botId:x.botId,botVersion:x.botVersion,eventCount:x.eventCount,eventsJson:x.eventsJson}))})); }

Driving Freedom 
Starts Here

Professional driving school in Stellenbosch offering car and motorcycle lessons.

WhatsApp Image 2026-07-02 at 18.30_edite

Qualified

Instructor

Professional Code 8 & Code 1 training

WhatsApp Image 2026-07-02 at 18.30_edite

Calm & Structured

Teaching 

Clear feedback without panic or pressure

WhatsApp Image 2026-07-02 at 18.30_edite

30+ Years on the Road

Real driving experience behind every lesson

WhatsApp Image 2026-07-02 at 18.30_edite

Above Average

Pass Rate

Focused preparation for test day

What does DME stand for?

DME stands for Driving Made Easy. It's the abbreviation you'll see on our learner vehicles around Stellenbosch and represents the same trusted driving school that has helped countless students pass their driving and motorcycle tests.

HOW DME (DRIVING MADE EASY) CAN HELP

Driving Made Easy (DME) learner vehicle in Stellenbosch
WhatsApp Image 2026-07-02 at 14.04_edite

CODE 8

CAR LESSONS

Structured Code 8 car lessons in Stellenbosch for learners who want calm instruction, clear feedback and proper test preparation.

ChatGPT Image Jun 29, 2026, 05_35_43 PM_edited.png
WhatsApp Image 2026-07-02 at 14.04_edite
file_00000000f5e482439b65cd8e45ea03df.png

CODE 1

MOTORCYCLE LESSONS

Yard-based Code 1 motorcycle training for beginners, rusty riders, scooter-to-bike learners and test preparation.

WhatsApp Image 2026-07-21 at 10.33.05.jpeg
WhatsApp Image 2026-07-02 at 14.04_edite

K53 TEST PREPARATION SUPPORT

 

K53 preparation support for approved learners, including observations, test routes, progress feedback and test readiness guidance.

WHY LEARNERS CHOOSE DME

Structured Progress

Every lesson is tracked with detailed progress reports so you always know where you stand

enquiry_first_clipboard_pencil_transparent.png
03_chat_bubble.png

Honest Feedback

You will know what to work on and what to improve.

WhatsApp Image 2026-06-19 at 06.46_edited.png

Real-World Training

Lessons are focused on real driving situations, safe habits and test preparation.

WhatsApp Image 2026-07-12 at 13.33_edited.png

Approved Test-Day Support

Test-day support is available once you are test-ready and confirmed.

heart_confidence_line.png

Safe & Patient Instruction

Calm, patient and professional instruction for all learners.

05_calendar_notes.png

Easy online booking

Approved learners can book lessons online quickly and easily.

WHAT OUR LEARNERS SAY

"Communication was very good and helped me stay calm to give confidence for my test."

Sebastian Oosthuizen (Code 8)

"Very calm and respectful. I started with no experience, and in no time could successfully pass my first test. Wouldn’t have been able to this without Oom Jacques!"

Luka Swanepoel (Code 8)

Instagram

"Great teacher and gives instructions clearly what you need to do, and what to avoid. Learned fast with his help!"

Roux Strauss (Code 1)

Instagram

WhatsApp Image 2026-07-02 at 11.23.27.jpeg

MEET YOUR INSTRUCTOR

JACQUES FOURIE

Qualified, experienced and patient driving instructor based in Stellenbosch.  Jacques focuses on calm, structured lessons, honest feedback and helping learners build safe habits that last beyond test day.

READY TO START YOUR

DRIVING JOURNEY?

Take the first step today.  I will guide you from your first lesson to test-day success.

bottom of page