Files
gw-svelte/mail-api/__pycache__/main.cpython-314.pyc
T

2526 lines
287 KiB
Plaintext
Raw Normal View History

2026-05-04 20:32:24 +12:00
+
2026-06-17 21:51:29 +12:00
&¢1jàAã"óøaEEt 0t^RIt^RIt^RIHt^RIHt^RIt^RIt^RI t ^RI
2026-05-04 20:32:24 +12:00
t
2026-05-19 23:36:58 +12:00
^RI t ^RI t ^RI
2026-06-17 21:51:29 +12:00
t
^RIHtHtHt^RIHt^RIHt^RIt^RIHtHtHt^RIHt^R IHt^R
IHtH t ^R I!H"t"H#t#H$t$H%t%^RI&t'^R I(H)t)^R
I*H+t,H-t-H.t.H/t/H0t0H1t1H2t2H3t3H4t4H5t5H6t6H7t8H9t9H:t:H;t;H<t<H=t>H?t?H@t@HAtAHBtBHCtCHDtEHFtFHGtGHHtHHItIHJtJHKtKHLtLHMtMHNtNHOtOHPtPHQtRHStSHTtTHUtU^RIVHWtWHXtXHYtYHZtZH[t[H\t\H]t]H^t^H_t_H`t`HataHbtbHctcHdtdHete]RRl4tf]!R]fR7tgRRlthRRltiRRltjRRltkRRltlRRltmRR ltnR!R"ltoR#R$ltpR%R&ltqR'R(ltrR)R*ltsR+R,lttR-R.ltuR/R0ltvR1R2ltwR3R4ltxR5R6lty]i!4sz]^k]J'd3]JPø!444/t~]^k/t]^k/t€]^k]k!4s]^k]m!4s]^k/tƒ]^k/t„]^k]EP
!4t†Rs‡]^k]o!4sˆ]^ kRs‰]^
k]EP
!4tŠ]UEP!R7]Œ!44R8R9ltR:R;ltŽR<R=ltR>R?ltR@RAltRBRCltRDRElt“RFRGlt”RHRIlt•RJRKltRLRMlt—!RNRO4t˜RPRQlt™]gEP5]˜]GRR7]gEP5]]!]T4RS7]gEP5]]!]94RTRU..ERìORVRWRX7]gEP9RY4RZR[l4tR\R]ltžR^R_ltŸ/t ]^ k/t¡]^ k]EP
!4t¢R`Ralt£RbRclt¤RdRelt¥RfRglt¦RhRilt§RjRklt¨RlRmlt©RnRoltªRpRqlt«RrRslt¬RtRult­RvRwlt®RxRylt¯RzR{lt°R|R}lt±R~Rlt²R€Rlt³Rlt´ERíR…R†lltµR‡Rˆlt¶R‰lt·Rlt¸Rlt¹RRltºRRlt»R“R”lt¼RVt½R•t¾RR—lt¿R˜R™ltÀRšRltÁRœRltÂRžltÃR ltÄR¢ltÅR¤ltÆR¦ltÇ]gEPR¨4l4tÉR«ltÊR­ltËR¯ltÌR±ltÍR³R´ltÎERîRµlltÏR·R¸ltÐERïR¹lltÑR»ltÒR½ltÓ]
E!R¿4tÕ]gEP­RÀ4l4t×]gEP­RÃ4l4tØ]gEPRÆ4l4tÙ]gEP­RÉ4l4tÚ]gEP­RÌ4l4tÛRÏ/RÐRÏbRÑRÒbRÓRÔbRÕRÖbR×RØbRÙRÚbRÛRÜbRÝRÞbRßRàbRáRâbRãRäbRåRæbRçRÜbRèRÚbRéRêbRëRÜbRìRàbRíRîRïRÚRðRÜRñR„RòR„RóRôRõRöR÷RøRùRúRûR„RüRýRþRÿ/ CER/RÐERbRÑERbRÓERbRÕERbR×ERbRÙERbRÛERbRÝERbRßERbRáER bRãER
bRåRæbRçER bRèERbRéER bRëER bRìER
bRíERRïERRðERRñERRòERRóERRõERR÷ERRùERRûERRüRýRþER/ CER/RÐERbRÑERbRÓERbRÕERbR×ERbRÙERbRÛERbRÝERbRßERbRáERbRãER bRåER!bRçER"bRèER#bRéER$bRëER%bRìERbRíER&RïERRðER#RñER'RòER(RóER)RõER*R÷ER+RùER,RûER-RüRýRþER./ CER//RÐER/bRÑER0bRÓER1bRÕER2bR×ER3bRÙER4bRÛER5bRÝER5bRßER6bRáER7bRãER8bRåER9bRçER:bRèER4bRéER;bRëER:bRìER4bRíER<RïER4RðER7RñER=RòER>RóER?RõER@R÷ERARùERBRûERCRüRýRþERD/ CERE/RÐEREbRÑERFbRÓERGbRÕERHbR×ERIbRÙRÚbRÛRÜbRÝERJbRßERKbRáRâbRãER
2026-05-19 23:36:58 +12:00
bRåRæbRçRÜbRèRÚbRéERLbRëRÜbRìRÚbRíERMRïRÚRðRÜRñERNRòERORóERPRõERQR÷ERRRùERSRûERTRüRýRþERU/ C/tÜ]^
kERVRÐERVRÑERWERXERYERZR„ER[ER\/ER]RÐER]RÑER^ERXER_ERZER`ER[ER_/ERaRÐERaRÑERbERXER\ERZERcER[ERd/EReRÐEReRÑERfERXERgERZERhER[ERg/ERiRÐERiRÑERjERXERkERZERlER[ERk/ERmRÐERmRÑERnERXERoERZERpER[ERo/ERqRÐERqRÑERrERXERsERZERtER[ERs/ERuRÐERuRÑERvERXERwERZERxER[ERw//tÝ]^kERyERzltÞER{ER|ltßER}ER~ltàERðERER€lltáERñERERlltâ]gEPERƒ4ER„ER…l4tã]gEP­ER†4ER‡ERˆl4tä]gEP­ER‰4EERl4tå]gEP­ERŒ4EREl4tæ]gEP­ER4ERERl4tç]gEPER4ER“ER”l4tè]gEPER•4ERER—l4té]gEP­ER˜4ER™El4tê]gEPER4EERl4të]gEPERž4EER l4tì]gEPER¡4EEl4tí]gEPER¤4EEl4tî]gEPER§4EEl4tï]gEP­ERª4EEl4tð]gEP­ER­4EEl4tñ]gEPER°4EEl4tò]gEPER³4ER´El4tóEEltôER¸EltõEEltöEElt÷EER¿ltøEEltù]gEP­ERÂ4EEl4túEEltû]gEPERÇ4EEl4tü]gEP­ERÊ4EEl4tý]gEP­ERÍ4EEl4tþ]gEP­ERÐ4EEl4tÿ]gEP­ERÓ4EEl4Et]gEP­ERÖ4ER×El4Et]gEP­ERÙ4EEl4Et]gEP­ERÜ4EEl4EtEElEtEElEtEElEt]gEP­ERå4EEl4Et]gEP­ERè4EEl4EtR#éN)Údeque)Úasynccontextmanager)ÚdatetimeÚ timedeltaÚtimezone)ÚPath)ÚAny)ÚFastAPIÚ
2026-06-17 21:51:29 +12:00
HTTPExceptionÚRequest)ÚCORSMiddleware)ÚTrustedHostMiddleware)Ú JSONResponseÚResponse)ÚASGIAppÚReceiveÚScopeÚSend)Úmyob)&ÚALLOWED_EMAILS_FILEÚ APP_VERSIONÚAUTH_CODE_MAX_ATTEMPTSÚAUTH_CODE_REQUESTS_PER_HOURÚAUTH_CODE_TTL_SECONDSÚAUTH_IP_BLOCK_DURATIONÚAUTH_IP_FAILURE_WINDOWÚAUTH_IP_MAX_FAILURESÚAUTH_SESSION_TTL_SECONDSÚBIRTHDAY_CHECK_INTERVAL_SECONDSÚ
2026-05-19 23:36:58 +12:00
CLIENT_BCCÚCLIENT_PROFILES_FILEÚCORS_ALLOWED_ORIGINSÚCP_ADMIN_EMAILSÚDEPLOY_SMOKE_SECRETÚDEV_MODEÚ DRAFTS_FILEÚEMAIL_SEND_TIMEOUT_SECONDSÚENABLE_GENERAL_ENQUIRIESÚFORM_MAX_SECONDSÚFORM_MIN_SECONDSÚ
2026-06-17 21:51:29 +12:00
FROM_EMAILÚLEGACY_SEED_FILEÚLOGO_URLÚMAX_REQUEST_BODY_BYTESÚMAX_SEND_ATTEMPTSÚ OWNER_BCCÚ OWNER_EMAILÚRATE_LIMIT_MAX_PER_EMAILÚRATE_LIMIT_MAX_PER_IPÚRATE_LIMIT_MIN_INTERVAL_SECONDSÚRATE_LIMIT_WINDOW_SECONDSÚREPLY_TOÚ SCHEDULED_CHECK_INTERVAL_SECONDSÚSCHEDULED_EMAILS_FILEÚSTARTUP_TEST_RECIPIENTÚ
2026-05-19 23:36:58 +12:00
TRUSTED_HOSTSÚlogger)ÚBaseSubmissionÚBirthdayAutoSendRequestÚBirthdayEmailRequestÚClientProfileUpdateÚBookingSubmissionÚClientStatusUpdateÚContractSubmissionÚNewClientRequestÚOnboardingSubmissionÚRenderMessageRequestÚResetOnboardingRequestÚScheduledEmailCancelRequestÚScheduledEmailRescheduleRequestÚSendMessageRequestÚWelcomePackEmailRequestcó$V^8„dQhR\/#)éÚapp)r
)Úformatsmain.pyÚ __annotate__rPUs÷ñcóš"\4GRjxL
R5x\4GRjxL
R#LL \4GRjxL
i;i5i©N)Ú_startup_mail_checkÚ_shutdown_background_tasks)rMs&rOÚ _lifespanrVTs<éä
2026-06-17 21:51:29 +12:00
Ó
2026-05-19 23:36:58 +12:00
×Ðð
ä ñ +øÔ*×*üs<A /A 3
A ¨1©A ±A ³AÁAÁAÁA zGoodWalk Mail API)ÚtitleÚlifespancó4V^8„dQhR\R\RR/#)rLÚpathÚpayloadÚreturnN)rÚobject)rNs"rOrPrPas!÷
ñ
2026-06-17 21:51:29 +12:00
œ$ð
¬ð
°Dñ
rQcóTVPPRRR7VPVPR,4pVP \
P !V^R7RR7\P!VR4\P!W 4R# \dL%i;i) zÊAtomically write a JSON file and chmod it owner-only (0600).
The chmod is best-effort: it is a no-op on Windows, but on the Linux
Docker host it ensures the file with PII is unreadable by other users.
T)ÚparentsÚexist_okz.tmp)Úindentúutf-8©Úencodingi€N) ÚparentÚmkdirÚ with_suffixÚsuffixÚ
2026-05-19 23:36:58 +12:00
write_textÚjsonÚdumpsÚosÚchmodÚOSErrorÚreplace)rZr[Útmps&& rOÚ_write_pii_jsonrqas„ð  ‡Kјd¨TÐÔ
×
Ñ
˜4Ÿ;™;¨Õ
0€C؇NN”4—:’:˜g¨aÔ0¸7€NÔ
Ü
Šô‡J‚JˆsÖøô ô
2026-06-17 21:51:29 +12:00
Ù ð
2026-05-19 23:36:58 +12:00
úsÁ*B B'Â&B'có:V^8„dQhR\\,/#©rLr\©ÚsetÚstr)rNs"rOrPrPqs÷ñ¬¬C­ñrQcó0\PPRR4PR4Uu0uF8qP 4'gKVP 4P 4kK: pp\ P!4'dT\P!\ P!RR74pVPRVPR.444V#uupi \d#p\P!RT4Rp?T#Rp?ii;i) ÚALLOWED_EMAILSÚÚ,rbrcc3ór"TF-p\V\4'gKVP4xK/ R#5irS©Ú
isinstancervÚlower©Ú.0Úes& rOÚ <genexpr>Ú1_load_allowed_emails_from_file.<locals>.<genexpr>vs'éÐXÑ+A aÄZÐPQÔSV×EWœ ˜ŸŸ ˜ Ó+Aùó7Ÿ7Úemailsz&Could not load allowed_emails file: %sN)rlÚenvironÚgetÚsplitÚstripr~Ú_ALLOWED_EMAILS_FILEÚexistsrjÚloadsÚ read_textÚupdateÚ Exceptionr;Úwarning)rÚseedÚdataÚexcs rOÚ_load_allowed_emails_from_filer”qÜ')§z¡z§~¡~Ð6FÈÓ'K×'QÑ'QÐRUÔ'VÓ dÑ'V !×ZaÑZa×ZcÔ ˆAG‰GIO‰OÖ Ñ'V€DÐ FÜ × &× —:2×<ÀgÔOˆ K‰KÑX¨4¯8©8°H¸bÔ+AÓ  €Kùò eøô
2026-06-17 21:51:29 +12:00
ôFÜŠÐ× €KûðFús$²C#Á"C#Á3A.C(Ã( DÃ3DÄDcó>V^8„dQhR\\,RR/#)rLr…r\Nrt)rNs"rOrPrP|s"÷FñF¤c¬#¥hðF°4ñFrQcóž\\R\V4/4R# \d#p\P
!RT4Rp?R#Rp?ii;i)r…z&Could not save allowed_emails file: %sN)rqÚsortedrr;r)r…r“s& rOÚ_save_allowed_emails_filer˜|s@ðFÜÔ,¨x¼À»Ð.HÖIøÜ ôFÜŠÐ×EûðFúsŸ A ªAÁA cóFV^8„dQhR\\\3,/#rs©Údictrv)rNs"rOrPrPƒs÷ñ¬¬c´4¨i­ñrQcóö\P!4'd,\P!\P!RR74#/# \
2026-05-19 23:36:58 +12:00
d#p\ P!RT4Rp?/#Rp?ii;i)rbrcz'Could not load client_profiles file: %sN)Ú_CLIENT_PROFILES_FILErrjrrr;r©r“s rOÚ_load_client_profiles_from_filerŸƒsiðGÜ × '× —:3×=ÀwÔ   €Iøô ôGÜŠÐ@À#×
€IûðGúóA *A Á A8ÁA3Á3A8có(V^8„dQhR\RR/#)rLÚprofilesr\r)rNs"rOrPrPŒs÷GñG¬ðG°$ñGrQcóˆ\\V4R# \d#p\P!RT4Rp?R#Rp?ii;i)z'Could not save client_profiles file: %sN)rqrrr;r)r“s& rOÚ_save_client_profiles_filer¥Œs7ðGÜÔ-¨xÖ8øÜ ôGÜŠÐ@À#×FûðGúó AŸ<¼Acó$V^8„dQhR\/#rs)rNs"rOrPrPs÷ñ¤ñrQcóö\P!4'd,\P!\P!RR74#/# \
d#p\ P!RT4Rp?/#Rp?ii;i)rbrczCould not load drafts file: %sN)Ú _DRAFTS_FILErrjrrr;rs rOÚ_load_drafts_from_filerªseð × Ò × Ò Ü—:’:œl×4¸gÔ   €Iøô ôŠÐ×
€Iûð>úr có(V^8„dQhR\RR/#)rLÚdraftsr\Nr£)rNs"rOrPrPœs÷>œdð> >rQcóˆ\\V4R# \d#p\P!RT4Rp?R#Rp?ii;i)zCould not save drafts file: %sN)rqrr;r)r“s& rOÚ_save_drafts_filer®œs3𜠠-øÜ ôŠÐ7¸×=ûð>úr¦cóFV^8„dQhR\\\3,/#rs)rNs"rOrPrP£s÷ñ¬$¬s´D¨y­/ñrQcó$\P!4'dD\P!\P!RR74p\ V\ 4'dV#/# \d#p\P!RT4Rp?/#Rp?ii;i)rbrcz(Could not load scheduled_emails file: %sN)
2026-06-17 21:51:29 +12:00
Ú_SCHEDULED_EMAILS_FILErrjrr}rrr;r)rr“s rOÚ _load_scheduled_emails_from_filer²£suðHÜ —:4×ÔQˆ˜$¤× ð €Iøô ôHÜŠÐAÀ3×
€IûðHúsA"AA"Á" BÁ-B
2026-05-18 22:25:43 +12:00
Â
Bcó(V^8„dQhR\RR/#)rLÚ scheduledr\Nr£)rNs"rOrPrP®s÷HñH¬4ðH°DñHrQcóˆ\\V4R# \d#p\P!RT4Rp?R#Rp?ii;i)z(Could not save scheduled_emails file: %sN)rqrr;r)r´r“s& rOÚ_save_scheduled_emails_filer¶®s7ðHÜÔ.° Ö:øÜ ôHÜŠÐAÀ3×GûðHúr¦cóV^8„dQhRR/#©rLr\)rNs"rOrPrPµs÷ Eñ E¨4ñ ErQcƒóh"\P!4p\P4UUu/uF wrVPR^4V8”gKWbK" ppp\P
!RV4GRjxL
R#uuppiL \ d#p\P!RT4Rp?R#Rp?ii;i5i)Persist live sessions to admin_kv so they survive container restarts.
Snapshot filters out expired entries before writing. Best-effort —
failure is logged but does not block the auth flow (memory remains
authoritative for the current process).
2026-05-19 23:36:58 +12:00
Ú
2026-05-18 22:25:43 +12:00
expires_atÚactive_sessionsNz%Could not persist active_sessions: %s) ÚtimeÚ_active_sessionsÚitemsr‡Úadmin_dbÚset_kvrr;r)ÚnowÚtokÚsnapshotr“s rOÚ_save_active_sessions_asyncrƵséô )Š)+€CÜ%5×%;Ñ%;Ô%=Ô^Ñ%=™6˜ÇÁÀ|ÐUVÓAWÐZ]ÑA]”Ñ%=€HÑEÜoŠoÐÓ:ùó_á:øÜ ôEÜŠÐ×DûðEüsR-B2¯A:ÁA:ÁB2ÁBÁ3BÁ4BÁ8B2ÂB B/Â
B*Â$B2Â*B/Â/B2cóFV^8„dQhR\\\3,/#rs)rNs"rOrPrPÄs÷ñ¬4´´T° ­?ñrQc ƒó@"\P!4'g/#\P!R4GRjxL
p\V\4'g/#\
P
!4pVP
4UUu/uF\wr#\V\4'gK\VPR4\\34'gKJVR,V8”gKZW#bK^ upp#Lªuuppi \d$p\P!RT4/uRp?#Rp?ii;i5i)Nr»z0Could not load active_sessions from admin_kv: %s)
Ú
is_enabledÚget_kvr}rr¿r‡ÚintÚfloatrr;r)rr“s rOÚ_load_active_sessions_asyncrÍÄéÜ × Ò × Ò Øˆ ð Ü—_’_Ð%6Óܘ$¤×ˆIÜiŠi‹kˆðŸ*™*œ,ô
2026-06-17 21:51:29 +12:00
á&ܘ!œT×
2026-05-18 22:25:43 +12:00
ä'1°!·%±%¸ Ó2EÌÌUÀ|×'Tô
2026-06-17 21:51:29 +12:00
àYZÐ[gÕYhÐknÑYnô
ˆCŠFÙ
ð
ñ 8ùó
øô
ôÜŠÐIÈ3Ô ûðüstD¡C-ºC%»C-ÁDÁ(C-Á?C'Â(C'à C'ÃC'Ã!C-Ã$DÃ%C-Ã'C-Ã- DÃ8DÄDÄDÄDÄDcó4V^8„dQhR\R\RR/#)rLÚkeyÚvaluer\rvr )rNs"rOrPrPÖs&÷gñg¤Cðg´ðg¸ñgrQcƒó°"\P!W4GRjxL
R#L \d#p\P!RY4Rp?R#Rp?ii;i5i)zHWrite a single admin_kv blob to postgres when the database is available.NzBPostgres persist (%s) failed; JSON copy is still authoritative: %s)rr;r)r“s&& rOÚ_persist_admin_staterÓÖsAéðgÜoŠo˜cÓ)øÜ ôgÜŠÐ[Ð]`×fûðgüs6A&$ž&¢A¤&¦ A±AÁAÁAÁAcóV^8„dQhRR/#r¸)rNs"rOrPrPÞs÷""?°Tñ"?rQc ƒóŠ"\PPRR4;'gRP4P 4pVR8XdR#\
P !4'gR#VR8Xd&\
P!4GRjxL
'dR#\4p\\44p\4pV'gV'g V'gR#V'd \
P!RV4GRjxL
V'd"\
P!RRV/4GRjxL
V'd \
P!RV4GRjxL
\P!R V\V4\V4\V44R#LLfLA \ d#p\P"!R
T4Rp?R#Rp?ii;i5i) a`Seed admin_kv from the JSON files on disk.
Controlled by ADMIN_DATA_SEED_FROM_JSON:
- "never": do nothing
- "auto": seed only when admin_kv has no rows yet (default, safe on every boot)
2026-05-19 23:36:58 +12:00
- "force": overwrite postgres with whatever the JSON files currently hold
The deployer exposes -SeedAdminData which sets this to "force" for one boot.
ÚADMIN_DATA_SEED_FROM_JSONÚautoÚneverNÚclient_profilesÚallowed_emailsr…zCSeeded admin_kv from JSON (mode=%s): clients=%d emails=%d drafts=%dzAdmin seed from JSON failed: %s)rlr†r‡r‰r~Ú
2026-06-17 21:51:29 +12:00
has_any_valuerŸr—r”r;ÚinfoÚlenrr)ÚmodeÚ seed_clientsÚ seed_emailsÚ seed_draftsr“s rOÚ%_seed_admin_state_from_json_if_neededrâÞsAéô
J‰JN‰NÐÓ ?× IÀ6× Z€DØ ˆw„ÙÜ × Ò × Ò Ùð 6Œ>¤H×$:Ò$:Ó$<× Ü8ˆ ÜÔ Ü ß§K¿ Ù ß Ü—/’/Ð"3°\ÓB× Ü—//Ð"2°X¸{Ð4KÓL× Ü—/’/ (¨KÓ  Š Ø ”##¤S¨Ó%5´s¸;Ó7Gö
ñ
Cá 8øô
ôŠÐ8¸#×>ûð?üs®A*GÁ-GÁ0FÂF Â FÂGÂ6FÃFÃGÃFÃ%FÃ?F
2026-05-18 22:25:43 +12:00
Ä FÄ FÄ(FÄ) FÄ5FÅFÅ9FÆ GÆ FÆ
FÆFÆFÆ GÆF;Æ5GÆ;GÇGcóV^8„dQhRR/#r¸)rNs"rOrPrPs÷=ñ=¨Tñ=rQcƒóÚ"\pVP4'gR#\P!VP RR74p\T\4'd T'gR#.p^pTP4wrV\T\4'd\T\4'gK3TP4P4pT'gK[T\P!4P48XdK…T\9d T^,
pKT\T&TP!T4 T'g$\ P"!RT\%T44R#\\4p\&P(!\*T4GRjxL
2026-06-17 21:51:29 +12:00
\-RT4GRjxL
2026-05-19 23:36:58 +12:00
\ P"!R \%T4T\%\44R# \
2026-05-18 22:25:43 +12:00
d#p\ P!RY4Rp?R#Rp?ii;iLz \
2026-05-19 23:36:58 +12:00
d"p\ P!RT4Rp?LŸRp?ii;iL \
d"p\ P!RT4Rp?L»Rp?ii;i5i)
2026-06-17 21:51:29 +12:00
aEMerge the shipped legacy-clients-seed.json into _client_profiles.
2026-05-19 23:36:58 +12:00
Add-only: never overwrites an email that already exists in the live data.
2026-06-17 21:51:29 +12:00
Idempotent: re-running on every boot is a no-op once the entries are in.
Writes the updated profiles back to the JSON file + admin_kv so the merged
2026-05-18 22:25:43 +12:00
state survives container restarts.
Nrbrcz$Legacy seed file unreadable (%s): %sz8Legacy seed already merged (existing=%d, candidates=%d).z5Could not save client_profiles after legacy merge: %srÙzDCould not persist client_profiles to postgres after legacy merge: %sz?Legacy seed merged: added=%d skipped_existing=%d total_after=%d)Ú_LEGACY_SEED_FILErrjrrr;rr}rr¿rvr‰r~r1Ú_client_profilesÚappendrÜÚasyncioÚ to_threadr¥) Ú seed_pathrr“ÚaddedÚskipped_existingÚ raw_emailÚprofileÚemailrÅs rOÚ_merge_legacy_seed_if_presentrðéô"€IØ × Ñ × Ò ÙðÜzŠz˜)×-°wÐô
dœD× Ùà€EØÐà"Ÿj™jžlш ܘ)¤S׸GÄT×1JÒ1JÙ ØÓ!×)ˆßÙ Ø ”K× Ø Ô  Õ Ù Ø")Ô˜ÑØ
ñ Ü Š Ø œc $›iô
ñ äÔ%€HðUÜ×ÒÔ :¸HÓE×dÜ"Ð#4°hÓ?× ‡K‚KØ ˆE‹
2026-05-18 22:25:43 +12:00
Ð$¤cÔ*:Ó&;öøôS ôÜŠÐ=¸yÔûðúñB FøÜ ôUÜŠÐNÐPS×TûðUúñ @øÜ ôdÜŠÐ]Ð_b×cûðdüs´I+¢&GÁI+Á&A.I+ÃA'I+Ä=2I+Å0H ÆH ÆH ÆH<Æ#H:Æ$H<Æ(1I+Ç HÇ$HÇ;I+ÈHÈI+È H È H7ÈH2È-I+È2H7È7I+È:H<È< I(ÉI#ÉI+É#I(É(I+có:V^8„dQhR\\,/#rsrt)rNs"rOrPrPCs÷  ,¬#¬c­ ,rQcƒó0"\P!4'\P!R4GRjxL
2026-06-17 21:51:29 +12:00
p\V\4'd´VP R.4p\V\ 4'\PP RR4PR4Uu0uF8q"P4'gKVP4P4kK: ppVPRV44V#\4#L×uupi5i)Nr…rxryrzc3ór"TF-p\V\4'gKVP4xK/ R#5irSr|rs& rOrÚ-_load_allowed_emails_async.<locals>.<genexpr>Js#éÐL©v¨!¼ÀAÄs×9KœI˜AŸG™GŸI˜I«vùr„)r}rr‡Úlistrlr†rˆr‰r~r”)rr…rrs rOÚ_load_allowed_emails_asyncröCéÜ×Ò×ÒÜ—_’_Ð%5ÓÜ dœD× —X‘X˜Ó+ˆ˜&¤$×'Ü35·:±:·>±>ÐBRÐTVÓ3W×3]Ñ3]Ð^aÔ3bÓpÑ3b¨a×fmÑfm×foÔŸ› ŸÖ)Ñ3bÐ ÑL©vÓ Ü 7ùòqùs(5D·D¸A3DÂ+DÃ"DÃ)'DÄDcóFV^8„dQhR\\\3,/#rs)rNs"rOrPrPOs÷-¬4´´­-rQcƒóÄ"\P!4'd7\P!R4GRjxL
2026-05-18 22:25:43 +12:00
p\V\4'dV#\ 4#L&5i)N)r}r©rs rOÚ_load_client_profiles_asyncrúOsFéÜ×Ò×ÒÜ—_’_Ð%6ÓÜ dœD× ˆKÜ 8ùó5A ·A¸'A có$V^8„dQhR\/#rs)rNs"rOrPrPWs÷$¤$ñ$rQcƒóÄ"\P!4'd7\P!R4GRjxL
p\V\4'dV#\ 4#L&5i)N)r}rs rOÚ_load_drafts_asyncrþWsEéÜ×Ò×ÒÜ—_’_ XÓÜ dœD× ˆKÜ /ùrûcóFV^8„dQhR\\\3,/#rs)rNs"rOrPrP_s÷.¬D´´­.rQcƒóÄ"\P!4'd7\P!R4GRjxL
p\V\4'dV#\ 4#L&5i)Úscheduled_emailsN)r}rs rOÚ_load_scheduled_emails_asyncr_sFéÜ×Ò×ÒÜ—_’_Ð%7ÓÜ dœD× ˆKÜ 9ùrûz Auth: loaded %d allowed email(s)có0V^8„dQhR\R\/#©rLÚrequestr\©r rv)rNs"rOrPrP}s÷ ñ ¬'ð ´ rQcƒó,"VPPRR4pVPR4P4pV'g\ RRR7h\
;_uu_4GRjxL
\ PV4pV'g\ RRR7h\P!4VR,8”d$\ PVR4\ RR R7hVR
,uuRRR4GRjxL
#LL +GRjxL
'giR#;i5i) Ú
2026-06-17 21:51:29 +12:00
AuthorizationryúBearer izNo token provided.©Ú status_codeÚdetailNzInvalid session.r»z&Session expired. Please sign in again.rï) Úheadersr‡Ú removeprefixr‰r Ú
_auth_lockr¾Úpop)rÚ auth_headerÚtokenÚsessions& rOÚ_require_session_emailr}騗/‘/×% o°rÓ:€KØ × $ YÓ 7€Eç ܨÐ4HÔzŽzÜ"×& -ˆßܨCÐ8JÔ 9Š9‹;˜ Õ × Ñ  ¨Ô ¨CÐ8`Ô ÷zzzzzˆzüsOA#DÁ%C3Á&DÁ)A7C7Ã
DÃ-C5Ã.DÃ5DÃ7D Ã=DÃ>
D Ä D Ä Dcó0V^8„dQhR\R\/#rr)rNs"rOrPrPŽs÷ñ¬ð´CñrQcƒóh"\V4GRjxL
pV\9d\RRR7hV#L5i)Né“zOwner access required.r
)rr#r )rs& rOÚ_require_owner_emailrŽs2éÜÓ 1€EØ ”OÔ¨Ð4LÔ €Lñ
2ùs 202có(V^8„dQhR\RR/#)rLr\rv)rNs"rOrPrPs÷
Nñ
N¤ð
N¨ñ
NrQcƒó"VP4P4pV'gR#\;_uu_4GRjxL
V\9d\P V4\ \4p\ P!\\\44GRjxL
\RRV/4GRjxL
\P!RV4RRR4GRjxL
R#LEL1L +GRjxL
'giR#;i5i)NrÚr…z&Auth: registered new allowed email: %s)
r‰r~rÚ_allowed_emailsÚaddr—r˜rur;)Ú
normalizedrÅs& rOÚ_register_emailréØ×&€Jß ÙßzŽzØ œ_Ô × Ñ  
Ô œoÓ.ˆHÜ×#Ô$=¼sÄ?Ó?SÓT× &Ð'7¸(ÀHÐ9MÓN× KŠKÐ@À*Ô
z
UÙ zzzüsp;D½C ¾DÁAC(ÂC"ÂC(Â2C$Â3C(Ã DÃC&ÃDÃ"C(Ã$C(Ã&DÃ(D Ã.C1Ã/
D Ã:D Ã< Dcó0V^8„dQhR\R\/#)rLr\)rÚbool)rNs"rOrPrP¢s÷DñD¤$ðD¬4ñDrQcó|VPR4p\V\4'gR#VPR4R9#)z—True if outreach (welcome pack, birthday email, etc.) should still target
this client. Excludes lifecycle states that mean the relationship has ended.
Ú lifecycleTÚstatus>ÚarchivedÚ cancelled)r‡r}r)r#s& rOÚ_client_is_reachabler'¢s7ð ˜KÓ(€IÜ × Ø =‰=˜Ó "Ð*CÑ CrQcó4V^8„dQhR\R\RR/#)rLr\rvr)rNs"rOrPrP¬s&÷DñD¤sðD´D¸DrQc
ƒóp"VP4P4pV'gR#\;_uu_4GRjxL
\P V/4p/VCVCP 4UUu/uF,wrEVfK \
V\4'd
VR8XdK*WEbK. pppWc8wdPV\V&\\4p\P!\V4GRjxL
\RV4GRjxL
RRR4GRjxL
R#LÍuuppiL2L L +GRjxL
'giR#;i5i)Nry)
r‰r~rr‡r¿r}rvr)rÚexistingÚmergedrÅs&& rOÚ_store_client_profiler/¬éØ×&€Jß ÙßzŽzÜ#×
°BÓð0˜8Ð/ wÐ
á7Øô
ä&0°´C×&8Ò&8¸QÀ"¹Wô
ˆAŠDÙ ñ
ð
Ô Ø+1Ô ˜ZÑ Ô-ˆHÜ×#Ô$>ÀÓI× &Ð'8¸C× zzùó
ñ
JÙ zzzüs‡;D6½D ¾D6Á.DÁ/D
Á<D
ÂD
Â!?DÃ DÃ!DÃ4DÃ5DÃ9 D6ÄDÄD6Ä
DÄDÄD6ÄD3 ÄD"Ä
D3 Ä+D3 Ä- D6cóV^8„dQhRR/#r¸)rNs"rOrPrP¾s÷ñ=rQcƒó¢"\\4p\P!\V4GRjxL
\ RV4GRjxL
R#LL5i)zˆWrite the scheduled-email queue to the JSON file + postgres. Callers
must hold _scheduled_lock so the snapshot is internally consistent.Nr)rÚ_scheduled_emailsrè)s rOÚ_persist_scheduled_emailsr3¾sCéôÔ&€HÜ
×
Ò
Ô7¸Ó
B×
Ð1°8Ó
<×CÙ<ùs!.A°A ±AÁA
ÁAÁ
Acó0V^8„dQhR\R\/#©rLr\©rvr)rNs"rOrPrPÆs÷ñ¤Cð¬HñrQcó&T;'gRP4pV'g\RRR7h\P!V4pTP
e!TP
4PRR7pT# \d\RRR7hi;i)zîParse an ISO 8601 datetime from the owner UI (datetime-local sends
'YYYY-MM-DDTHH:MM'). Returns a naive local datetime to match the rest of
the app, which compares against datetime.now(). Raises HTTPException(400)
on anything unparseable.ryéz4Please choose a date and time to schedule the email.r
z+That schedule time could not be understood.N©Útzinfo)r‰r rÚ
fromisoformatÚ
ValueErrorr:Ú
astimezonero©ÚrawÚparseds& rOÚ_parse_schedule_datetimerAÆsð
;ˆ;B×
Ñ
Ó
€Cß Ü¨Ð4jÔcÜ×Ó,ˆð‡} Ø×$×,°DÐØ €Møô ôcܨÐ4aÔcús ±A7Á7Bc
óŒV^8„dQhR\R\R\\\3,R\\\3,/#)rLÚ
next_emailÚprofile_updatesr\©rvrr )rNs"rOrPrPØs@÷?ñ?Ü ð?äð?ôœ#œs˜(•^ð?ô
Œ#Œsˆ(…^ñ ?rQc
ƒóN"VP4P4pVP4P4pV'd V'g\RRR7h\;_uu_4GRjxL
\P V4p\
V\4'g\RRR7h\P V4pWC8wd$\
V\4'd\RRR7h/VCVCP4UUu/uF,wrxVfK \
V\4'd
VR8XdK*WxbK. p ppWC8wEd+\PVR4V \V&\PVR4p
V
e
V
\V&\PVR4p V e
V \V&\PVR4p V e
V \V&\P4F7p
\
V
\4'gKV
P R 4V8XgK3WMR &K9 V\ P!4P48wd\"P%V4\"P'V4M V \V&\\4p\\4p\)\"4pRRR4GRjxL
\*P,!\.X4GRjxL
\*P,!\0X4GRjxL
\*P,!\2\5X44GRjxL
\7R
V4GRjxL
\7R V4GRjxL
\7R R
V/4GRjxL
2026-06-17 21:51:29 +12:00
\94GRjxL
X #ELuuppi+GRjxL
'giLè;iLLoL]LIL95i)r8úA valid email is required.r
2026-06-17 21:51:29 +12:00
Né”úClient not found.é™z/Another client already uses that email address.ryr…)r‰r~r rr‡r}rr¿rvrÚ_draftsÚ_pending_codesÚ_code_requestsr¾Úvaluesr1rÚdiscardrr—r˜ru)rCrDrÚnext_normalizedr+Útarget_existingr,r-r.ÚdraftÚpendingÚ
code_requestsrÚprofiles_snapshotÚdrafts_snapshotÚallowed_emails_snapshots&&& rOÚ_update_client_profilerXØéð
×&€JØ ×(×0€Oß Ÿ_ܨÐ4PÔzŽzÜ#×
Óܘ(¤DרCÐ8KÔ ÓØ Ô (¬Z¸Ì×-NÒ-NܨCÐ8iÔ 8˜8Ð7 Ð7×
á?Øô
ä&0°´C×&8Ò&8¸QÀ"¹Wô
2026-06-17 21:51:29 +12:00
ˆAŠDÙ ñ
ð Õ × Ñ  ¨TÔ 2Ø06Ô ˜_Ñ —KK 
2026-06-17 21:51:29 +12:00
¨DÓ1ˆEØÒ Ø+0”˜Ñ°TÓ:ˆGØÒ"Ø29”˜Ñ*×.¨z¸4Ó@ˆMØÒ(Ø2?”˜Ñ4ܘg¤t×·±¸WÓ1EÈÖ1SØ'6˜œ[×0××
Ô × Ñ  Õ 0à+1Ô ˜ZÑ  Ô!1ÓÜœw-ˆÜ"(¬Ó"9Ð÷WzôZ ×
Ò
Ô6Ð8IÓ
J×
2026-05-19 23:36:58 +12:00
×
Ò
2026-06-17 21:51:29 +12:00
ÔÓ
2026-05-19 23:36:58 +12:00
?×
×
Ò
Ô5´sÐ;RÓ7SÓ
2026-06-17 21:51:29 +12:00
T×
2026-05-19 23:36:58 +12:00
Ð0Ð2CÓ
D×
˜Ó
9×
Ð/°(Ð<SÐ1TÓ
U×
2026-06-17 21:51:29 +12:00
'× €Mòkùó
÷zzŠzúñZKÙ'ùsùA N%ÁN%Á.M0Á/N%Á2BM;ÄM3
Ä
2026-05-19 23:36:58 +12:00
M3
Ä,M3
2026-06-17 21:51:29 +12:00
Ä2B<M;Ç3M;È BM;Ê N%Ê'M9Ê("N%Ë
NË "N%Ë-NË.+N%ÌNÌN%Ì-NÌ.N%ÍNÍN%ÍN!ÍN%Í)N#Í*N%Í3M;Í9N%Í;N ÎNÎ
2026-05-19 23:36:58 +12:00
N Î
N Î N%ÎN%ÎN%ÎN%ÎN%Î!N%Î#N%cóRV^8„dQhR\R\\\3,/#)rLr\rE)rNs"rOrPrPs"÷"ñ"¬#ð"´$´s¼C°xµ.ñ"rQcƒóú"VP4P4pV'g\RRR7h\;_uu_4GRjxL
2026-06-17 21:51:29 +12:00
\P V4p\
2026-05-19 23:36:58 +12:00
V\4'g\RRR7h\V4pRVR&VPR R
4pVPR R4pV'dWCR &VeWSR
2026-06-17 21:51:29 +12:00
&\P!4PRR7VR&V\V&\\4pRRR4GRjxL
2026-05-04 20:32:24 +12:00
\P!\X4GRjxL
\RV4GRjxL
X#ELL@ +GRjxL
2026-05-19 23:36:58 +12:00
'giLW;iL;L)5i)a]Mark a client's onboarding as incomplete while keeping every saved detail.
2026-05-04 20:32:24 +12:00
2026-06-17 21:51:29 +12:00
Used for clients imported from the legacy Gravity Forms data: they keep their
contact/dog details (and their previous submission is archived for reference),
2026-05-19 23:36:58 +12:00
but they drop back into the pending list so they can sign in with their email
and complete the new onboarding form.
2026-06-17 21:51:29 +12:00
r8rGr
NrHrIonboardingCompletedÚonboardingSubmittedAtryÚonboardingSubmissionÚpreviousOnboardingSubmittedAtÚpreviousOnboardingSubmissionÚseconds©ÚtimespecÚonboardingResetAtrÙ)r‰r~r rr‡r}rrrÚ isoformatrè)rr+ÚupdatedÚprevious_submittedÚprevious_submissionrÅs& rOÚ_reset_client_onboardingrhs3éð×&€Jß Ü¨Ð4PÔzŽzÜ#×
Óܘ(¤DרCÐ8KÔ x“.ˆØ).ˆÐ%Ÿ[™[Ð)@À"ÓØ%Ÿk™kÐ*@À$Óß Ø7IÐ Ò *Ø6IÐ 3Ü'/§|¢|£~×'?Ñ'?ÈÐ'?Ó'SˆÐ$à'.Ô˜ÑÔ÷%zô( ×
Ò
Ô6¸Ó
A×
Ð0°(Ó
;× €N÷-zzzúñ(BÙ;ùsmAE;ÁEÁ E;Á CEÄ
E;ÄEÄ"E;Ä;E7Ä<E;ÅE9ÅE;ÅE;ÅE4 Å!E$Å"
2026-05-04 20:32:24 +12:00
E4 Å-E4 Å/ E;Å9E;có4V^8„dQhR\R\RR/#)rLÚipÚ
2026-06-17 21:51:29 +12:00
request_idr\Nr)rNs"rOrPrP?s!÷
2026-05-19 23:36:58 +12:00

2026-05-04 20:32:24 +12:00
!œ#ð
2026-05-19 23:36:58 +12:00
!¬3ð
2026-05-04 20:32:24 +12:00
!°4ñ
2026-05-19 23:36:58 +12:00
!rQcó(\P!4p\PV4pVedW#8dU\ W2,
4p\
2026-05-04 20:32:24 +12:00
P !RWV4\RRV^<,^, R2R\V4/R7h\VR#R#)Nz([%s] auth: blocked ip=%s (%ds remaining)é­z'Too many failed attempts. Try again in z minute(s).z Retry-After)r r r
2026-05-19 23:36:58 +12:00
) r½Ú monotonicÚ _blocked_ipsr‡r;rr rv)rjrkÚ
unblock_atÚ remainings&& rOÚ_check_ip_blockedrr?Ü
2026-06-17 21:51:29 +12:00
.Š.Ó
€CÜ×! %€JØÒØ Ô Ü˜JÕ-ˆIÜ NŠNÐEÀzÐW`Ô ØØÈbÅÐSTÕATÐ@UÐU`ШI«Ðð
2026-05-04 20:32:24 +12:00
ô ˜RÒ ñrQcó@V^8„dQhR\R\R\RR/#)rLrjrkÚreasonr\Nr)rNs"rOrPrPOs(÷ 
2026-05-19 23:36:58 +12:00
ñ 
œSð 
¬cð 
¼3ð 
2026-06-17 21:51:29 +12:00
À4ñ 
2026-05-04 20:32:24 +12:00
rQc óÖ\P!4p\PV\ 44pV'd+W4^,,
\
8”dVP
4K2VPV4\P!RWV\V44\V4\d=V\,\V&\P!RW\\V44R#R#)rz5[%s] auth: failure ip=%s reason=%r total_in_window=%dz2[%s] auth: ip=%s BLOCKED for %ds after %d failuresN)rnÚ_auth_failures_by_ipÚ
2026-06-17 21:51:29 +12:00
setdefaultrrÚpopleftrçr;rrrro)rjrkrtÚfailuress&&& rOÚ_record_auth_failurerzOÜ
2026-05-04 20:32:24 +12:00
.Š.Ó
2026-05-19 23:36:58 +12:00
€CÜ.¨r´5³7Ó;€Hß
s a(Ô+AÔ×ÑÖØ ‡OOÜ
2026-06-17 21:51:29 +12:00
‡NJÈJÐ\bÔdgÐhpÓdqÔ
ˆ8ƒ}ÔÔ!7Õ ÜŠØ Ô2´C¸³Mö
2026-05-04 20:32:24 +12:00
ñ-rQcóHa]tRtRtoRtV3RlRltV3RlRltRtVtR#) Ú_BodySizeLimitMiddlewarei^zûReject requests whose Content-Length exceeds MAX_REQUEST_BODY_BYTES.
2026-05-19 23:36:58 +12:00
Defence-in-depth alongside nginx ``client_max_body_size``. Streaming
2026-05-04 20:32:24 +12:00
requests without a Content-Length header are tracked byte-by-byte and
short-circuited if they overflow the cap.
có*<V^8„dQhRS[RS[RR/#)rLrMÚ max_bytesr\N)r)rNÚ
2026-05-19 23:36:58 +12:00
__classdict__s"€rOrPÚ%_BodySizeLimitMiddleware.__annotate__fs"ø€÷#™Gðð#¸ñ#rQcóWnW nR#rS©rMr~)ÚselfrMr~s&&&rOÚ__init__Ú!_BodySizeLimitMiddleware.__init__fs ØŒØrQcó0<V^8„dQhRS[RS[RS[RR/#)rLÚscopeÚreceiveÚsendr\N)rrr)rNrs"€rOrPr€js)ø€÷6¡Eð6±Gð6Á4ð6ÈDñ6rQcƒóbaaa a
2026-05-04 20:32:24 +12:00
"VR,R8wdSPVSV4GRjxL
R#VPR.4UUu/uF4wrEVPR4P4VPR4bK6 pppVPR4pVe2\ V4SP
2026-06-17 21:51:29 +12:00
8”d\
V4GRjxL
R#^o
Ro V VV
V3RlpS 'd\
2026-06-17 21:51:29 +12:00
V4GRjxL
R#SPWV4GRjxL
R#LäuuppiLU \dL]i;iL=L#5i)ÚtypeÚhttpNr
2026-05-04 20:32:24 +12:00
zlatin-1zcontent-lengthFcóÀ<"S!4GRjxL
pVR,R8Xd:S\VPRR44,
oSSP8”dRoRR/#V#LM5i)Nrz http.requestÚbodyrQTzhttp.disconnect)r‡r~)ÚmessageÚ
2026-05-19 23:36:58 +12:00
overflowedrˆÚreceivedrƒs €€€€rOÚ_wrapped_receiveÚ;_BodySizeLimitMiddleware.__call__.<locals>._wrapped_receive|s\øéá#I—oˆGØv .ÔœC § ¡ ¨F°CÓ 8Ó9ؘdŸn™nÔ,Ø!%"Ð$5Ј
2026-05-04 20:32:24 +12:00
&ùsƒ AŽAAA)rMr‡Údecoder~r~Ú _send_413r<) r‡rˆr‰r,r-r
Údeclaredrrrs f&f& @@rOÚ__call__Ú!_BodySizeLimitMiddleware.__call__jsûéØ =˜ —((˜5 '¨4Ó0× àPU×PYÑPYÐZcÐegÔPhÔiÑPhÉÈ1—88˜&×·±¸Ó0CÒCÑPhˆÑ—;‘;ÐØ Ò ð
2026-05-19 23:36:58 +12:00
Üx“= 4§>¡>Ô# D/×ð ˆØˆ
2026-05-04 20:32:24 +12:00
÷ ð ÷ ܘD“/× Øh‰hÓ5ñ;
1ùójñ
2026-05-19 23:36:58 +12:00
*øäô
2026-05-04 20:32:24 +12:00
Ùð
úñ"
2026-05-19 23:36:58 +12:00
5ùs{†%D/«D¬D/Á:DÂD/Â(DÃDÃDÃD/ÃD/Ã-D+Ã.D/Ä D-Ä
2026-05-04 20:32:24 +12:00
D/ÄD/ÄDÄ D(Ä%D/Ä'D(Ä(D/Ä-D/rN) Ú__name__Ú
2026-06-17 21:51:29 +12:00
__module__Ú __qualname__Ú__firstlineno__Ú__doc__r„r—Ú__static_attributes__Ú__classdictcell__)rs@rOr|r|^sø‡ñ÷6rQr|có(V^8„dQhR\RR/#)rLr‰r\N)r)rNs"rOrPrPŒs÷ ñ œ$ð   rQcƒól"V!RRRRRR ./4GRjxL
V!RRRR/4GRjxL
R#LL5i)
rzhttp.response.startr$ir
2026-06-17 21:51:29 +12:00
Nzhttp.response.bodyrŽs${"detail":"Request body too large."})s content-typesapplication/jsonr¹)r‰s&rOr•r•Œs_éÙ
ØÐÐó ÷ðñ
ØÐÐó ÷òñ ñ
2026-06-17 21:51:29 +12:00
ùs404©2ª4²4)r~)Ú
2026-05-19 23:36:58 +12:00
allowed_hostsÚPOSTÚGETFiX)Ú
2026-06-17 21:51:29 +12:00
allow_originsÚ
allow_methodsÚ
allow_headersÚallow_credentialsÚmax_agerŒcó$V^8„dQhR\/#©rLr©r )rNs"rOrPrP¥s÷ñ¬wñrQcƒó„"\P!4PR,pW Pn\
P !4pV!V4GRjxL
p\
2026-05-19 23:36:58 +12:00
P !4T,
2026-06-17 21:51:29 +12:00
R,p\P!RY PTPPTPT4Y$PR&T#Ly \d]\
P !4T,
2026-06-17 21:51:29 +12:00
R,p\P!RY PTPPT4hi;i5i)ºNéNNéèz[%s] %s %s crashed after %.0fmsu[%s] %s %s → %d (%.0fms)z X-Request-ID)ÚuuidÚuuid4ÚhexÚstaterkrnrr;Ú exceptionÚmethodÚurlrZr r
)rÚ call_nextrkÚstartedÚresponseÚ
elapsed_mss&& rOÚ_request_logging_middlewarer¼¤éä×! "Õ%€JØ)‡MÜnŠnÓ€GðÙ" +×+ˆô—." Õ4€JÜ
‡K‚KØ—NN G§K¡K×$4Ñ$4°h×6JÑ6JÈJôð(2×Ñ €Oñ,øÜ ôÜ—n’nÓÕ0°DÕ8ˆ
2026-05-04 20:32:24 +12:00
Ü×ÒØ Ÿ¨¯ © ×(8Ñ(8¸*ô
ð ð
üs2A EÁ CÁCÁCÁA5EÃCÃA'D=Ä=Ecó0V^8„dQhR\R\/#rr)rNs"rOrPrP½s÷@ñ@”Wð@¤ñ@rQcóèVPPR4pV'd'VPR4^,P4#VP'dVPP
2026-06-17 21:51:29 +12:00
#R#)zx-forwarded-forrzÚunknown)r
r‡rˆr‰ÚclientÚhost)rÚ forwardeds& rOÚ_get_iprýsTØ×#Ð$5Ó6€Iߨ˜# &×.Ø")§.§. .ˆ7>‰>× Ñ Ð?°iÐ?rQcó0V^8„dQhR\R\/#r)r r!)rNs"rOrPrPÄs÷ Bñ Bœgð B¬$ñ BrQcó²\'gR#VPPR4;'gRpV'gR#\P!V\4#)zûTrue when the request carries a matching X-Deploy-Smoke header.
2026-05-04 20:32:24 +12:00
Used by the deploy script to verify the form endpoints are reachable and
parse a valid payload, without producing a real submission. Disabled
entirely when DEPLOY_SMOKE_SECRET is unset.
Fzx-deploy-smokery)r$r
r‡ÚsecretsÚcompare_digest)rÚ presenteds& rOÚ_is_deploy_smokerÉÄsD÷ Ó ÙØ×#Ð$4Ó€Iß ÙÜ × ! )Ô-@Ó ArQcó0V^8„dQhR\R\/#r5r)rNs"rOrPrPØs÷ñ”CðœCñrQcó"VP4#rS©r‰©s&rOÚ_trimmedrÎØsØ ;‰;rQcóVV^8„dQhR\\,R\R\RR/#)rLÚattemptsrÂÚwindow_secondsr\N)r)rNs"rOrPrPÜs-÷ñœe¤E´ðÌðÐPTñrQcófV'd)W^,,
V8”dVP4K.R#R#)rN)rx)s&&&rOÚ_prune_attemptsrÓÜs&ß
s a(¨>Ô×ÑÖñ:‰(rQcóHV^8„dQhR\R\R\R\/#)rLÚlast_attempt_atrÂÚmin_interval_secondsr\))rNs"rOrPrPás*÷ñ¬Eð¼ðÔUXðÔ]`ñrQcóJ\^\W!V,
2026-06-17 21:51:29 +12:00
,
44pV#)é)ÚmaxrË)Ú retry_afters&&& rOÚ_seconds_until_allowedrÛás"ÜÐ1¸?Õ5JÕM€KØ ÐrQcó@V^8„dQhR\R\R\RR/#)rLrkrjr\Nr)rNs"rOrPrPæs(÷44#´4#¼3ð4#Äsð4#Ètñ4#rQc
2026-05-04 20:32:24 +12:00
ƒóö"\P!4pVP4P4p\;_uu_4GRjxL
\
P
V\44p\P
V\44p\WS\4\Wc\4V'dmW5R
,,
2026-06-17 21:51:29 +12:00
\8dU\VR
,V\4p\P!RVVW5R
,,
\4\RRV R2R7h\!V4\"d0\P!RVV\"\4\RRR7h\!V4\$d0\P!RVV\$\4\RR R7hVP'V4VP'V4RRR4GRjxL
R#ELL +GRjxL
2026-05-04 20:32:24 +12:00
'giR#;i5i) NzB[%s] rate limited: ip=%s submitted again after %.1fs (minimum %ss)rmzPlease wait about z seconds before trying again.r
z7[%s] rate limited: ip=%s exceeded %d submissions in %sszIToo many enquiries from this connection. Please try again a little later.z:[%s] rate limited: email=%s exceeded %d submissions in %sszQThat email address has reached the enquiry limit for now. Please try again later.éÿÿÿÿ)rnr‰r~Ú_submit_rate_limit_lockÚ_submit_attempts_by_iprwrÚ_submit_attempts_by_emailrÓr5r4r;rr r3r2)rkrjÚnormalized_emailÚ ip_attemptsÚemail_attemptsrÚs&&& rOÚ_enforce_submit_rate_limitsråæéÜ
.Š.Ó
€CØ—{‘{“}×ç&×,×7¸¼E»GÓDˆ Ü2×=Ð>NÔPUÓPWÓXˆä˜ Ô*CÔ˜Ô-FÔ ˜3¨R¥Õ0Ô3RÔ¸RµÀ#ÔGfÓgˆKÜ NŠNØØØ "•oÕ 
ô ØØ+¨K¨=Ð8UÐð
ô
2026-05-18 22:25:43 +12:00
ˆ{Ó Ô NŠNØØÜ 
2026-05-04 20:32:24 +12:00
ô ØØð
ô
2026-06-17 21:51:29 +12:00
ˆ Ô":Ô NŠNØØ Ü 
ô ØØð
2026-05-04 20:32:24 +12:00
ð
×ј3ÔØ×ј"÷a'×&×&×&×&×&üsOAG9ÁGÁ G9Á E9GÇ G9ÇGÇG9ÇG9ÇG6 Ç"G%Ç#
G6 Ç.G6 Ç0 G9có4V^8„dQhR\R\RR/#©rLrkrr\N)rvr<)rNs"rOrPrPs!÷ 
ñ 
¤Sð 
´ð 
À4ñ 
rQcóÈVPeVP^8:d%\P!RV4\RRR7h\P!4R,VP,
R, pV\
8d+\P!RVV\
4\RRR7hV\ 8”d+\P!RVV\ 4\RR R7hR#)
Nz/[%s] rejected: missing or invalid formStartedAtr8z&Please refresh the page and try again.r
z7[%s] rejected: form submitted too quickly (%.2fs < %ss)z;Please take a moment to fill in the form before sending it.z2[%s] rejected: stale form submission (%.0fs > %ss)zLThis form has been open for too long. Please refresh the page and try again.)Ú
formStartedAtr;rr r*r))rkrÚelapsed_secondss&& rOÚ_enforce_form_timingrëØ ×ÑÒ! T×%7Ñ%7¸1Ô%<ÜŠÐHÈ*ÔØØ
ð
ô
—yy“{ )¨D×,>Ñ,>Õ>À$ÕF€OàÔŠØ Ø Ü ô 
2026-06-17 21:51:29 +12:00
ô ØØ
2026-05-04 20:32:24 +12:00
ð
ð
ÔŠØ Ø Ü ô 
ô ØØ
ð
ñ*rQcó0V^8„dQhR\R\/#©rLrr\)r<r!)rNs"rOrPrP@s÷ð(´(rQcó>\\VP44#rS)r!Úwebsiterùs&rOÚ_is_honeypot_triggeredrð@sÜ ˜ŸÓ 'rQcó0V^8„dQhR\R\/#)r@r!)rNs"rOrPrPDs÷;´;rQcóN\VP4P4R8H#)Úgeneral)Ú enquiryTyper~s&rOÚ_is_general_enquiryrõDs!Ü  %× Ñ :rQcó0V^8„dQhR\R\/#©r@rv)rNs"rOrPrPHs÷QñQÔQ´QrQcó,\V4'dR#R#)zGeneral enquiryzBooking enquiry)s&rOÚ_enquiry_type_labelrùHsÜ 3°D× 9Ò 9Ð ÐPÐ?PÐPrQcó4V^8„dQhR\R\RR/#)rvr@)rNs"rOrPrPLs"÷3
ñ3
¤Sð3
Ô0Að3
Àdñ3
rQcó²\VP4P4pVR9d/\P!RWP4\ RRR7h\VP 4'g%\P!RV4\ RRR7h\VP4'g%\P!RV4\ RRR7h\V4'dr\'g%\P!R V4\ R
R R7h\VP4'g%\P!R V4\ RR
R7hR#\VP4'g%\P!RV4\ RRR7h\VP4'g%\P!RV4\ RRR7hR#)Úbookingz%[%s] rejected: invalid enquiryType=%rr8z1Please choose a valid enquiry type and try again.r
z [%s] rejected: missing full nameúPlease enter your full name.z#[%s] rejected: missing phone numberz!Please enter your contact number.z-[%s] rejected: general enquiries are disabledrz>General enquiries are currently unavailable through this form.z.[%s] rejected: missing general enquiry messagezPlease tell us how we can help.Nz[%s] rejected: missing pet nameúPlease enter your dog's name.z[%s] rejected: missing locationzPlease enter your location.>)
r~r;rr ÚfullNameÚphonerõr(rÚpetNameÚlocation)rkrÚ enquiry_types&& rOÚ_validate_submissionrLsˆÜ˜5€LàЊÐ
×L\ÑL\ÔØØ
ð
ô
D—MM× ŠÐ9¸ØØ
ð
ô
D—J‘J× Ò ÜŠÐ<¸jÔØØ
ð
ô
˜4× Ò ß NŠNÐJÈJÔ ØØð
2026-06-17 21:51:29 +12:00
ô˜Ÿ × NŠNÐKÈZÔ ØØð
2026-05-04 20:32:24 +12:00
ñ ä D—L‘L× ŠÐ8¸*ÔØØ
ð
ô
D—MM× ŠÐ8¸ØØ
ð
ñ #rQcó(V^8„dQhR\RR/#©rLrr\r@)rNs"rOrPrPs÷ñÔ 1ð°dñrQcóœ\V4'dRMRVn\VP4Vn\VP4Vn\VP
4Vn\VP 4Vn\VP4Vn\VP4Vn\VP4Vn VPUu.uF!p\V4'gK\V4NK# upVn
VPUu.uF!p\V4'gK\V4NK# upR,Vn \^VP4Vn
RF'p\W4pVe
V^8:gK\WR4K) \V4'dRVnRVn.Vn
R#R#uupiuupi):Né NNry©ÚvisitStartedAtÚ
pageEnteredAtÚfirstInteractionAtÚ
sendClickedAt)rÿrrrrÚreferrerÚpageÚservicesÚjourneyrÙÚ stepChangesÚgetattrÚsetattr)rÚserviceÚstepÚ
field_namerÐs& rOÚ_normalize_submissionrsJÜ$7¸×$=Ò$=‘yÀ9€DÔܘTŸ]™]Ó+€D„Mܘ$Ÿ*™*Ó%€D„JܘDŸL™LÓ)€D„LܘTŸ]™]Ó+€D„MܘDŸL™LÓ)€D„LܘTŸ]™]Ó+€D„MܘŸÓ#€D„IØ6:·m²mÓY±m¨7ÄxÐPW×GXÔ&”X˜&±mÑY€D„MØ/3¯|ª|ÓN©| t¼xÈ¿~”N”H˜T–N©|ÑNÈsÕS€D„Lܘ1˜d×/€DÔã
Ü˜ÓØ Š=˜E QžJÜ D  aô
˜4× Ò ØˆŒ ؈Œ
؈Ž
ñ!ùòZùÚNsÃGÃ7GÄG Ä4G có4V^8„dQhR\R\RR/#)rvrD)rNs"rOrPrPšs(÷4añ4a´ð4aÔ;Oð4aÐTXñ4arQcóX\VP4'g%\P!RV4\ RRR7h\VP
4'g%\P!RV4\ RRR7hRRRR R
R R R
RRRRRRRRRR/ pVP
4FCwr4\\W44'dK!\P!RW4\ RVR7h VP'g%\P!RV4\ RRR7hVPR%9d\ RRR7hVPR%9d\ RRR7hVPR8Xd VP'g\ RRR7hVP'g\ RRR7hVP'g\ RR R7h\VP4pVPR!4'd\!V4^€8d%\P!R"V4\ RR#R7hR$#)&z+[%s] onboarding rejected: missing full namer8r
z'[%s] onboarding rejected: missing phoneúPlease enter your phone number.ÚaddressúPlease enter your address.ÚdogNamerþÚdogBreedúPlease enter your dog's breed.ÚdogAgez&Please enter your dog's date of birth.ÚvetNamez"Please enter your vet clinic name.Ú
vetAddresszPlease enter your vet address.ÚvetPhonez#Please enter your vet phone number.ÚemergencyContactNamez'Please enter an emergency contact name.ÚemergencyContactPhonez/Please enter an emergency contact phone number.z$[%s] onboarding rejected: missing %sz*[%s] onboarding rejected: missing servicesz#Please choose at least one service.ÚnozEPlease confirm whether your dog gets regular flea and tick treatment.z2Please confirm whether your dog has pet insurance.zPPlease confirm the owner-expense acknowledgement for dogs without pet insurance.z,Please confirm emergency veterinary consent.z*Please confirm the onboarding declaration.údata:image/png;base64,z3[%s] onboarding rejected: invalid signature payloadú)Please add your signature before sending.N>r(Úyes)rÿr;rr rr¿rÚservicesNeededÚregularFleaTickTreatmentÚ petInsuranceÚ petInsuranceOwnerExpenseAcceptedÚemergencyVetConsentÚ
termsAcceptedÚsignatureDataUrlÚ
startswithrÝ)rkrÚrequired_fieldsrrÚ signatures&& rOÚ_validate_onboarding_submissionr6šÜ D—MM× ŠÐDÀjÔ¨Ð4RÔ D—J‘J× Ò ÜŠÐ@À*Ô¨Ð4UÔ ÐÐÐÐÐÐÐÐ IØÐ!Rð
€Oðˆ
Üœ Ó NŠNÐAÀ:Ô ¨C¸Ô 
× × Ð ÜŠÐCÀZÔ¨Ð4YÔ ×$¨MÔ¨Ð4{Ô ×Ñ 
Ô¨Ð4hÔ ×јDÔ ¨×)N×)NÐ)Nܨð5GôHð Hð × ¨Ð4bÔ × × Ð Ü¨Ð4`Ô˜×/€IØ × Ñ Ð 8× 9¼SÀ»^ÈcÔ=QÜŠÐLÈjÔ¨Ð4_Ô>RrQcó(V^8„dQhR\RR/#r)rD)rNs"rOrPrPÑs÷,Ô+?ð,ÀDñ,rQcóÒ\VP4Vn\VP4Vn\VP4Vn\VP4Vn\VP
4Vn\VP 4Vn\VP4Vn\VP4Vn\VP4Vn \VP4Vn
\VP4Vn \VP4Vn \VP4Vn
\VP4Vn\VP4P!4Vn\VP"4P!4Vn\VP$4Vn\VP&4VnVP(Uu.uF!p\V4'gK\V4NK# upR,VnRF'p\+W4pVe
V^8:gK\-WR4K) R#uupi)Nr
)rÿrrrr r"Ú temperamentÚ medicalNotesÚaccessInstructionsr#r$r%r&r'r-r~r.rrr,rr)rrrs& rOÚ _normalize_onboarding_submissionr<ÑܘTŸ]™]Ó+€D„Mܘ$Ÿ*™*Ó%€D„JܘDŸL™LÓ)€D„LܘDŸL™LÓ)€D„LܘTŸ]™]Ó+€D„Mܘ4Ÿ;™;Ó'€D„KÜ × 0Ñ 0Ó1€DÔÜ  ×!2Ñ!2Ó3€DÔÜ& t×'>Ñ'>Ó?€DÔܘDŸL™LÓ)€D„LܘtŸÓ/€D„OܘTŸ]™]Ó+€D„MÜ (¨×)BÑ)BÓ C€DÔÜ!)¨$×*DÑ*DÓ!E€DÔÜ$,¨T×-JÑ-JÓ$K×$QÑ$QÓ$S€DÔ  ×!2Ñ!2Ó;€DÔܘTŸ]™]Ó+€D„MܘŸÓ#€D„IØ<@×<OÒ<OÓeÑ<O°ÔS[Ð\c×SdÔ,œ8 ,Ñ<OÑeÐfhÕi€DÔã`ˆ
Ü˜ÓØ Š=˜E QžJÜ D  aùòfs Ç?I$ÈI$có0V^8„dQhR\R\/#)rLÚuar\r)rNs"rOrPrPìs÷

$”#ð
$œ#ñ
$rQcóŽaS'gR#.ROp.ROp\V3RlV4R4p\V3RlV4R4pV RV 2#)ÚUnknownc3ó><"TFwrVS9gKVxK R#5irS©r€Únr>s& €rOrÚ_parse_ua.<locals>.<genexpr>ôsøéÐ6¡(™$˜!¨a°2©g—A’A£(ùóƒ 
zUnknown browserc3ó><"TFwrVS9gKVxK R#5irSrBs& €rOrrEõsøéИ¨A°©G—1’1£ùrFz
Unknown OSú on ))zEdg/ÚEdge)zOPR/ÚOpera)zChrome/ÚChrome)zFirefox/ÚFirefox)zSafari/ÚSafari))z
Windows NT 10z
Windows 10/11)z Windows NT 6z Windows 8)zMac OS XÚmacOS)ÚiPhonerO)ÚiPadrP)ÚAndroidrQ)ÚLinuxrR)Únext)r>ÚbrowsersÚsystemsÚbrowserÚsystemsf rOÚ _parse_uarXìsPø€ß
Ùò@€Hò;€GôÔ6¡(Ó6Ð8IÓJ€GÜ
ÔÓ4°lÓ
C€F؈Yd˜6˜ #rQcó<V^8„dQhR\R\R\/#©rLÚlabelrÐr\r)rNs"rOrPrPùs!÷ 
ñ 
2026-06-17 21:51:29 +12:00
”sð 
2026-05-04 20:32:24 +12:00
¤3ð 
2026-06-17 21:51:29 +12:00
¬3ñ 
2026-05-04 20:32:24 +12:00
rQcó(V'gR#RV RV R2#)ry
<tr>
2026-06-17 21:51:29 +12:00
<td style="padding:8px 0;color:#888;font-size:13px;white-space:nowrap;
2026-05-04 20:32:24 +12:00
font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
vertical-align:top;width:130px;">z×</td>
2026-06-17 21:51:29 +12:00
<td style="padding:8px 0 8px 16px;color:#213021;font-size:14px;font-weight:500;
2026-05-04 20:32:24 +12:00
font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
vertical-align:top;">ú</td>
</tr>r¹©r[s&&rOÚ _detail_rowr_ùs/ß Ùð49°'ð:'ð(- .
ð
ð
rQcó<V^8„dQhR\R\R\/#rZr)rNs"rOrPrPs!÷ 
ñ 
”Sð 
¤ð 
2026-06-17 21:51:29 +12:00
– 
2026-05-04 20:32:24 +12:00
rQcó(V'gR#RV RV R2#)ry
<tr>
<td style="padding:5px 0;color:#aaa;font-size:12px;white-space:nowrap;
font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
vertical-align:top;width:100px;">zÙ</td>
<td style="padding:5px 0 5px 16px;color:#666;font-size:12px;
font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
vertical-align:top;word-break:break-all;">r]r^s&&rOÚ _meta_rowrbs1ß Ùð49°'ð:<ð=B¸C
ð
2026-06-17 21:51:29 +12:00
ð
2026-05-04 20:32:24 +12:00
rQcó>V^8„dQhR\R,R\/#)rLÚ duration_msNr\©rv)rNs"rOrPrPs÷ ñ ¤S¨4¥Zð ´Cñ rQcóÐVeV^8dR#\\VR, 44p\V^<4wr#\V^<4wrBV^8”d V RV R2#V^8”d V RV R2#V R2#)Nryzh Úmzm rÄ)ÚroundÚdivmod)rdÚ
total_secondsÚminutesr`Úhourss& rOÚ_format_duration_msrmsØÒ˜k¨AœoÙ䜘k¨DÕ2€Mܘm¨RÓ€GܘG RÓ(N€Eà ˆq„yؘ˜7˜) 1Є{ؘ"˜W˜I ˆYaˆrQcóXV^8„dQhR\R,R\R,R\/#)rLÚstart_msNÚend_msr\re)rNs"rOrPrP$s)÷ 
ð2´C¸$µJð2Ä3ñ2rQcóDVe VeW8dR#\W,
4#)Nry)rm)rorps&&rOÚ_duration_betweenrr$s"ØÒ˜6š>¨VÔ->ÙÜ ˜ 1rQcóFV^8„dQhR\\,R\/#)rLrr\©rv)rNs"rOrPrP*s÷ ñ œ4¤ ¬ñ rQcó8V'gR#RPV4#)ryz -> )Újoin)rs&rOÚ
_journey_textrw*sß ÙØ ;‰; ÐrQrycó<V^8„dQhR\R\R\/#)rLÚ
badge_htmlÚsubtitler\r)rNs"rOrPrP2s!÷
ñ
œSð
´ð
¼cñ
rQcóbV'dRV R2MRpV'dRV R2MRpR\ RV RV R2#)z<div style="margin-top:20px;">ú</div>ryz¿<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:13px;color:#7aaa7a;letter-spacing:0.04em;margin-top:8px;">
2026-05-04 20:32:24 +12:00
zx
<tr>
<td style="background:#213021;padding:36px 48px 32px;text-align:center;">
<img src="zŠ" width="161" height="32" alt="GoodWalk"
style="display:inline-block;max-width:161px;height:auto;border:0;">
ú
z
</td>
</tr>)r-)ryrzÚbadgeÚsubs&& rOÚ _logo_headerr€2scßCMÐ,¨Z¨L¸Ñ ?ÐSU€E÷(0ðà
˜ $à57ððô !
à
ˆ
Ø
ˆð
 ðrQcó0V^8„dQhR\R\/#)rNs"rOrPrPBs÷F ñF ÔF ¬SñF rQc ó\V4pVP'dRPVP4MRp\RVP4\R\ VP 44\RVP4\R\V44.pV'd?VP'd&VP\RVP44RpRpR pMŸVP\R
VP4\R VP4\R V4.4VP'd&VP\R
VP44RVP R2pRVP R2pRpR\VR7 RVPP4^, RV RRPV4 RV R2 #)ú, z
Not specifiedz Your nameÚEmailÚPhoneÚTypeÚMessagezBWe&rsquo;ve received your message and we will be in touch shortly.z<We will review your message and reply within 1 business day.z)General enquiries and dog walking supportzDog&rsquo;s nameÚLocationÚServicesú
About the dogz•We&rsquo;ve received your enquiry and we will be in touch shortly to arrange a <strong style="color:#213021;">Meet &amp; Greet</strong> with you and Ú.zWe will review your details and reach out within 1 business day to schedule a free Meet &amp; Greet. No commitment required &mdash; just a chance for z to make a new best friend.z!Professional dog walking servicesav<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1">
<title>We received your enquiry</title>
</head>
<body style="margin:0;padding:0;background:#f2f2f0;">
<table width="100%" cellpadding="0" cellspacing="0" role="presentation"
style="background:#f2f2f0;padding:40px 16px;">
<tr><td align="center">
<table width="600" cellpadding="0" cellspacing="0" role="presentation"
style="max-width:600px;width:100%;border-radius:16px;overflow:hidden;
box-shadow:0 4px 24px rgba(0,0,0,0.08);">
)rza?
<!-- Body -->
<tr>
<td style="background:#ffffff;padding:48px 48px 40px;">
<h1 style="margin:0 0 8px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:26px;font-weight:700;color:#213021;line-height:1.2;">
Thanks, zÚ! &#x1F43E;
</h1>
<p style="margin:0 0 32px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:16px;color:#555;line-height:1.65;">

</p>
<!-- Details card -->
<table width="100%" cellpadding="0" cellspacing="0" role="presentation"
style="background:#f8f7f4;border-radius:12px;margin-bottom:36px;">
<tr>
<td style="padding:28px 32px;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:11px;font-weight:700;letter-spacing:0.1em;
color:#888;text-transform:uppercase;margin-bottom:20px;">
Your enquiry summary
</div>
<table width="100%" cellpadding="0" cellspacing="0" role="presentation">
rya*
</table>
</td>
</tr>
</table>
<!-- What's next -->
<table width="100%" cellpadding="0" cellspacing="0" role="presentation"
style="border-left:3px solid #FFD100;margin-bottom:36px;">
<tr>
<td style="padding:4px 0 4px 20px;">
2026-05-04 20:32:24 +12:00
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:13px;font-weight:700;color:#213021;margin-bottom:6px;">
What happens next?
</div>
2026-05-04 20:32:24 +12:00
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:14px;color:#666;line-height:1.6;">
2026-05-04 20:32:24 +12:00

2026-06-17 21:51:29 +12:00
</div>
2026-05-04 20:32:24 +12:00
</td>
</tr>
</table>
2026-05-04 20:32:24 +12:00
<p style="margin:0;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:14px;color:#888;line-height:1.6;">
Questions? Just reply to this email or reach us at 022 642 1011.
2026-05-04 20:32:24 +12:00
</p>
</td>
2026-05-04 20:32:24 +12:00
</tr>
<!-- Footer -->
<tr>
<td style="background:#213021;padding:24px 48px;text-align:center;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:12px;color:#5a8a5a;line-height:1.6;">
GoodWalk &middot; Auckland, New Zealand<br>
2026-05-04 20:32:24 +12:00
<a href="https://www.goodwalk.co.nz" style="color:#7aaa7a;text-decoration:none;">
goodwalk.co.nz
</a>
</div>
</td>
</tr>
</table>
</td></tr>
</table>
2026-05-04 20:32:24 +12:00
</body>
</html>)rrvr_rÿrvrrÚextendrrr€rˆ)rÚ
is_generalÚ
services_textÚenquiry_summary_rowsÚ
intro_htmlÚnext_steps_htmlÚ
logo_subtitles& rOÚ client_emailr“Bs¿Ü$ *€JØ04·
·
°
D—II˜dŸm™mÔ,À?€Mä§¡ÓGœS §¡›_ÓG˜TŸZ™ZÓÓÐ÷Ø <<ˆ × °I¸t¿|¹|Ó(LÔ  ð
Kð ðD
à×з ± Ó˜J¨¯
©
Ó˜
Ó
ô
ð <<ˆ × °OÀTÇ\Á\Ó(RÔ 
Yà|‰|ˆn˜
ð ð 
àŸ,™,˜Ð'Bð
Dð ð
<ˆ
ð ô"
˜}Ô -Ð/ð—}‘}×,¨QÕ1ðˆlðð—W‘WÐ4ð" &ðy\ ð\ rQcóHV^8„dQhR\R\R\R\/#©rLrrjrVr\)rNs"rOrPrPËs/÷w ñw Ôw ¬Sðw ¼3ðw Ä3ñw rQcóÌ\V4pVP'dRPVP4MRp\P!4pVP R4P
R4pVPP4'd"VPP4^,MRpV'dRMRpV'dRMRp VP'dR V R
VP R 2MR p
R
PVR7p VP'd\RVP4M \RR4p VP'd\RVP4MR p
\R\VP VP"44p\R\VP$VP"44p\R\VP&VP"44p\R\VP(VP"44pVP*'d \R\-VP*44MR p\R\/VP044pV'dRMRp\3R\5V44.pV'dpVP6'd&VP9\3RVP644VP:'d&VP9\3RVP:44MFVP=\3RVP64\3RVP:4\3RV4.4R P.RNV NRN\?V R 7 NR!NV NR"NVP@ NR#NVP@ NR$NVP NR%NVP@ NR&NVP@ NR'NVPB NR&NVPB NR(NV NR)NR PV4 NR*NV
NR+NVP@ NR,NV NR-NVPB NR.NVPB NR/N\R0V4 NR*N\R1V4 NR*NV NR*NV NR*NV NR*NV NR*NV NR*NV NR*NV
NR*NV NR2N4#)3rƒõ—ú%d %b %Y at %I:%M %pÚthemzNew GoodWalk EnquiryzNew GoodWalk Leadr‡a)
<tr>
<td colspan="2" style="padding:16px 0 0;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:11px;font-weight:700;letter-spacing:0.08em;color:#888;
text-transform:uppercase;margin-bottom:8px;">zë</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:14px;color:#444;line-height:1.6;background:#f0efe9;
border-radius:8px;padding:14px 16px;">z</div>
</td>
</tr>ryar<div style="display:inline-block;background:#FFD100;border-radius:100px;
padding:10px 28px;">
<span style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:18px;font-weight:700;color:#213021;">
&#x1F4E9;&nbsp; New enquiry!
</span>
</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:12px;color:#5a8a5a;margin-top:12px;">
Submitted {submitted_at}
</div>)Ú submitted_atú Came fromúDirect / bookmarkÚPageú Time on siteú Time on pageúActive form timeúForm open timez Step changesÚJourneyzEnquiry detailszDog &amp; servicesr†ÚDogrˆr‰zú<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1">
<meta name="color-scheme" content="light only">
<meta name="supported-color-schemes" content="light">
<title>a</title>
<style>
:root {
color-scheme: light only;
2026-05-04 20:32:24 +12:00
supported-color-schemes: light;
}
body,
table,
td,
div,
p,
span,
a {
forced-color-adjust: none !important;
-webkit-text-size-adjust: 100%;
}
.gw-owner-body {
background: #f2f2f0 !important;
color: #213021 !important;
}
.gw-owner-shell {
background: #ffffff !important;
}
.gw-owner-dark-panel {
background: #213021 !important;
}
.gw-owner-email-chip {
display: inline-block;
background: #ffffff !important;
color: #213021 !important;
border-radius: 10px;
padding: 12px 14px;
border: 1px solid #d9dfd9;
text-decoration: none !important;
}
.gw-owner-email-chip,
2026-05-04 20:32:24 +12:00
.gw-owner-email-chip a,
a.gw-owner-email-chip {
color: #213021 !important;
}
@media (prefers-color-scheme: dark) {
html,
body,
.gw-owner-body {
background: #f2f2f0 !important;
color: #213021 !important;
}
.gw-owner-shell,
.gw-owner-shell td {
background: #ffffff !important;
color: #213021 !important;
}
.gw-owner-dark-panel,
.gw-owner-dark-panel td {
background: #213021 !important;
}
2026-06-17 21:51:29 +12:00
.gw-owner-email-chip,
.gw-owner-email-chip a,
2026-05-04 20:32:24 +12:00
a.gw-owner-email-chip {
background: #ffffff !important;
color: #213021 !important;
}
}
</style>
</head>
<body class="gw-owner-body" style="margin:0;padding:0;background:#f2f2f0;color:#213021;">
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" bgcolor="#f2f2f0"
style="background:#f2f2f0;padding:40px 16px;">
2026-05-04 20:32:24 +12:00
<tr><td align="center">
2026-06-17 21:51:29 +12:00
<table class="gw-owner-shell" width="600" cellpadding="0" cellspacing="0" role="presentation" bgcolor="#ffffff"
style="max-width:600px;width:100%;border-radius:16px;overflow:hidden;
box-shadow:0 4px 24px rgba(0,0,0,0.08);background:#ffffff;">
)rya
2026-06-17 21:51:29 +12:00
<!-- Body -->
<tr>
<td bgcolor="#ffffff" style="background:#ffffff;padding:40px 48px 36px;color:#213021;">
<!-- Quick contact -->
<table class="gw-owner-dark-panel" width="100%" cellpadding="0" cellspacing="0" role="presentation" bgcolor="#213021"
style="background:#213021;border-radius:12px;margin-bottom:28px;">
<tr>
<td bgcolor="#213021" style="padding:22px 24px;background:#213021;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:11px;font-weight:700;letter-spacing:0.1em;color:#7aaa7a;
text-transform:uppercase;margin-bottom:10px;">
Quick contact
</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:14px;color:#d8e6d8;line-height:1.6;margin-bottom:10px;">
Email z| directly:
</div>
<div style="margin-bottom:12px;">
<a href="mailto:aß" class="gw-owner-email-chip"
style="display:inline-block;background:#ffffff;color:#213021 !important;
font-family:Menlo,Consolas,'SFMono-Regular',monospace;
font-size:20px;font-weight:700;line-height:1.4;word-break:break-all;
border-radius:10px;padding:12px 14px;border:1px solid #d9dfd9;
text-decoration:none;">
a 
</a>
</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:12px;color:#b7cbb7;line-height:1.6;">
Tap and hold the address to copy on iPhone, or tap below to open a new email.
</div>
</td>
</tr>
</table>
<!-- Owner details -->
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:11px;font-weight:700;letter-spacing:0.1em;color:#888;
text-transform:uppercase;margin-bottom:16px;">Owner details</div>
<table width="100%" cellpadding="0" cellspacing="0" role="presentation"
style="background:#f8f7f4;border-radius:12px;margin-bottom:28px;">
<tr><td style="padding:24px 28px;">
<table width="100%" cellpadding="0" cellspacing="0" role="presentation">
<tr>
<td style="padding:6px 0;font-size:13px;color:#888;width:80px;
font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
vertical-align:top;">Name</td>
<td style="padding:6px 0 6px 16px;font-size:15px;font-weight:600;
color:#213021;font-family:-apple-system,BlinkMacSystemFont,
'Segoe UI',sans-serif;vertical-align:top;">a#</td>
</tr>
<tr>
<td style="padding:6px 0;font-size:13px;color:#888;
font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
vertical-align:top;">Email</td>
2026-06-17 21:51:29 +12:00
<td style="padding:6px 0 6px 16px;font-size:14px;
font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
vertical-align:top;">
<a href="mailto:zX" style="color:#213021;font-weight:500;
text-decoration:none;">a9</a>
</td>
</tr>
<tr>
<td style="padding:6px 0;font-size:13px;color:#888;
font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
vertical-align:top;">Phone</td>
<td style="padding:6px 0 6px 16px;font-size:14px;
font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
vertical-align:top;">
<a href="tel:a¤</a>
</td>
</tr>
</table>
</td></tr>
</table>
<!-- Dog & service details -->
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:11px;font-weight:700;letter-spacing:0.1em;color:#888;
text-transform:uppercase;margin-bottom:16px;">aO</div>
2026-06-17 21:51:29 +12:00
<table width="100%" cellpadding="0" cellspacing="0" role="presentation"
style="background:#f8f7f4;border-radius:12px;margin-bottom:28px;">
<tr><td style="padding:24px 28px;">
<table width="100%" cellpadding="0" cellspacing="0" role="presentation">
ú
a4
</table>
</td></tr>
</table>
2026-06-17 21:51:29 +12:00
<!-- CTA buttons -->
<table cellpadding="0" cellspacing="0" role="presentation" style="margin-bottom:32px;">
<tr>
<td style="padding-right:12px;">
<a href="mailto:ac"
style="display:inline-block;background:#213021;color:#FFD100;
font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:14px;font-weight:600;text-decoration:none;
2026-06-17 21:51:29 +12:00
border-radius:8px;padding:12px 24px;">
Email zb
</a>
</td>
<td>
<a href="tel:a{"
style="display:inline-block;background:#f8f7f4;color:#213021;
font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:14px;font-weight:600;text-decoration:none;
border-radius:8px;padding:12px 24px;border:1px solid #e0e0d8;">
Call aµ
2026-06-17 21:51:29 +12:00
</a>
</td>
</tr>
</table>
<!-- Session info -->
<table width="100%" cellpadding="0" cellspacing="0" role="presentation"
style="border-top:1px solid #eeeee8;padding-top:20px;">
<tr><td>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
2026-06-17 21:51:29 +12:00
font-size:11px;font-weight:700;letter-spacing:0.08em;color:#ccc;
text-transform:uppercase;margin-bottom:12px;">Session info</div>
<table width="100%" cellpadding="0" cellspacing="0" role="presentation">
ú
IP addressÚBrowseraE
2026-06-17 21:51:29 +12:00
</table>
</td></tr>
</table>
2026-06-17 21:51:29 +12:00
</td>
2026-06-17 21:51:29 +12:00
</tr>
<!-- Footer -->
2026-05-18 22:25:43 +12:00
<tr>
<td style="background:#f8f7f4;padding:18px 48px;text-align:center;
border-top:1px solid #e8e8e4;">
2026-05-19 23:36:58 +12:00
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:12px;color:#bbb;">
Sent automatically by GoodWalk enquiry form
2026-05-18 22:25:43 +12:00
</div>
</td>
</tr>
</table>
</td></tr>
</table>
</body>
</html>)"rõrrvrÚstrftimeÚlstriprÿr‰rˆrrNrrbrrrr rr r
rrvrwrr_rrr€r)rrjrVrrÚ
first_nameÚ email_titleÚ
message_labelÚ
message_blockr~Ú referrer_rowÚpage_rowÚvisit_time_rowÚ
page_time_rowÚactive_time_rowÚ
form_time_rowÚstep_changes_rowÚ journey_rowÚdetail_headingÚ detail_rowss&&& rOÚ owner_emailr¸ËÜ$ *€JØ04·
2026-06-17 21:51:29 +12:00
·
2026-05-18 22:25:43 +12:00
°
D—II˜dŸm™mÔ,À5€MÜ
2026-06-17 21:51:29 +12:00
,Š,.€CØ—<<Ð 6Ó7×>¸C€LØ-1¯]©]×-@Ñ-@×-BÒ-B×& €Jß,6Ñ(Ð<O€Kç!+€Mð ðBð
CPÀðQ<@¿<¹<¸I
ñ

ð#%ðð
÷¨\˜Ó
ð=A¿M¿M¸M”9˜[¨$¯-©-Ô8ÌyÐYdÐfyÓOz€LØ/3¯y¯y¨yŒy˜ §¡Ô+¸b€Hܘ~Ô/@À×ATÑATÐVZ×VhÑVhÓ/iÓj€NܘnÔ.?À×@RÑ@RÐTX×TfÑTfÓ.gÓh€MÜÐ 2Ô4EÀd×F]ÑF]Ð_c×_qÑ_qÓ4rÓs€OÜÐ.Ô0AÀ$×BTÑBTÐVZ×VhÑVhÓ0iÓj€MØKO×K[×K[ÐK[”y ´°T×5EÑ5EÓ1FÔGÐacÐܘI¤}°T·\±\Ó'BÓC€Kß*4Ñ&Ð:N€NܘvÔ':¸4Ó'@ÓB€KçØ <<ˆ × Ñ œ{¨5°$·,±,Ó ==ˆ=Ø × Ñ œ{¨:°t·}±}Ó Føà×Ñä˜E 4§<¡<Ó˜¯
©
Ó˜
Ó
ô
÷} ó} ð
ð} ð ˆð} ðU ð} ôx
 Ô 'Ð(ðy} ðx)ðy} ð\&˜,ð]} ð\'%ð]} ðb&*§Z¡Z Lðc} ðb1ðc} ðn—zzlðo} ðn#Kðo} ðbLPÏ=É=È/ðc} ðb Z'ðc} ðt(,§z¡z lðu} ðt31ðu} ðv26·±° ðw} ðv
=$ðw} ðJ%)§J¡J <ðK} ðJ01ðK} ðL26·±° ðM} ðL
=GðM} ð`HVÐFVða} ð`Wða} ðl—77˜(ðm} ðl)ðm} ðn!/ðo} ðn "#ðo} ð@$(§:¡: ,ðA} ð@/ðA} ðJ&˜,ðK} ðJ' ðK} ðR!%§
¡
˜|ðS} ðR,ðS} ð\Ÿ*™*˜ð]} ð\&ð]} ôx˜\¨2Ó/ðy} ðx0ðy} ôz˜Ó1ð{} ðz2ð{} ð|"ð}} ð|#ð}} ð~!} ð~"ð} ð@#ðA} ð@$ðA} ðB!/ðC} ðB"ðC} ðD$ðE} ðD%ðE} ðF .ðG} ðF!ðG} ðH*ðI} ðHðI} ðJ-ðK} ðJ ôK} ð} rQcóHV^8„dQhR\R\R\R\/#r•©rDrv)rNs"rOrPrPs0÷j ñj Ô!5ðj ¼3ðj Ìðj ÔQTñj rQc ó` \P!4PR4PR4pRP VP
4p\
R\VPVP44p\
R\VPVP44p\
R\VPVP44p\
R\VPVP44pVP'd\
RVP4M \
RR4p VP'd\
R VP4MR
p
VP'dR VP R 2MR
p VP 'dR
VP R 2MR
p VP"'dRVP" R 2MR
p
RVP$ R2pRV R2pR
P .RN\'VRR7 NRNVP( NRNVP( NRNVP* NRNVP* NRN\-RVP.4 NRN\-R\1VP(44 NRN\-RVP*4 NRN\-RVP24 NRNV
NR N\-R!VP44 NRN\-R"VP64 NRN\-R#VP8;'gR$4 NRN\-R%V4 NRNV NRNV NR&N\-R'VP:4 NRN\-R(VP<4 NRN\-R)VP>4 NRN\-R*VP@4 NRN\-R+VPB4 NRN\-R,VPDR-8XdR.MR/4 NRN\-R0VPFR-8XdR.MR/4 NRNVPFR18XdVPH'd
\-R2R34MR
NRN\-R4VPJ'dR3MR54 NRN\-R6VPL'dR3MR54 NRN\-R7R34 NRN\-R8R94 NR:NV NR;N\
R<V4 NRN\
R=V4 NRNV NRNV NRNV NRNV NRNV NRNV
NR>N4#)?r˜r™r rrya;
<tr>
<td colspan="2" style="padding:16px 0 0;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:11px;font-weight:700;letter-spacing:0.08em;color:#888;
text-transform:uppercase;margin-bottom:8px;">Temperament and routine</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:14px;color:#444;line-height:1.6;background:#f0efe9;
border-radius:8px;padding:14px 16px;">ú </div>
</td>
</tr>a1
<tr>
<td colspan="2" style="padding:16px 0 0;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:11px;font-weight:700;letter-spacing:0.08em;color:#888;
text-transform:uppercase;margin-bottom:8px;">Medical notes</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:14px;color:#444;line-height:1.6;background:#f0efe9;
border-radius:8px;padding:14px 16px;">a<
<tr>
<td colspan="2" style="padding:16px 0 0;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:11px;font-weight:700;letter-spacing:0.08em;color:#888;
text-transform:uppercase;margin-bottom:8px;">Home access instructions</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:14px;color:#444;line-height:1.6;background:#f0efe9;
border-radius:8px;padding:14px 16px;">á•
<div style="margin-top:16px;border-radius:16px;background:#ffffff;border:1px solid #e3e3db;padding:14px 14px 10px;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:11px;font-weight:700;letter-spacing:0.1em;color:#888;
text-transform:uppercase;margin-bottom:10px;">Captured signature</div>
<img src="ú{" alt="Client signature" style="display:block;max-width:100%;height:auto;border-radius:10px;background:#fff;">
</div>aT<div style="display:inline-block;background:#FFD100;border-radius:100px;
padding:10px 28px;">
<span style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:18px;font-weight:700;color:#213021;">
&#x270D;&nbsp; New onboarding form
</span>
</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;
font-size:12px;color:#5a8a5a;margin-top:12px;">
Submitted ú
</div>aZ<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1">
<title>New GoodWalk onboarding form</title>
</head>
<body style="margin:0;padding:0;background:#f2f2f0;">
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" style="background:#f2f2f0;padding:40px 16px;">
<tr><td align="center">
<table width="680" cellpadding="0" cellspacing="0" role="presentation"
style="max-width:680px;width:100%;border-radius:16px;overflow:hidden;box-shadow:0 4px 24px rgba(0,0,0,0.08);">
zSigned onboarding form©ryrz
<tr>
<td style="background:#ffffff;padding:38px 40px 34px;">
<table width="100%" cellpadding="0" cellspacing="0" role="presentation"
style="background:#213021;border-radius:12px;margin-bottom:26px;">
<tr>
<td style="padding:22px 24px;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:11px;font-weight:700;letter-spacing:0.1em;color:#7aaa7a;text-transform:uppercase;margin-bottom:10px;">
Quick contact
</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:14px;color:#d8e6d8;line-height:1.6;margin-bottom:10px;">
Reply directly to the owner or call them back:
</div>
<div style="margin-bottom:10px;">
<a href="mailto:úé" style="display:inline-block;background:#ffffff;color:#213021;text-decoration:none;border-radius:10px;padding:12px 14px;border:1px solid #d9dfd9;font-family:Menlo,Consolas,'SFMono-Regular',monospace;font-size:18px;font-weight:700;">ú=</a>
</div>
<a href="tel:úã" style="display:inline-block;background:#ffd100;color:#213021;text-decoration:none;border-radius:999px;padding:10px 16px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:14px;font-weight:700;">Call aU</a>
</td>
</tr>
</table>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:11px;font-weight:700;letter-spacing:0.1em;color:#888;text-transform:uppercase;margin-bottom:16px;">Owner details</div>
2026-05-19 23:36:58 +12:00
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" style="background:#f8f7f4;border-radius:12px;margin-bottom:24px;">
<tr><td style="padding:24px 28px;">
2026-06-17 21:51:29 +12:00
<table width="100%" cellpadding="0" cellspacing="0" role="presentation">
ÚNamer¥r„r…ÚAddressac
</table>
</td></tr>
</table>
2026-05-19 23:36:58 +12:00
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:11px;font-weight:700;letter-spacing:0.1em;color:#888;text-transform:uppercase;margin-bottom:16px;">Dog and service details</div>
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" style="background:#f8f7f4;border-radius:12px;margin-bottom:24px;">
2026-05-19 23:36:58 +12:00
<tr><td style="padding:24px 28px;">
<table width="100%" cellpadding="0" cellspacing="0" role="presentation">
ÚBreedú
Date of birthr—ÚServiceaZ
</table>
</td></tr>
</table>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:11px;font-weight:700;letter-spacing:0.1em;color:#888;text-transform:uppercase;margin-bottom:16px;">Safety details</div>
2026-06-17 21:51:29 +12:00
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" style="background:#f8f7f4;border-radius:12px;margin-bottom:24px;">
2026-05-19 23:36:58 +12:00
<tr><td style="padding:24px 28px;">
<table width="100%" cellpadding="0" cellspacing="0" role="presentation">
2026-06-17 21:51:29 +12:00
ú
Vet clinicú Vet phoneú Vet addressúEmergency contactúEmergency phoneúRegular flea and tick treatmentr+ÚYesÚNoú
Pet insurancer(úOwner covers all vet costsÚ ConfirmedúCouncil registrationuNot confirmed — follow upÚ VaccinationsúEmergency consentÚ DeclarationÚSignedú*
</table>
á
2026-06-17 21:51:29 +12:00
</td></tr>
</table>
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" style="border-top:1px solid #eeeee8;padding-top:20px;">
2026-06-17 21:51:29 +12:00
<tr><td>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:11px;font-weight:700;letter-spacing:0.08em;color:#ccc;text-transform:uppercase;margin-bottom:12px;">Session info</div>
2026-06-17 21:51:29 +12:00
<table width="100%" cellpadding="0" cellspacing="0" role="presentation">
2026-05-19 23:36:58 +12:00
úž
</table>
2026-06-17 21:51:29 +12:00
</td></tr>
2026-05-19 23:36:58 +12:00
</table>
</td>
</tr>
</table>
</td></tr>
</table>
</body>
</html>)'rrvr,rbrrr rr r
rrr9r:r;r2r€rr_rÿrvrrr r"r#r%r$r&r'r-r.r/ÚcouncilRegistrationConfirmedÚvaccinationsConfirmed)rrjrVrÚdog_notes_blockÚ
medical_blockÚ access_blockÚsignature_blockr~s&&& rOÚowner_onboarding_emailrâÜ—<<“>×*Ð+AÓB×IÈ#ÓN€LØ—I‘I˜d×2€Mܘ~Ô/@À×ATÑATÐVZ×VhÑVhÓ/iÓj€NܘnÔ.?À×@RÑ@RÐTX×TfÑTfÓ.gÓh€MÜÐ 2Ô4EÀd×F]ÑF]Ð_c×_qÑ_qÓ4rÓs€OÜÐ.Ô0AÀ$×BTÑBTÐVZ×VhÑVhÓ0iÓj€MØ<@¿M¿M¸M”9˜[¨$¯-©-Ô8ÌyÐYdÐfyÓOz€LØ/3¯y¯y¨yŒy˜ §¡Ô+¸b€Hð×"×>B×=MÑ=MÐ<NðO ñ
2026-06-17 21:51:29 +12:00
ð)+ðð,×#×>B×=NÑ=NÐ<OðP ñ
ð*,ðð,×)×>B×=TÑ=TÐ<UðV ñ
ð02ððð
2026-05-19 23:36:58 +12:00
×*
ð €Oð ð)˜*ð
2026-06-17 21:51:29 +12:00
2026-05-19 23:36:58 +12:00
€E÷h óh ð
 ðh ô
 Ð1IÔ JÐh ðLh ð8&*§Z¡Z Lð9h ð81Zð9h ð8[_÷[eñ[eðZfð9h ð8f ð9h ð<!%§
2026-06-17 21:51:29 +12:00
¡
˜|ð=h ð<,Oð=h ð<PT÷PZñPZðO[ð=h ð< [ð=h ôN˜v t§}¡}Ó6ðOh ðN7ðOh ôP˜w¬¨D¯J©J«Ó9ðQh ðP:ðQh ôR˜¯
©
Ó4ðSh ðR5ðSh ôT˜y¨$¯,©,Ó8ðUh ðT9ðUh ðV .ðWh ðV !ðWh ôh˜u d§l¡lÓ4ðih ðh5ðih ôj˜¯
©
2026-05-19 23:36:58 +12:00
Ó7ðkh ðj8ðkh ôl˜°· ± ×0DÐ0D¸uÓFðmh ðlGðmh ôn˜y¨-Ó9ðoh ðn:ðoh ðp#ðqh ðp$ðqh ðr!/ðsh ðr "ðsh ôD˜|¨T¯\©\Ó;ðEh ðD<ðEh ôF˜{¨D¯M©MÓ;ðGh ðF<ðGh ôH˜}¨d¯o©oÓ?ðIh ðH@ðIh ôJÐ2°D×4MÑ4MÓOðKh ðJPðKh ôLÐ0°$×2LÑ2LÓNðMh ðLOðMh ôNÐ@È4×KhÑKhÐlqÔKqÁ%Ðw{Ó}ðOh ðN~ðOh ôP˜¸×9JÑ9JÈeÔ9S±ÐY]Ó_ðQh ðP`ðQh ðRNR×M^ÑM^ÐbfÔMfÐko÷lQ÷lQðlQ”;Ð;¸WYðZðSh ðRZðSh ôTÐ5Àd×Fg×FgÐFg±{ðnKóLðMðUh ðTMðUh ôV˜~¸d×>X×>XÐ>X©{Ð^{Ó}ðWh ðV~ðWh ôXÐ2°KÓAðYh ðXBðYh ôZ˜}¨hÓ8ð[h ðZ9ð[h ð^!ð_h ð^"ð_h ôn˜\¨2Ó/ðoh ðn0ðoh ôp˜Ó1ðqh ðp2ðqh ðr"ðsh ðr#ðsh ðt!/ðuh ðt"ðuh ðv#ðwh ðv$ðwh ðx!/ðyh ðx"ðyh ðz .ð{h ðz!ð{h ð|*ð}h ð|
ô}h ðh rQc óbV^8„dQhR\R\R\R\R\R,/#)rLÚdog_nameÚdog_birth_dateÚ
owner_namerkr\Nr))rNs"rOrPrP²s7÷)ñ)¤sð)¼Cð)ÌSð)Ô^að)ÔfjÐmqÕfqñ)rQcóN\V4p\V4p\V4pV'd V'gR#\P!VR4P4pT\^R7,p\P!RRTP44PR4;'gRp T R2p
2026-06-17 21:51:29 +12:00
RT R 2p T'gT
MT
R
T 2p R \P!4 R \P!\P 4P#R
4 RTP#R4 RTP#R4 RT
RT RT R2p
RRT R2R\$P&!T
P)R44P+R4/# \d\
P !RY14R#i;i)%Y-%m-%dz<[%s] onboarding birthday calendar skipped: invalid dogAge=%r)Údaysú
[^a-z0-9]+Údogz 's BirthdayzGoodWalk reminder: z 's birthday.ú for zƒBEGIN:VCALENDAR
VERSION:2.0
PRODID:-//GoodWalk//Dog Birthday Reminder//EN
CALSCALE:GREGORIAN
METHOD:PUBLISH
BEGIN:VEVENT
UID:z@goodwalk.co.nz
DTSTAMP:z%Y%m%dT%H%M%SZz
DTSTART;VALUE=DATE:z%Y%m%dz
DTEND;VALUE=DATE:z
RRULE:FREQ=YEARLY
SUMMARY:z
DESCRIPTION:z
X-WR-CALNAME:z
END:VEVENT
END:VCALENDAR
Úfilenameú goodwalk-z
-birthday.icsÚcontentrbÚascii)rÚstrptimeÚdater<r;rrÚrerr~r‰rÚutcr¨Úbase64Ú b64encodeÚencoder”)rkÚdog_name_cleanÚbirth_date_cleanÚowner_name_cleanÚ starts_onÚends_onÚ safe_nameÚsummaryÚ descriptionÚ
calendar_nameÚics_bodys&&&& rOÚ_birthday_ics_attachmentr²Ü˜'€NÜ ÓÜ 
Óç ×!1ÙðÜ×%Ð&6¸
ÓC×Jˆ ð
œ)¨Ô+€GÜ} c¨>×+?Ñ+?Ó+AÓB×ÓVÐQV€IØÐ   Ð,€GØÐ'7°|ÐD€Kß#3G¸G¸9ÀEÐJZÐI[Ð9\€Mð ô zŠz|ˆÜ—<§ ¡ Ó-×6Ð7GÓJØ'×Ó<Ø#×,¨XÓ8àØ"$Ø%ð'ð ð
ð( i  ˜{¨-Д6×# H§O¡O°GÓ$<Ó=×DÀWÓ ðøô9 ôÜŠÐUÐWaÔðúsµ%E>Å>"F$Æ#F$có0V^8„dQhR\R\/#r5©r rv)rNs"rOrPrPÞs÷ ñ ”sð œsñ rQcó¨VfR#\V4pVPRR4PRR4PRR4PRR 4#)
NryÚ&amp;Ú&lt;Ú&gt;Ú
ú<br>)rvro)Útexts& rOÚ _pdf_escaperÞsJØ ‚}ÙÜ ˆu‹:€Dà S˜
‰WS˜
‰WS˜
‰WT˜
rQcó0V^8„dQhR\R\/#)rNs"rOrPrPês÷D ñD Ô$8ðD ¼SñD rQc óž a\P!4PR4PR4pVP;'g/p\ V\ 4'dVPR4MRpRRlo.p\ V\4'V'Vp\ V\ 4'gK\VPRR44pVPR 4;'g.pRpVF[p \ V \ 4'gK\V PR
R44p
VR V
R S!V PR
44 R2,
pK] V'gVPRV RV R24 EM¥RV3Rllp V !RVP4V !R\VP44,V !RVP4,V !RVP4,V !RVP 4,p V !RVP"4V !RVP$4,T !RVP&;'gR4,V !RVP(4,V !RVP*4,V !RVP,4,p
V !RVP.4V !R VP04,V !R!VP24,V !R"VP44,V !R#VP64,T !R$VP8R%8XdR&MR'4,T !R(VP:R%8XdR&MR'4,T !R)VP:R*8XdVP<'dR+MR4,T !R,VP>'dR+MR-4,T !R.VP@'dR+MR-4,T !R/VPB'dR+MR-4,T !R0VPD'dR1MR24,pVPR3V R4V
R5V R24RpVPF'd3R6VPF R7\VP4 R8\V4 R92pRPIV4V,pR:\VP4 R;\VP4 R<\VP"4 R=\V4 R>V R?2 #)@zPClean, full-width, black-and-white, Arial HTML for the printable onboarding PDF.r˜r™ÚsectionsNcó0V^8„dQhR\R\/#r5r)rNs"rOrPÚ/owner_onboarding_pdf_html.<locals>.__annotate__ñs÷+œCð+¤Cñ+rQcó.\V\4'dWVUu.uF/p\V4P4'gK$\ V4NK1 ppV'dRP V4#R#\ V4P4pV'dV#R#uupi)z&mdash;)r}rvr‰rrv)Úitemr¿rs& rOÚ render_valueÚ/owner_onboarding_pdf_html.<locals>.render_valueñstÜ eœT× "Ù38ÓN±5¨4¼CÀ»I¿O¹O×<MÔ&”[ Ö&±5ˆNß',4—99˜ ;°)Ð ˜!×)ˆßˆ* Ð*ùòOs !BÁBrWryÚfieldsr[ú<tr><th>ú </th><td>rÐú
</td></tr>z!<section class='pdf-section'><h2>z%</h2><table class='pdf-table'><tbody>z</tbody></table></section>có<V^8„dQhR\R\R\/#rZ)rNs"rOrPrs&÷ [ñ [”sð [¤3ð [¬3ñ [rQcó4<R\V4 RS!V4 R2#)rrr)r)r[rs&&€rOÚrowÚ&owner_onboarding_pdf_html.<locals>.rows$ø€Øœk¨%Ó¹<ÈÓ;NÐ:OÈzÐ ZrQr„r…z Home accessr¤r‰zTemperament / routinez
Medical notesrÉr+r(z
2026-06-17 21:51:29 +12:00
Not confirmedrÕzEmergency vet consentr×z
Not signedzS<section class='pdf-section'><h2>Owner Details</h2><table class='pdf-table'><tbody>zk</tbody></table></section><section class='pdf-section'><h2>Dog Details</h2><table class='pdf-table'><tbody>zf</tbody></table></section><section class='pdf-section'><h2>Safety</h2><table class='pdf-table'><tbody>zG<section class='pdf-section pdf-signature'><h2>Signature</h2><img src='z@' alt='Client signature'><div class='pdf-signed-line'>Signed by rHz</div></section>zk<!DOCTYPE html>
<html lang="en">
2026-05-18 22:25:43 +12:00
<head>
2026-06-17 21:51:29 +12:00
<meta charset="utf-8">
<title>Goodwalk onboarding form &mdash; a1</title>
<style>
2026-05-18 22:25:43 +12:00
@page {
size: A4;
margin: 14mm 12mm 14mm 12mm;
}
* { box-sizing: border-box; }
html, body {
margin: 0;
padding: 0;
background: #ffffff;
color: #000000;
font-family: Arial, Helvetica, sans-serif;
font-size: 10.5pt;
line-height: 1.4;
}
.pdf-doc { width: 100%; }
.pdf-header {
width: 100%;
border-bottom: 1.5pt solid #000;
padding-bottom: 8pt;
margin-bottom: 14pt;
}
.pdf-header h1 {
font-size: 18pt;
font-weight: 700;
margin: 0 0 4pt 0;
letter-spacing: 0.5pt;
text-transform: uppercase;
}
.pdf-header .pdf-meta {
font-size: 9.5pt;
2026-06-17 21:51:29 +12:00
color: #000;
}
2026-05-18 22:25:43 +12:00
.pdf-section {
width: 100%;
margin: 0 0 14pt 0;
page-break-inside: avoid;
2026-06-17 21:51:29 +12:00
}
2026-05-18 22:25:43 +12:00
.pdf-section h2 {
font-size: 11pt;
font-weight: 700;
text-transform: uppercase;
letter-spacing: 0.6pt;
margin: 0 0 6pt 0;
padding: 0 0 3pt 0;
border-bottom: 0.75pt solid #000;
}
table.pdf-table {
width: 100%;
border-collapse: collapse;
2026-06-17 21:51:29 +12:00
table-layout: fixed;
2026-05-19 23:36:58 +12:00
}
table.pdf-table th,
2026-06-17 21:51:29 +12:00
table.pdf-table td {
2026-05-19 23:36:58 +12:00
text-align: left;
vertical-align: top;
padding: 5pt 8pt;
border-bottom: 0.4pt solid #000;
word-wrap: break-word;
overflow-wrap: break-word;
}
table.pdf-table th {
width: 34%;
font-weight: 700;
2026-06-17 21:51:29 +12:00
background: #ffffff;
2026-05-19 23:36:58 +12:00
}
table.pdf-table td {
width: 66%;
font-weight: 400;
}
.pdf-signature img {
2026-06-17 21:51:29 +12:00
display: block;
2026-05-19 23:36:58 +12:00
max-width: 70%;
max-height: 60mm;
height: auto;
border: 0.5pt solid #000;
padding: 4pt;
margin: 4pt 0 6pt 0;
background: #fff;
}
.pdf-signed-line {
font-size: 9.5pt;
border-top: 0.4pt solid #000;
padding-top: 4pt;
margin-top: 4pt;
}
</style>
</head>
<body>
<div class="pdf-doc">
<header class="pdf-header">
<h1>Goodwalk Onboarding Form</h1>
<div class="pdf-meta">
<strong>z</strong> &middot; z &middot; Submitted z
</div>
</header>
z
</div>
</body>
</html>)%rÚsubmissionSnapshotr}rr‡rrÿrvrrr;rr r"r,r9r:r#r%r$r&r'r-r.r/r0r1r2rv)rrrÚsections_html_partsÚsectionrWrÚ rows_htmlÚfieldr[r Ú
owner_rowsÚdog_rowsÚ safety_rowsÚsignature_htmlÚ body_htmlrs& @rOÚowner_onboarding_pdf_htmlr,êø€ä—<<“>×*Ð+AÓB×IÈ#ÓN€Là×&×,¨"€HÜ+5°hÄ×+EÒ+Eˆx|‰|˜'È4€Hõ&(Ðä(œD×!§hÛˆGܘg¤t×Ü § ¡ ¨G°RÓ 8Ó9ˆEØ—[‘[ Ó0¨bˆF؈IÛÜ! %¬×Ü# E§I¡I¨g°rÓ$:Ó;ØðØ ˜"Ù¯ © °'Ó(:Ó=ðõ ñ  ÷‰yØ#ר ˜"7Ø7@°kðBó# ÷2 [ð [ñ
˜Ÿ
Ó 'œ3˜tŸz™z
'˜4Ÿ:™:Ó
)˜TŸ\™\Ó
- ×!8Ñ!8Ó
 ñ
t—| '˜4Ÿ=™=Ó
/ 4§;¡;×#4Ð#4°"Ó
*˜d×
Ð)¨4×+;Ñ+;Ó
/ 4×#4Ñ#4Ó 
 ñ
 ˜dŸl™lÓ +˜tŸ}™}Ó
- §¡Ó
Ð% t×'@Ñ'@Ó
BñÐ# T×%?Ñ%?Ó
Añ
Ð3¸d×>[Ñ>[Ð_dÔ>d±UÐjnÓ 
pñ /¨D×,=Ñ,=ÀÔ,F¡5ÈDÓ

RñÐ.¸t×?PÑ?PÐTXÔ?XÐ]a÷^C÷^Cð^C± ðIKóLõ
LñÐ(¸×9Z×9ZÐ9Z©+Ð`oÓ
qñ×1K×1KÐ1K¡+ÐQ`Ó
bñÐ)¸$×:R×:RÐ:R©;ÐXgÓ
iñ-¨T×-?×-?Ð-?¡À\Ó
Sð ð ×aÐblÐamðn`Ø`hÐ_iðj[Ø[fÐZgðhBð
Cô
2026-06-17 21:51:29 +12:00
ð €NØ ××Ðð
2026-05-19 23:36:58 +12:00
à×06Ü6AÀ$Ç-Á-Ó6PÐ5QÐQUÔVaÐbnÓVoÐUpðqð
2026-06-17 21:51:29 +12:00
ð ðÐ,¨~Õ=€Ið,7°t·}±}Ó+EÐ*Fð^Gô|˜TŸ]™]Ó,Ð,?Ä ÈDÏLÉLÓ@YÐ?ZÐZnÔozð|HópIðoJðJð€KððKh ðh rQcó0V^8„dQhR\R\/#)rLÚhtmlr\)rvÚbytes)rNs"rOrPrP±s÷)œ3ð)¤5ñ)rQcó<^RIHpV!VR7P4#)r)ÚHTML)Ústring)Ú
2026-05-18 22:25:43 +12:00
weasyprintr1Ú write_pdf)r.r1s& rOÚ_render_pdf_syncr5±sÝÙ  × (rQTc óbV^8„dQhR\R\R\R\R\R,/#)rLr.Ú full_nameÚkindrkr\Nr))rNs"rOrPrP¼s7÷ ñ ¬Cð ¼Cð Äsð ÔX[ð Ô`dÐgkÕ`kñ rQc ƒóî"\P!RR\V4P44P R4;'gRp\
P !\V4GRjxL
p\P!RY2\T44RR T RT R
2R \P!T4PR 4/#LU \d&p\P!RY2TRR7Rp?R#Rp?ii;i5i)
Nz![%s] %s PDF generation failed: %sT©Úexc_infoz[%s] %s PDF generated: %d bytesrîz.pdfrð)rr~r‰r5rr;ÚerrorrÜr”)r.r7r8rkÚ pdf_bytesr“s&&&& rOÚ_signed_form_pdf_attachmentr>¼éÜ} c¬8°IÓ+>×+DÑ+DÓ+FÓG×MÈcÓR×^ÐV^€IðÜ!×+Ô,<¸C×Cˆ ô
 ‡K‚KÐ1°:ÄSÈÃ^Ôi ˜v Q y Ð”6×# .×5°gÓ ðñ
DøÜ ôÜ Š Ð8¸*ÈCÐZ^ÕûðüsCA C5Á CÁ*CÁ+CÁ/AC5ÃCÃ C2Ã
C-Ã'C5Ã-C2Ã2C5có:V^8„dQhR\\,/#rsrt)rNs"rOrPrPÍs÷
ñ
œ$œs
rQcó6.p\\3FpT;'gRP4pV'dVP4R8XdK<VP4VUu0uFq3P4kK up9gKpVP V4 V#uupi)a=BCC recipients for any real email sent home to a client (welcome pack,
birthday, enquiry reply, onboarding confirmation, ...). The business owner is
always copied so they can see exactly what each client received; CLIENT_BCC
adds an optional extra inbox when configured. The OWNER_BCC placeholder is
treated as unset.ryzexample@example.com)r1r r‰r~)ÚoutÚaddrÚxs rOÚ_client_bcc_listrEÍsxð €CÜœjÓØ
ZˆZ Ñ Ó ˆßA—G‘G“IÐ!6Ô Ø 7‰7‹9±Ó¨1ŸW™WžY±Ñ J‰JqŽMñ  €Jùò5sÁBcóHV^8„dQhR\R\R\R\/#)rLr[r[rkr\)rNs"rOrPrPÝs(÷2ñ2œtð2¬Cð2¼Sð2ÄTñ2rQcƒóÂ"\'dAVPR.4pVPRR4p\P!RWV4RR/#Rp\ ^\
^,4p\ P!4p\P!\P!\PPV4\R7GRjxL
p\ P!4V,
R,p \V\ 4'dVPR4MRp
\P"!R Y!VPR4T\
Yš;'gR
4T;'g/u# VfQhVhL  \$Edap T p\ P!4T,
R,p \'T R R4;'g\'T R R4p \T \(4;'d$R
T u;8*;'dR8Mu;'dT R8gp
\P!RY!T\
T \+T 4P,Y¼RR7
T
'd \P"!RY!T 4Rp ? T\
8Xd Rp ? EK^T^,
,\.P0!^R4,p\P"!RY!T4\P2!T4GRjxL
Rp ? EKoRp ? ii;i5i)ÚtoÚsubjectz (no subject)u7[DEV] skipping email send — label=%s to=%s subject=%rÚidzdev-modeN)Útimeoutr°z1[%s] %s sent to %s (attempt %d/%d, %.0fms, id=%s)zn/ar Úcoder8rmz?[%s] %s send failed (attempt %d/%d, %.0fms): %s: %s (status=%s)Tr:z2[%s] %s: non-retryable status %s, aborting retriesgš™™™™™Ù?z[%s] retrying %s in %.2fs)r%r‡r;rÚranger/rnÚwait_forréÚresendÚEmailsr‰r'r}rrrrr™ÚrandomÚuniformÚsleep)r[r[rkrHrIÚlast_excÚattemptr¹Úresultr»Úemail_idr“r$Ú
non_retryableÚbackoffs&&& rOÚ _send_emailrZÝsFé߃xØ
[‰[˜˜
Ø—+‘+˜i¨ÓÜŠÐPÐRWÐ]dÔ!à!%€Hä˜ÔÕÜ—."ˆð$ )Ü"××!¤&§-¡-×"4Ñ"4°gÓ÷ˆFôŸ.š.Ó*¨WÕ4¸Õ<ˆJÜ+5°f¼d×+CÒ+Cv—zz ˆ KŠKØ 7§;¡;¨tÓ#4°gÔ?PØ×ô
ð
2026-06-17 21:51:29 +12:00
—<<˜ ñ3ðP Ò ÐÐ Ø
€NñMøôõˆHÜŸ.š.Ó*¨WÕÕ<ˆ˜S Ó6×T¼'À#ÀvÈtÓ:Tˆ˜6¤3Ó'×Q¨C°6×,?Ô,?¸CÔ,?×QÀFÈcÁMð
2026-05-18 22:25:43 +12:00
ô
2026-06-17 21:51:29 +12:00
NŠNØ 7Ô,=¸S“ ×" õ 
2026-05-18 22:25:43 +12:00
÷ Ü Ø vôöØÔؘW q)¬V¯^ª^¸A¸sÓ-CÕCˆGÜ KŠKÐ3°ZÈÔ —-’- Ó (ûð/ )üs‰A>KÂA E0Ã
E.ÃBE0ÅE0ÅE0Å!
KÅ.E0Å0 KÅ<AKÇKÇ)KÇ8AKÉKÉ KÉ%KÉ-AKË
K
2026-06-17 21:51:29 +12:00
Ë KËKËKËKcó$V^8„dQhR\/#rsr)rNs"rOrPrPs÷ñÔ(9ñrQcó\\P!4R,4p\R/RRbRRbRRbRRbR R
bR R bR
RbRRR.bRVR,
bRVR,
bRVR ,
bRVR!,
bRVbR^bR.R"ObRRbRRbp\V4V#)#r°rÿzSarah Thompsonrïzsarah.thompson@example.comrz 021 555 0142rÚMilorz Grey LynnrzÉMilo is a 2-year-old cavoodle with good recall and a friendly nature. He loves other dogs, is comfortable off lead in safe areas, and we are looking for regular weekday pack walks while we are at work.rz
Pack Walksz Puppy Visitsrér r r
rrrrz=https://www.google.com/search?q=goodwalk+auckland+dog+walkingrz2https://www.goodwalk.co.nz/book?service=pack-walksr¹iPø i(|iâ)Ú/z /pack-walksz /our-pricingz/book)r@r)Únow_msÚsamples rOÚ_build_startup_test_submissionraÜ
˜
$€Fä
òÙðáññð ñ
ð ñ ð
ñ
Kðð ÑðÐ 9ÖðÐ!;ÖðÐ 8Öð "Ð%>Ö?ð!ñ"ð#ñ$ð%ó&>ð'ñ(Qð)ñ*Bð+€Fô.˜ €MrQcóV^8„dQhRR/#r¸)rNs"rOrPrP0s÷RñR¨ñRrQcƒóJ"\'g\P!R4R#Rp\4pR\R\.R\ VP 4RRVP RVP R 2R
\VR R \ R 24/p\VR
VR7GRjxL
2026-05-18 22:25:43 +12:00
R#L5i)zBStartup test email skipped: OWNER_BCC is not set to a real addressNz startup-testÚfromrHÚreply_torIu*Startup preview — New GoodWalk lead — ú)r.z 127.0.0.1zStartup Preview (Ústartup_test_email©r[rk) r9r;rar+rvrÿrr¸rrZ)rkr`r[s rOÚ_send_startup_test_emailrj0séß  Š Ðà€JÜ
-€Fà
2026-06-17 21:51:29 +12:00
Ø Ô”C˜Ÿ ÓÐÇÁÐ?PÐPRÐSY×SaÑSaÐRbÐbcÐ ˜F KÐ3DÄ[ÀMÐQRÐ1SÓ €Gô gÐ%9ÀjÔ
Q×QùsBB#ÂB!ÂB#cóV^8„dQhRR/#r¸)rNs"rOrPrPDs÷lñl lrQcƒóæ"\P!\R4GRjxL
\P!R4R#L \
d#p\P !RT4Rp?R#Rp?ii;i5i)zImport WeasyPrint and run a trivial render to surface native-lib issues
(libpango/cairo/etc.) at boot rather than on the first PDF request.z<html><body>ok</body></html>Nu:Startup smoke: WeasyPrint OK — PDF attachments availableuNStartup smoke: WeasyPrint UNAVAILABLE — PDF attachments will be skipped (%s))r5r;rr<s rOÚ_startup_smoke_pdfrmDsZéðlÜ×ÒÔ 0Ð2PÓ Š Ð Røä ôlÜ Š ÐeÐgj×kûðlüs;A1A¢?£A½A1¿AÁ A.Á A)Á#A1Á)A.Á.A1cóV^8„dQhRR/#r¸)rNs"rOrPrPNs÷IñI IrQcƒóT"\P!4'g\P!R4R#\P!4GRjxL
pVf\P!R4R#\P
!4GRjxL
VP
4;_uu_4GRjxL
pVPR4GRjxL
2026-05-19 23:36:58 +12:00
pRRR4GRjxL
2026-06-17 21:51:29 +12:00
X'd7VR,'d(VR,'d\P!R4R#\P!RV'd
2026-05-18 22:25:43 +12:00
VR,MRV'd
VR,MR4R#ELL•L‡ +GRjxL
'giLž;i \d#p\P!R T4Rp?R#Rp?ii;i5i)
2026-05-19 23:36:58 +12:00
z‡Force schema creation at boot and verify the new tables exist so the
2026-05-18 22:25:43 +12:00
activity log isn't silently empty if CREATE permission is missing.uNStartup smoke: postgres disabled — activity/submissions will NOT be recordedNuVStartup smoke: postgres pool unavailable — activity/submissions will NOT be recordedzSselect to_regclass('public.events') as ev, to_regclass('public.submissions') as subÚevru:Startup smoke: pg tables OK — events + submissions readyuRStartup smoke: pg tables MISSING (events=%s submissions=%s) — check CREATE permsz+Startup smoke: pg schema verify FAILED (%s)) r;rÚget_poolÚ_ensure_schemaÚacquireÚfetchrowrÜr<r)ÚpoolÚconnr r“s rOÚ_startup_verify_schemarwNséô × Ò × Ò ÜŠÐðIÜ×(×(ˆØ Š<Ü NŠNÐ Ü×'×—<<—>—>”> Ÿ
2026-05-19 23:36:58 +12:00
Ø÷ˆ"—>÷ 3t—9”9  ¤Ü KŠKÐ LŠLÐmß&)˜˜¨tÇ3°S¸¶ZÈDö
Rò÷"—>—>>ûô ôIÜ Š ÐBÀC×HûðIüsè4F(·E8ÁEÁE8Á.F(Á0E8ÂEÂ E8Â)EÂ*E8Â-EÃEÃEÃ E8ÃEÃ E8ÃE8Ã.E8Ã=E8ÄF(ÄE8Ä.E8ÅE8ÅF(ÅE8ÅE8ÅE8ÅEÅE8ÅE5 Å"E%Å#
E5 Å.E5 Å0E8Å8 F%ÆF ÆF(Æ F%Æ%F(cóV^8„dQhRR/#r¸)rNs"rOrPrPgs÷0Hñ0H 0HrQc
2026-06-17 21:51:29 +12:00
ƒóÀ"\4GRjxL
\4GRjxL
2026-05-18 22:25:43 +12:00
\4GRjxL
2026-05-19 23:36:58 +12:00
\P!4'Edw\ 4GRjxL
2026-06-17 21:51:29 +12:00
p\
V\4'dVs\4GRjxL
2026-05-18 22:25:43 +12:00
p\
2026-06-17 21:51:29 +12:00
V\4'dEVs \'d7\P\P!4P44\!4GRjxL
p\
V\4'dVs\%4GRjxL
pV'd\&P)V4\+4GRjxL
p\
V\4'dVs\.P0!R\3\4\3\4\3\"4\3\&4\3\,44\94GRjxL
\;4GRjxL
\<e\<P?4'd\@PB!\E44s\Fe\FP?4'd!\@PB!\I44s#R#R#ELdELUELFELEEELcEL7 \4d\.P6!R4Läi;i\4d\.P6!R4Lêi;i5i)Nz\Admin state refreshed from postgres: clients=%d emails=%d drafts=%d sessions=%d scheduled=%dz=Admin state refresh from postgres failed; using JSON snapshotzStartup test email failed)%rmrwr}rrurr1rr‰r~rKrr2r;rrjÚ_birthday_auto_taskÚdonerèÚ create_taskÚ_birthday_auto_sender_loopÚ_scheduled_taskÚ_scheduled_sender_loop)Ú
db_clientsÚ db_emailsÚ db_draftsÚ db_sessionsÚ db_scheduleds rOrTrTgséô Ó
×ÐÜ
Ó
"×
×Ò×Óð ^Ü<×<ˆ˜*¤d×+Ø#-Ð Ü:ˆ˜)¤S×)Ø"+ß“;Ü#× ×(9Ò(9Ó(;×(AÑ(AÓ(CÔ2×2ˆ˜)¤T×#Ü ;Ó =×=ˆÜ × Ô4Ü!=Ó!?×?ˆ˜,¬×-Ø$0Ð KŠKØÔ%¤s¬?Ó';¼SÄ»\Ì3ÔO_ÓK`ÔbeÔfwÓbxô
ô
)×(×Ò"Ô&9×&>Ñ&>×&@Ò&@Ü%×1Ô2LÓ2NÓÜÒ¤/×"6Ñ"6×"8Ò"8Ü!×-Ô.DÓ.FÓñ#9òWÚ 
@øôô ^Ü × Ò Ð  ^úñ )øÜ ô×ÒÐ6üs KI4K¢I7£K´I:µKÁ
J Á#I=Á$)J Â
JÂ'J Â6AJ Ã9JÃ:)J Ä#JÄ$ J Ä0"J ÅJ ÅA8J Ç
KÇJ3ÇKÇ
J7Ç+J5Ç,J7Ç0!KÈ?KÉ#KÉ7KÉ:KÉ=J ÊJ ÊJ ÊJ Ê J Ê !J0Ê-KÊ/J0Ê0KÊ5J7Ê7!KËKËKËKcóV^8„dQhRR/#r¸)rNs"rOrPrPšs÷

(¨$ñ
(rQcƒóè"RFJp\4PV4pVfK"VP4VGRjxL
R\4V&KL R#L \PdL,i;i5i)rzN)rzr~)Úglobalsr‡ÚcancelrèÚCancelledError)Ú task_nameÚtasks rOrUrUšseéã?ˆ Üy}‰}˜YÓØ Ô Ø K‰KŒMð
2026-05-19 23:36:58 +12:00
Ø
ð$(ŒGI ó@ñ
2026-05-19 23:36:58 +12:00
øÜ×
Ùð
2026-06-17 21:51:29 +12:00
üs= A2§A2¸A½A¾AÁA2ÁAÁA/Á,A2Á.A/Á/A2z/healthcó$V^8„dQhR\/#rs)rNs"rOrPrP§s÷ñ”dñrQcƒó"RR/#5i)r$Úokr¹rQrOÚhealthr¦séà  Ðùscó<V^8„dQhR\R\R\/#)rLrLr\r)rNs"rOrPrP«s!÷) ñ) œCð) ¤sð) ¬sñ) rQcó8R\ RV R\^<, R2#)a¿<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1">
<title>Your Goodwalk login code</title>
</head>
<body style="margin:0;padding:0;background:#f2f2f0;">
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" style="background:#f2f2f0;padding:40px 16px;">
<tr><td align="center">
<table width="480" cellpadding="0" cellspacing="0" role="presentation"
style="max-width:480px;width:100%;border-radius:16px;overflow:hidden;box-shadow:0 4px 24px rgba(0,0,0,0.08);">
2026-05-19 23:36:58 +12:00
<tr>
<td style="background:#213021;padding:32px 40px;text-align:center;">
<img src="aÊ" width="161" height="32" alt="Goodwalk" style="display:inline-block;max-width:161px;height:auto;border:0;">
</td>
</tr>
<tr>
2026-05-19 23:36:58 +12:00
<td style="background:#ffffff;padding:40px 40px 36px;text-align:center;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:13px;font-weight:700;letter-spacing:0.1em;text-transform:uppercase;color:#888;margin-bottom:16px;">Your login code</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:52px;font-weight:800;letter-spacing:0.18em;color:#213021;background:#f8f7f4;border-radius:14px;padding:20px 28px;display:inline-block;margin-bottom:24px;">aŽ</div>
2026-06-17 21:51:29 +12:00
<p style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:15px;color:#666;line-height:1.6;margin:0 0 8px;">
Enter this code on the Goodwalk onboarding page.
</p>
<p style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:13px;color:#aaa;margin:0;">
This code expires in aë minutes. If you didn&rsquo;t request this, you can safely ignore it.
</p>
2026-05-19 23:36:58 +12:00
</td>
</tr>
<tr>
<td style="background:#213021;padding:20px 40px;text-align:center;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:12px;color:#5a8a5a;">
Goodwalk &middot; Auckland, New Zealand
2026-06-17 21:51:29 +12:00
</div>
</td>
2026-05-19 23:36:58 +12:00
</tr>
2026-06-17 21:51:29 +12:00
</table>
</td></tr>
</table>
</body>
</html>)r-r)rLs&&rOÚ_auth_code_emailr«sEðô !Að BFðAGðG
2026-05-19 23:36:58 +12:00
%:¸RÕ$?Ð#@ðAð3( ð( rQcó0V^8„dQhR\R\/#r5r)rNs"rOrPrP×s÷ñœcð¤cñrQcóÀ\V4pV'gR#\P!V4pVP RVP R4 2# \
dTu#i;i)zTo be confirmedÚ z%b %Y)rr;Údayr¨r<r>s& rOÚ_format_date_labelr—×sYÜ
5‹/€Cß Ù ðÜ×Ó,ˆØ—*‘*˜Q˜vŸ¨wÓ9øÜ ôØŠ
ðús—5A
2026-06-17 21:51:29 +12:00
Á
2026-05-19 23:36:58 +12:00
AÁAc ó`V^8„dQhR\R\R\R\R\R\/#)rLÚ client_nameräÚ service_typeÚ
price_detailsÚ
start_dater\r)rNs"rOrPrPâs9÷8 ñ8 ¬#ð8 ¼ð8 ÌCð8 Ô`cð8 Ôqtð8 Ôy|ñ8 rQcó8VP4'dVP4^,MRpVP4'dRV 2MRp\V4pR\ RT RT;'gR RV R \ R
2026-06-17 21:51:29 +12:00
V4 R \ R V4 R \ R
V4 R2#)rÚthereríry<!DOCTYPE html>
2026-05-18 22:25:43 +12:00
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1">
<title>Welcome to the pack</title>
2026-05-19 23:36:58 +12:00
</head>
<body style="margin:0;padding:0;background:#f2f2f0;">
2026-06-17 21:51:29 +12:00
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" style="background:#f2f2f0;padding:28px 12px;">
<tr><td align="center">
<table width="560" cellpadding="0" cellspacing="0" role="presentation" style="max-width:560px;width:100%;border-radius:22px;overflow:hidden;box-shadow:0 10px 32px rgba(17,20,24,0.08);">
<tr>
<td style="background:#213021;padding:28px 24px;text-align:center;">
<img src="aÜ" width="161" height="32" alt="Goodwalk" style="display:inline-block;max-width:161px;height:auto;border:0;">
</td>
2026-05-18 22:25:43 +12:00
</tr>
<tr>
<td style="background:#fbfaf7;padding:34px 24px 30px;">
2026-05-19 23:36:58 +12:00
<div style="display:inline-block;background:#ffd100;border-radius:999px;padding:8px 14px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:12px;font-weight:700;color:#213021;letter-spacing:0.06em;text-transform:uppercase;">
Welcome to the pack
</div>
<h1 style="margin:18px 0 12px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:32px;line-height:1.05;letter-spacing:-0.03em;color:#171b20;">
2026-06-17 21:51:29 +12:00
Hi z, we&rsquo;d love to get úyour dogzø started with Goodwalk.
2026-05-18 22:25:43 +12:00
</h1>
<p style="margin:0 0 20px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:15px;line-height:1.7;color:#4b584b;">
We&rsquo;ve set aside the details belowaÈ. When you&rsquo;re ready, complete your onboarding form and we&rsquo;ll take it from there.
</p>
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" style="background:#ffffff;border-radius:18px;border:1px solid rgba(33,48,33,0.08);margin-bottom:22px;">
<tr><td style="padding:22px 20px;">
<table width="100%" cellpadding="0" cellspacing="0" role="presentation">
ÚPriceú
Start datea
2026-06-17 21:51:29 +12:00
</table>
2026-05-18 22:25:43 +12:00
</td></tr>
2026-06-17 21:51:29 +12:00
</table>
2026-05-18 22:25:43 +12:00
<a href="https://clients.goodwalk.co.nz/" style="display:inline-block;background:#213021;color:#ffffff;text-decoration:none;border-radius:999px;padding:14px 20px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:15px;font-weight:700;">
Complete onboarding
</a>
2026-06-17 21:51:29 +12:00
2026-05-18 22:25:43 +12:00
<p style="margin:18px 0 0;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:14px;line-height:1.7;color:#657365;">
Use the same email address you originally used with Goodwalk. We&rsquo;ll send you a one-time code when you sign in.
</p>
</td>
</tr>
2026-06-17 21:51:29 +12:00
</table>
</td></tr>
2026-05-18 22:25:43 +12:00
</table>
2026-06-17 21:51:29 +12:00
</body>
2026-05-18 22:25:43 +12:00
</html>)r‰rˆr—r-r_)r™rÚdog_lineÚformatted_start_dates&&&&& rOÚ_welcome_pack_email_htmlr¤âØ+6×+<Ñ+<×+>Ò+>×$ 'ÀG€JØ%-§^¡^×%5Ò%5x!¸2€HÜ-¨jÓð
ô !ðÐ6°x×7MÐ7MÀ:Ð6NðO7?°Zð@ô ˜y¨,Ó9ܘw¨
Ó8ܘ|Ð-AÓDðC3 ð3 rQcó0V^8„dQhR\R\/#)rNs"rOrPrP s÷] ñ] Ô.Bð] Äsñ] rQcóœVPP4'd"VPP4^,MRp\VP4pVP
Uu.uFCp\
2026-06-17 21:51:29 +12:00
V\4'gKVP4'gK3VP4NKE ppV'dRPVR,4MRp\V4^8”dVR\V4^,
R2,
2026-05-18 22:25:43 +12:00
pRpRpR \VR
R 7 R T R
V'dRV 2MR RVP RT;'gR RV RV R2#uupi)r:NrLNzyour selected servicez + z morezhttps://clients.goodwalk.co.nz/a <div style="display:inline-block;background:#ffd100;border-radius:999px;padding:8px 14px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:12px;font-weight:700;color:#213021;letter-spacing:0.06em;text-transform:uppercase;">Submitted</div>aV<!DOCTYPE html>
2026-06-17 21:51:29 +12:00
<html lang="en">
2026-05-18 22:25:43 +12:00
<head>
2026-06-17 21:51:29 +12:00
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1">
<title>Your onboarding has been submitted</title>
</head>
<body style="margin:0;padding:0;background:#f2f2f0;">
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" style="background:#f2f2f0;padding:28px 12px;">
2026-05-18 22:25:43 +12:00
<tr><td align="center">
<table width="560" cellpadding="0" cellspacing="0" role="presentation" style="max-width:560px;width:100%;border-radius:22px;overflow:hidden;box-shadow:0 10px 32px rgba(17,20,24,0.08);">
z*Your onboarding details are safely with usrÀa
<tr>
<td style="background:#fbfaf7;padding:34px 24px 30px;">
<h1 style="margin:0 0 12px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:32px;line-height:1.05;letter-spacing:-0.03em;color:#171b20;">
Thanks, zù. Your onboarding is complete.
</h1>
<p style="margin:0 0 20px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:15px;line-height:1.7;color:#4b584b;">
2026-06-17 21:51:29 +12:00
We&rsquo;ve received your detailsrírya5 and they&rsquo;re now on file with Goodwalk.
2026-05-18 22:25:43 +12:00
You can sign back in any time to review what you submitted.
</p>
2026-06-17 21:51:29 +12:00
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" style="background:#ffffff;border-radius:18px;border:1px solid rgba(33,48,33,0.08);margin-bottom:22px;">
<tr><td style="padding:22px 20px;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:11px;font-weight:700;letter-spacing:0.1em;color:#888;text-transform:uppercase;margin-bottom:16px;">
2026-05-18 22:25:43 +12:00
Snapshot
</div>
<div style="display:grid;gap:14px;">
<div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:12px;font-weight:700;color:#7b867b;text-transform:uppercase;letter-spacing:0.08em;margin-bottom:4px;">Owner</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:18px;font-weight:700;color:#171b20;">a§</div>
</div>
<div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:12px;font-weight:700;color:#7b867b;text-transform:uppercase;letter-spacing:0.08em;margin-bottom:4px;">Dog</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:18px;font-weight:700;color:#171b20;">zDetails submitteda¬</div>
</div>
<div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:12px;font-weight:700;color:#7b867b;text-transform:uppercase;letter-spacing:0.08em;margin-bottom:4px;">Services</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:16px;line-height:1.5;color:#425042;">a</div>
</div>
</div>
</td></tr>
</table>
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" style="border-left:3px solid #ffd100;margin-bottom:24px;">
<tr>
<td style="padding:4px 0 4px 20px;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:13px;font-weight:700;color:#213021;margin-bottom:6px;">
What happens next?
</div>
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:14px;color:#666;line-height:1.65;">
We&rsquo;ll review your submission and come back to you if we need anything clarified.
If you need to check your details again, use the button below to sign back in with a one-time code.
</div>
</td>
</tr>
</table>
<a href="aò" style="display:inline-block;background:#213021;color:#ffffff;text-decoration:none;border-radius:999px;padding:14px 20px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:15px;font-weight:700;">
2026-06-17 21:51:29 +12:00
Review your submission
</a>
2026-05-18 22:25:43 +12:00
<p style="margin:18px 0 0;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:14px;line-height:1.7;color:#657365;">
Your submitted form is read-only after completion. If anything needs changing, just reply to this email or contact us directly.
</p>
</td>
</tr>
<tr>
<td style="background:#213021;padding:24px 48px;text-align:center;">
<div style="font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:12px;color:#5a8a5a;line-height:1.6;">
Goodwalk &middot; Auckland, New Zealand
</div>
</td>
</tr>
</table>
</td></tr>
</table>
</body>
</html>) rÿr‰rˆrr,r}rvrvr€)rrÚ
service_namesÚservice_summaryÚonboarding_urlrys& rOÚ#_onboarding_confirmation_email_htmlrª sØ-1¯]©]×-@Ñ-@×-BÒ-B×& qÖ€JܘŸ Ó%€HØ48×4GÒ4GÓxÑ4G¨Ì:ÐV]Ô_b×Kc”_Ðho×huÑhu×hw”_W—]]_Ñ4G€MÐxß6Cd—ii 
¨bÕ 1Ô2ÐI`€OÜ
ˆ=Ó˜AÔØ˜S¤ ]Ó!3°aÕ!7Ð 8¸Ð>ˆà6€Nð jðð  ô
 Ð6bÔ cÐeð"#0÷GO°%¸°zÑ0BÐTVÐ/Wð XSðTX÷TañTaðSbðbSðT\÷TsðTsð`sðStðtSðTcðSdðdð(&ðuN ðN ùòysÁ'E ÂE ÂE có<V^8„dQhR\R\R\/#)rLr™r\r)rNs"rOrPrP} s!÷( ñ( ¤cð( ´( ¼Sñ( rQc óºVP4'dVP4^,MRpVP4;'gRpR\ RV RV RV R2 #)r<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1">
<title>Happy birthday from Goodwalk</title>
</head>
<body style="margin:0;padding:0;background:#f2f2f0;">
<table width="100%" cellpadding="0" cellspacing="0" role="presentation" style="background:#f2f2f0;padding:28px 12px;">
<tr><td align="center">
<table width="560" cellpadding="0" cellspacing="0" role="presentation" style="max-width:560px;width:100%;border-radius:22px;overflow:hidden;box-shadow:0 10px 32px rgba(17,20,24,0.08);">
<tr>
<td style="background:#213021;padding:28px 24px;text-align:center;">
<img src="aæ" width="161" height="32" alt="Goodwalk" style="display:inline-block;max-width:161px;height:auto;border:0;">
</td>
</tr>
<tr>
<td style="background:#fbfaf7;padding:34px 24px 30px;">
<div style="display:inline-block;background:#ffd100;border-radius:999px;padding:8px 14px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:12px;font-weight:700;color:#213021;letter-spacing:0.06em;text-transform:uppercase;">
Happy birthday
</div>
<h1 style="margin:18px 0 12px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:32px;line-height:1.05;letter-spacing:-0.03em;color:#171b20;">
Happy birthday to z¾.
</h1>
<p style="margin:0 0 18px;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:15px;line-height:1.7;color:#4b584b;">
Hi zE, sending a little birthday love from all of us at Goodwalk. We hope aJ has a very good day.
</p>
<p style="margin:0;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',sans-serif;font-size:15px;line-height:1.7;color:#4b584b;">
Aless and the Goodwalk pack
</p>
</td>
</tr>
</table>
</td></tr>
</table>
</body>
</html>)r‰rˆr-)r™s&& rOÚ_birthday_email_htmlr­} swØ+6×+<Ñ+<×+>Ò+>×$ 'ÀG€JØ—^%×€Nð
ô !!ð"0Ð 0ð1ðÐbÐcqÐbrð sð3$ ð$ rQcó>V^8„dQhR\R\R,/#)rLÚtodayNr6)rNs"rOrPrP¨ s÷ñ¬Cð¼À4½ñrQcó\V4pV'gR#\P!VR4P4pT;'g\P
2026-06-17 21:51:29 +12:00
!4P4pTP pTPTR7pYd8dT^,
2026-05-18 22:25:43 +12:00
pTPTR7pT#T# \dR#i;i \dTPT^^R7pKZi;i \dTPT^^R7pT#i;i)Nrè)Úyear)Úmonthr)rr<ro)r?Ú
birth_dateÚ
today_dateÚ target_yearÚ candidates&& rOÚ_upcoming_birthday_dater·¨ sÜ

"€Cß ÙðÜ×& s¨JÓ7×>ˆ
ð×)œ8Ÿ<š<>×1€JØ—//€Kà
ð Ø"× Ð<ˆ ð ÔØˆ ð NØ"× Ð<ˆ Ј9Ðøô- ôÚðûôô à"× À1È"ÐMˆ ð ûôô NØ"× À1È"ÐM‰Ià Ðð Nús5—%B0Á7CÂC(Â0 B?Â>B?ÃC%Ã$C%Ã(D Ä
D cójV^8„dQhR\\,R,R\\,/#)rLÚ requestedNr\rt)rNs"rOrPrPÈ s'÷

$¬4´­9°tÕ+;ð
ÄSÅ ñ
$rQcóò\Uu0uFBq'gK VP4'gK$VP4P4kKD pp.pT;'g.FUp\V4P4P4pV'gK4WR9gK<WS9gKDVP V4KW V'dV#\
P!4P4pV'dV.#.#uupirS)r#r‰r~rvr1)rBÚallowedÚresolvedr?Úowners& rOÚ_resolve_preview_recipientsr¾È Ý0?Ó¨Ã4Ô#ÈDÏJÉJÏLÔ#ˆtz‰z‹|×€GЀH؈˜BŠˆÜC“Ó ×(ˆß ‰5%¨%Ö*?Ø O‰O˜ ÷ØˆÜ × Ò Ó × '€E߈Eˆ# Ð#ùòZs‰ C4C4¯"C4có–V^8„dQhR\R\R\R\R,R\R\\,R,RR/#) rLrkÚmark_auto_yearNÚpreviewÚpreview_recipientsr\)rvrr!)rNs"rOrPrPÕ s[÷## ð#
ð#ð#˜$•Jð #
ð # œS  
#
ñ#7rQc
2026-06-17 21:51:29 +12:00
ƒó˜"\VPRR44P4p\VPRR44P4pV'd \V4MV.pRT;'gR 2p V'dRT;'gT RV 2p R\RVR \
R
2026-05-18 22:25:43 +12:00
V R \
Wg4/p
\4p V 'd
V'gWºR &\Y¤'dR
MRVR7GRjxL
V'dR#R\P!4PRR7/p Ve\V4V R&\W 4GRjxL
R#L\L5i)rÿryrzHappy birthday z
from Goodwalkú
[PREVIEW for ú] rdrHrerIr.ÚbccÚbirthday_email_previewÚbirthday_emailribirthdayEmailLastSentAtr`raÚbirthdayEmailLastSentYear)
rvr‡r‰r+r6r­rErZrrdr/)
rkr™Ú
recipientsrIr[Úprofile_updates
&&&&&& rOÚ _send_birthday_email_for_profilerÍÕ s8éôg—k‘k *¨bÓ2×:€KÜ7—;;˜y¨"Ó.×6€HßDKÔ,Ð-?Ô@ÐRWÐQX€JØ × ;Ð ;¨OÐ=€Gߨ! +×"6Ð"6°Ð!7°r¸'¸ÐCˆà
Ø ˆjØ”HØÔ$ [Ó €Gô Ó
€Cß
—7Øä
Ñ%=ÐN^ÐkuÔ
v×Ùð "¤8§<¢<£>×#;Ñ#;ÀYÐ#;Ó#Oð€NðÒ!Ü69¸.Ó6IˆÐ
2026-06-17 21:51:29 +12:00
 Ó
2026-05-18 22:25:43 +12:00
6×wñ7ùsCA2E
2026-06-17 21:51:29 +12:00
Á5 E
2026-05-18 22:25:43 +12:00
 E
 >E
à E
Ã)EÃ* E
Ã6A E
2026-06-17 21:51:29 +12:00
Ä?EÅE
2026-05-18 22:25:43 +12:00
ÅE
cóV^8„dQhRR/#r¸)rNs"rOrPrPû s÷^ñ^¨dñ^rQc ƒó‚"\P!4P4pVPVP3p\ \ P44EF(wr#VPR4'gKVPR4'gK8\\VPRR444pV'dVPVP3V8wd\VPRR44P4pV\VP48XdR\P!4PR, 2p\!W#W`PR7GRjxL
2026-06-17 21:51:29 +12:00
\"P$!R Wb4EK+ R#L" \&d&p\"P(!R
YgR R 7Rp?EK\Rp?ii;i5i)
r[ÚbirthdayAutoSendr"ryzbirthday-auto-ºNéN)Nz'[%s] auto birthday email sent: email=%sz#[%s] auto birthday email failed: %sTr:)rrr¿r‡rvr‰r;rr<)Útoday_month_dayrïÚupcomingÚlast_sent_yearrkr“s rOÚ_run_birthday_auto_sender_oncerÖû sGéÜ LŠL‹N× Ñ Ó !€EØ—{‘{ E§I¡IÐ.€OäÔ8‰ˆØ{‰{Ð Ø{‰{Ð ä*¬3¨w¯{©{¸8ÀRÓ/HÓ+IÓJˆß˜HŸN™N¨H¯L©LÐ9¸_Ô ä˜WŸ[™[Ð)DÀbÓØ œS §¡›_Ô à%¤d§j¢j£l×&6Ñ&6°rÕ&:Ð%;Ð<ˆ
2026-05-19 23:36:58 +12:00
ð ^ÜÀ×\fÑ\fÔg×
2026-06-17 21:51:29 +12:00
2026-05-18 22:25:43 +12:00
2026-06-17 21:51:29 +12:00
+Š+Ð×
Só# høäô ^Ü
,Š,Ð<¸jÐX\×
]ûð ^üsIBF?ÂB;F?Å
F Å'F
Å(F ÆF?Æ
F Æ F<ÆF7Æ0F?Æ7F<Æ<F?cóV^8„dQhRR/#r¸)rNs"rOrPrP
s÷=¨$ñ=rQcƒóú"\4GRjxL
\P !\4GRjxL
K8L( \Pdh\d\P
!R4L^i;iLD5i)TNz Birthday auto sender loop failed)r‰rr;rSrrQrOr}r}
shéØ
ð AÜ2×
2026-05-19 23:36:58 +12:00
mŠmÔ<×
2026-06-17 21:51:29 +12:00
3øÜ× Ø Üô AÜ × Ò Ð  Aúá<ùóAA;
=;=A;´A9µA;»=½A6ÁA6Á3A;Á5A6Á6A;z^[^\s@]+@[^\s@]+\.[^\s@]+$z/auth/request-codecó$V^8„dQhR\/#)rNs"rOrPrP$
s÷AñA¤WñArQc
2026-05-19 23:36:58 +12:00
ƒó"\VPR\P!4PR,4p\ V4pVP
2026-06-17 21:51:29 +12:00
4GRjxL
p\P!VPR4;'gR4p\TP!R
R 44P#4P%4p\&;_uu_4GRjxL
2026-05-19 23:36:58 +12:00
\)Y!4RRR4GRjxL
2026-06-17 21:51:29 +12:00
T'd\*P-T4'g(\P!R TTTT4\RR
R 7hT\.9dY\P0!RYT4\&;_uu_4GRjxL
\3Y!R4RRR4GRjxL
\RRR 7h\4P6!4p\&;_uu_4GRjxL
\8P;T\=44pT'd'Yg^,,
2026-05-18 22:25:43 +12:00
R8”dTP?4K.\AT4\Bd\RRR 7hTPET4\\FPH!R4R,4pRTR\4P4!4\J,R^/\LT&RRR4GRjxL
2026-06-17 21:51:29 +12:00
\P0!RY4\N'd\P!RTX4M-\QR\RRT.RRR \UTX4/R!TR"7GRjxL
2026-05-19 23:36:58 +12:00
\VPX!R#YTR$R%7GRjxL
R$R&/#E\\P3d/\P!RTTTR,4\RRR 7hi;iEL¸EL  +GRjxL
'giEL¸;iEL<EL# +GRjxL
'giEL;;iEL
2026-06-17 21:51:29 +12:00
EL, +GRjxL
'giELD;iLÂ5i)'rkNrbz{}z1[%s] auth: invalid json payload ip=%s raw_body=%rºNiôNr8zInvalid request payload.r
ryzB[%s] auth: invalid email payload ip=%s body=%r normalized_email=%rz#Please enter a valid email address.z![%s] auth: unknown email=%s ip=%sÚ
unknown_emailru‡We don’t have your email on file. Please use the address you used when enquiring with Goodwalk, or contact us at info@goodwalk.co.nz.irmz8Too many code requests. Please wait before trying again.i »
i †rLz#[%s] auth: code issued for email=%sz[DEV] auth code for %s: %srdrHrIzYour Goodwalk login coder.Úauth_code_emailriÚauth_code_requestedrŽ©Ú
2026-05-18 22:25:43 +12:00
event_typerkÚ actor_emailrjr$T)-rr´rjr”ÚUnicodeDecodeErrorÚJSONDecodeErrorr;rr rvr‡r‰r~rrrÚ _EMAIL_REÚmatchrrzrnrMrwrrxrÚ randbelowrrLr%rZr+rÚ record_event) rrkrjÚraw_bodyrŽÚrequestsrLs & rOÚauth_request_coderë#
2026-06-17 21:51:29 +12:00
é䘟¨ ´d·j²j³l×6FÑ6FÀrÕ6JÓK€JÜ Ó €BØ—\‘\“^×#€Hð PÜzŠz˜(Ÿ/™/¨'Ó2×:°dÓ;ˆô
˜  &× .× 6€EçzŽzܘ œ Ÿ¨×ŠØ Ø Ø Ø ô 
ô¨Ð4YÔ ”OÔ Š ÐÈBÔ—:–:Ü  °Ô —:äØð]ô
2026-05-18 22:25:43 +12:00
ð
ô
2026-06-17 21:51:29 +12:00
.Š.Ó
€CßzŽzÜ!×,¨U´E³GÓߘ3¨!¥Õ,¨tÔ × Ñ Ö Ü ˆx‹=Ô ¨CÐ8rÔ ˜Ôä”7×$ VÓ,¨vÕ6ˆØ!'¨¨|¼T¿YºY»[ÔK`Õ=`ÐblÐnoÐ pŒ÷ ‡K‚KÐ5°zÔƒxÜŠÐ3°U¸DÕØ
”Z ¨ w° Ð;UÐW]Ô_oÐpuÐw{Ó_|Ð 
÷
ð
ô ×
Ò
ذRÀô ÷ðð
$ˆò}$øô
¤× 4Ñ 4Ð PÜŠØ Ø Ø T
ô ¨Ð4NÔPú÷zzzú÷—:—:—:ú÷zzzúñ 
ñ ùs=AO?ÁMÁO?Á"'MÂ
MÂA O?ÃNÃO?Ã NÃ* O?Ã5NÃ6 O?ÄO?ÄAO?Å9N5Å:O?Å=
N;Æ
O?ÆN8Æ8O?ÇOÇO?Ç&OÇ9B+OÊ$ O?Ê/OÊ0A(O?ÌO;Ì!O?Ì:O=Ì; O?ÍA NÎO?ÎO?ÎN2 ÎN!Î
N2 Î*N2 Î,
O?Î8O?Î;O ÏOÏ
O Ï
O Ï
O?ÏO?ÏO8 Ï$O'Ï%
O8 Ï0O8 Ï2
O?Ï=O?z/auth/verify-codecó$V^8„dQhR\/#)rNs"rOrPrPi
s÷++8¤Gñ+8rQc
ƒóð"\VPR\P!4PR,4p\ V4pVP
4GRjxL
p\VPRR44P4P4p\VPRR44P4p\;_uu_4GRjxL
\W!4\PV4pV'g\W!R4\RRR 7h\ P !4VR
,8”d0\P#VR4\W!R 4\RR R 7hVR
;;,^,
uu&VR
,\$8”d0\P#VR4\W!R4\RRR 7hVR,V8wdH\'^\$VR
,,
4p\W!R4\RRT RV^8wdRMR R2R 7h\P#VR4\(P*!^ 4pRVR
\ P !4\,,/\.V&RRR4GRjxL
\14GRjxL
\2P4!RW4\6P8!RWVRR7GRjxL
RRRXRV/#ELrEL] +GRjxL
'giLt;iLiL25i)rkNrïryrLÚno_pending_coder8z7No code found for this email. Please request a new one.r
Ú expired_codez0Your code has expired. Please request a new one.rÐÚmax_attempts_exceededz7Too many incorrect attempts. Please request a new code.Ú
wrong_codezIncorrect code. z attemptrÄz remaining.z'[%s] auth: session created for email=%sÚ
auth_loginrŽTr)rr´rjrvr‡r‰r~rrrrLrzr rrÚ
token_urlsaferr;) rrkrjrLrSrqrs & rOÚauth_verify_coderôh
s`é䘟¨ ´d·j²j³l×6FÑ6FÀrÕ6JÓK€JÜ Ó €BØ× €DÜ ˜  &× .× 6€EÜ ˆtx‰x˜ Ó ,€DçzŽzܘ ×$ çÜ  Ð1BÔ ¨CÐ8qÔ 9Š9‹;˜ Õ × Ñ ˜u dÔ  °Ô ¨CÐ8jÔ 
טqÕ ÓØ  Ô!7Ô × Ñ ˜u dÔ  Ð1HÔ ¨CÐ8qÔ 6?˜ ˜5¸À
Õ8KÕLˆ  °Ô ¨CÐ:JÈ9È+ÐU]ÐenÐrsÔesÑ^aÐy{Ð]|ð}Hð9IôJð
Jä×ј5 ×% )ˆØ#*¨E°<ÄÇÂÃÔOgÕAgÐ"hÔ˜Ñ÷9zô<
'×
‡K9¸
×
Ò
ØØ°RÀô ÷ðð
 ¨°Ð 7òQ ÷zzzúñ<ùs€AK6ÁKÁA6K6ÃKÃK6ÃFKÉ+ K6É6KÉ7K6ÊK2Ê 8K6ËK4Ë
2026-05-19 23:36:58 +12:00
K6ËK6ËK6ËK/ ËKË
K/ Ë(K/ Ë* K6Ë4K6z /auth/verifycó$V^8„dQhR\/#)rNs"rOrPrP˜
2026-06-17 21:51:29 +12:00
s÷ ñ œwñ rQcƒóÜ"\V4GRjxL
p\PV/4p\PV/4pRRRVRVRVRV\9R\
2026-05-19 23:36:58 +12:00
R\
\4/#LX5i) NrŽTrïrRÚcpAdminÚ
2026-06-17 21:51:29 +12:00
ownerEmailÚ
2026-05-19 23:36:58 +12:00
previewEmails)rr‡rKr#r1r—)rrRs& rOÚ auth_verifyrú
spéäÓ1× 1€EÜ×" 5¨"Ó-€GÜ K‰K˜˜ "€Eà ˆdØØØ5œOÑ”kØœ¤Ó ðñ
2026-06-17 21:51:29 +12:00
2ùsA,A*AA,z /auth/logoutcó$V^8„dQhR\/#)rNs"rOrPrP¨
2026-05-19 23:36:58 +12:00
s÷
ñ
2026-06-17 21:51:29 +12:00
œwñ
rQcƒó*"VPPRR4pVPR4P4pRpV'dy\;_uu_4GRjxL
\
P
VR4p\V\4'dVPR4MRpRRR4GRjxL
\4GRjxL
\P!RV\V4RR7GRjxL
2026-05-18 22:25:43 +12:00
RR/#L”LG +GRjxL
2026-06-17 21:51:29 +12:00
'giL^;iLSL*5i) rryr NrïÚ auth_logoutrŽ)rjr$T)
r
r‡rr‰rrr}r)rrrÚlogged_out_emailr+s& rO§
2026-05-18 22:25:43 +12:00
éà—/‘/×% o°rÓ:€KØ × $ YÓ 7€EØÐß ß—:–:Ü'×+¨E°4Ó8ˆHÜ8BÀ8ÌT×8RÒ8R˜xŸ|™|¨GÔ4ÐX\Ð ÷—:ô
×
2026-06-17 21:51:29 +12:00
Ò
2026-05-18 22:25:43 +12:00
Ø Ø°Ó)9À$ô ÷ðð
$ˆ÷—:—:”:úñùsmADÁC/ÁDÁAC3 DÂ)C1Â*DÂ;DÂ<*DÃ&DÃ' DÃ1DÃ3D Ã9C<Ã:
D ÄD Ä DÄDz/auth/save-draftcó$V^8„dQhR\/#)rNs"rOrPrP¹
s÷ñ¤7ñrQcƒóÜ"\V4GRjxL
pVP4GRjxL
p\VPRR44P 4pVPR/4pVR 9d\ RRR7h\
2026-06-17 21:51:29 +12:00
V\4'g\ RRR7h\;_uu_4GRjxL
\PV/4pWEV&\\4pRRR4GRjxL
\P!\X4GRjxL
2026-05-18 22:25:43 +12:00
\RV4GRjxL
2026-06-17 21:51:29 +12:00
\P !R W4R
R /#EL1ELL•L^ +GRjxL
2026-05-18 22:25:43 +12:00
'giLu;iLYLG5i)
2026-06-17 21:51:29 +12:00
formryrr8z(form must be 'onboarding' or 'contract'.r
zdata must be an object.r¬zDraft saved: email=%s form=%srŽT)Ú
onboardingÚcontract)rrjrvr‡r‰r r}rrrKrwr;)rrrÚ user_draftsrÅs& rOÚauth_save_draftr¸
2026-05-18 22:25:43 +12:00
séäÓ 1€Eà× €DÜ ˆtx‰x˜ Ó $× ,€DØ 8‰8F˜BÓ €Dà ШÐ4^Ô dœD× ¨Ð4MÔzŽzÜ×°Ó Ø Üœ“=ˆ÷
2026-06-17 21:51:29 +12:00
×
Ò
2026-05-18 22:25:43 +12:00
Ô-¨xÓ
2026-06-17 21:51:29 +12:00
8×
2026-05-18 22:25:43 +12:00
˜Ó
2×
2026-06-17 21:51:29 +12:00
‡KÔ $ˆò'
2026-05-18 22:25:43 +12:00
÷zzŒzúñ
2ùsŒE,EE,©EªBE,Â2EÂ3E,Â6*E à E,Ã+E
Ã,"E,ÄE(ÄE,Ä"E*Ä# E,ÅE,ÅE,Å
2026-06-17 21:51:29 +12:00
E,Å E% ÅEÅ
E% ÅE% Å E,Å*E,rJÚnamezGeneral updaterz6Clean Goodwalk branding for everyday news and updates.Úkickerz
From GoodwalkÚ banner_emojiuðŸ¾Úaccentz#ffd100Ú accent_textz#213021Úpage_bgz#f3f0e5Úcard_bgz#fbfaf7Ú
heading_colorz#171b20Ú
body_colorz#4b584bÚ muted_colorz#6b766bÚband_bgÚ band_textÚband_decorationu$🾠· 🾠· 🾠· 🾠· ðŸ¾Ú footer_bgÚ footer_textÚ highlight_bgz#fff8d6Úhighlight_borderÚhighlight_textÚ ornament_topÚornament_bottomÚdefault_subjectzA note from GoodwalkÚdefault_headingzHello from the packÚdefault_sub_headingz*A quick update from your dog walking team.Ú default_bodyzÍThank you for being part of our community. Every wag and woof matters to us, and we have a small update to share.
We're always here if you need to chat about walks, training, or anything else dog-related.Údefault_highlightÚdefault_sign_offzAless & the Goodwalk packÚdefault_footer_noteugoodwalk.co.nz · Auckland, NZÚ christmasÚ Christmasz5Deep green and red festive styling with snow accents.zSeason's greetingsu🎄z#c0392bz#ffffffz#e8dccbz#fbf6ecz#0d3b1ez#3a4a3az#0d4d2au>℠· 🎄 · ℠· 🎠· ℠· 🦌 · ℠· ⭠· â„z#ffe8d6z#fff0eaz#7a1d12uOâ„ â„ â„ â„ â„ â„ â„ â„ â„ â„ â„ â„ â„ â„ â„ â„ â„ â„ â„ â„u$🎄 ⭠🎠🦌 ℠🎠⭠🎄u+Merry Christmas from the Goodwalk pack 🎄z"Wishing you a very woofy Christmasu<From our pack to yours — thank you for an incredible year.a'It's been a year full of muddy paws, sunny walks, and very good dogs. From all of us at Goodwalk, we wish you and your pup a warm, joyful Christmas.
We'll be taking a short break over the holidays and will be back in full swing for the new year. Looking forward to many more adventures in 2026.u?🎠Holiday schedule: walks pause from 24 Dec, resuming 6 Jan.z'Wishing you a warm and joyful ChristmasÚeasterÚEasterz2Soft pastel styling with floral and bunny accents.z Happy EasteruðŸ°z#d8a8dez#3a2a4az#fdf3f8z#5a4a5az#8a7a8az#f5d6e5z#5a2a6bu4🌷 · 🰠· 🌸 · 🥚 · 🣠· 🌷 · 🌸z#e7c9f0z#fff0fau1🌷 🌸 🌷 🌸 🌷 🌸 🌷 🌸 🌷 🌸u🥚 🰠🌸 🣠🥚 ðŸ°u%Hop on into Easter with Goodwalk ðŸ°zA happy, hoppy Easter to youz+Spring is in the air and tails are wagging.aWishing you and your pup a beautiful Easter weekend. May your walks be sunny, your eggs uneaten by curious snouts, and your treats plentiful.
A little reminder: chocolate is not for dogs, no matter how sweetly they ask. We'll be sticking to the good stuff on our walks.uT🣠Keep chocolate well out of reach — even small amounts can be harmful to dogs.zHappy Easter from all of usÚ halloweenÚ Halloweenz&Dark purple and orange spooky styling.zTrick or treatu🎃z#ff7518z#1a0d1fz#2b1838z#ffe8d0z#d8c8d8z#9a8aaaz#0a0410u<🎃 · 👻 · 🕷 · 🦇 · 🌙 · 🕸 · 🎃 · 👻z#4a2b66u1🦇 🕸 🦇 🕸 🦇 🕸 🦇 🕸 🦇 🕸u"🎃 👻 🕷 🌙 🦇 🕸 🎃uSpooky season at Goodwalk 🎃zIt's Howl-oweenz$Costumes optional. Treats mandatory.uúSpooky season is upon us. We'll be out walking with extra vigilance — fireworks, doorbell mayhem, and rogue chocolate are all on our radar.
If your pup is nervous around fireworks or doorbells, let us know and we'll factor it into walks this week.u_🫠Reminder: chocolate, raisins, and xylitol are all toxic to dogs. Keep the treat bowl high.zStay spooky out thereÚpromozSale / promotional offerz@Bright yellow promotional styling with a clear discount callout.z
Limited offeru🦴z#fffaebz#fffdf5u2★ · SPECIAL OFFER · ★ · LIMITED TIME · ★z#fff3a0u;★ ★ ★ ★ ★ ★ ★ ★ ★ ★ ★ ★ ★ ★ ★u🦴 ★ 🾠★ 🦴 ★ ðŸ¾u%A little something from Goodwalk 🦴zA special offer for our packzBecause regulars are family.zÊWe're running a small thank-you offer for our existing clients. As a regular, you're first in line.
Reply to this email or hit the button below to take it up. Offer is limited and won't be around long.u?20% off your next week of walks · Use code PACKLOVE at bookinguLimited time — be quickrWzSystem (clean sans-serif)Ústackú<-apple-system,BlinkMacSystemFont,'Segoe UI',Arial,sans-serifÚlinkÚ
heading_stackzGeorgia,'Times New Roman',serifÚlorazLora (warm serif)z&'Lora',Georgia,'Times New Roman',serifz\https://fonts.googleapis.com/css2?family=Lora:ital,wght@0,400;0,600;0,700;1,400&display=swapÚplayfairz"Playfair Display (editorial serif)zyhttps://fonts.googleapis.com/css2?family=Playfair+Display:wght@400;700;900&family=Source+Sans+3:wght@400;600&display=swapz2'Playfair Display',Georgia,'Times New Roman',serifÚ merriweatherzMerriweather (readable serif)z.'Merriweather',Georgia,'Times New Roman',serifzOhttps://fonts.googleapis.com/css2?family=Merriweather:wght@400;700&display=swapÚcrimsonzCrimson Text (classic serif)z.'Crimson Text',Georgia,'Times New Roman',serifzdhttps://fonts.googleapis.com/css2?family=Crimson+Text:ital,wght@0,400;0,600;0,700;1,400&display=swapÚinterzInter (modern sans)zD'Inter',-apple-system,BlinkMacSystemFont,'Segoe UI',Arial,sans-serifzPhttps://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&display=swapÚ
montserratzMontserrat (geometric sans)zI'Montserrat',-apple-system,BlinkMacSystemFont,'Segoe UI',Arial,sans-serifzUhttps://fonts.googleapis.com/css2?family=Montserrat:wght@400;500;600;700&display=swapÚopensanszOpen Sans (friendly sans)zH'Open Sans',-apple-system,BlinkMacSystemFont,'Segoe UI',Arial,sans-serifzahttps://fonts.googleapis.com/css2?family=Open+Sans:ital,wght@0,400;0,600;0,700;1,400&display=swapc
óTV^8„dQhR\R\R\R\R\/#)rLr+Ú
font_stackrÚ accent_colorr\r)rNs"rOrPrP« s1÷$
ñ$
¤ð$
´ð$
Ä#ð$
ÔUXð$
2026-05-18 22:25:43 +12:00
Ô]`ñ$
2026-06-17 21:51:29 +12:00
rQcóŽa
a ^RIo RV RV R2pRV RV R2pRV RV R2pTpRV R 2o
2026-05-18 22:25:43 +12:00
TpS P!R
R V4pVPR R
4pVPRR4PRR4pRV 3Rllp V !RWH4pV !RWh4pV !RWx4pV !RWX4pS P!RV
2026-06-17 21:51:29 +12:00
3RlVS PR7pV#)zQApply email-safe inline styles to common HTML tags in user-provided body content.Nzmargin:0 0 16px;font-family:ú&;font-size:16px;line-height:1.7;color:Ú;zmargin:0 0 6px;font-family:z1margin:0 0 16px 0;padding:0 0 0 22px;font-family:ú;color:zcolor:z;text-decoration:underline;z <div\b[^>]*>z<p>r|ú</p>rz<br/>z<br />cóHV^8„dQhR\R\R\R\/#)rLÚtagÚstylerr\r)rNs"rOrPÚ&_style_body_html.<locals>.__annotate__¼ s(÷
ñ
”Sð
¤ð
¬Cð
´
rQcóZ<aaSP!RS R2VV3RlVSPR7#)r z (\s[^>]*)?>cóL<RS VP^4;'gR RS R2#)r ryú style="ú">)Úgroup)rgr=r<s&€€rOÚ<lambda>Ú3_style_body_html.<locals>._inject.<locals>.<lambda>¿ s)ø€˜˜#˜˜qŸw™w q›z×/¨Rи%¸ÀÑDrQ©Úflags)rÚ
IGNORECASE)r<r=rsff&€rOÚ_injectÚ!_style_body_html.<locals>._inject¼ s-ú€ØvŠvØ Ø—-‘-ô 
ð
rQrCÚulÚolÚliz
<a(\s[^>]*?)>cóž<RVP^4P49dRVP^4 RS R2#VP^4#)zstyle=z<arArB)rCr~)rgÚa_styles&€rOrDÚ"_style_body_html.<locals>.<lambda>Ê sJø€¸HÈAÏGÉGÐTUËJ×L\ÑL\ÓL^Ô<^Bq—ww˜q“zl )¨G¨9°CÐnÐde×dkÑdkÐlmÓdnÐnrQrF)rrorH) r+r4rr5Ú base_p_styleÚ
base_li_styleÚ
base_ul_styleÚ
base_ol_stylerÄrIrOs &&&& @@rOÚ_style_body_htmlrU« s ù€ã
à1°*°Ð=cÐdnÐcoÐopÐq€LØ1°*°Ð=cÐdnÐcoÐopÐq€MØ
À|ÐSZÐ[eÐZfÐfgÐh€MØ!€MØ|nÐ$?Ð@€Gð €AØ
Šˆ  qÓ)€AØ (˜#€AØ &˜"×*¨8°WÓ=€A÷
ð
ñ %€AÙ'€AÙ'€AÙ'€AØ
ŠØÜ Øm‰mô  €Að
€HrQc
óTV^8„dQhR\R\R\R\R\/#)rLÚ body_textr4rr5r\r)rNs"rOrPrPÒ s1÷ñœSð¬cð¼sðÔRUðÔZ]ñrQcóJaaV'dVP4'gR#RV9dRV9d\VSSV4#VPR4Uu.uF*qDP4'gKVP4NK, ppRPVV3RlV44#uupi)zÑConvert user body input to email-safe HTML.
If the input already looks like HTML (contains a tag), we treat it as HTML and inline-style it.
Otherwise we split on blank lines and wrap each paragraph in a <p>.
ryr r z
c3ó<<"TFpRS RS RV R2xK R#5i)z&<p style="margin:0 0 16px;font-family:r7ú;">r:Nr¹)r€Úpararr4s& €€rOrÚ _body_to_html.<locals>.<genexpr>ß s4øéðáˆDð ° Ð<bÐcmÐbnÐnqÐrvÐqwÐw{Õùsƒ)r‰rUrˆrv)rWr4rr5rCÚpartss&ff& rOÚ
_body_to_htmlr^Ò sˆù€÷ ˜IŸO™O×à
ˆiÔ˜C   ¨:°zÀ<ÓPà )§¡°Ô 7Ó EÑ 7˜1¿7¹7¿9ŒYˆQW‰WŽYÑ 7€EÐ
7‰7õáóó ðùò
Fs ÁB Á.B có0V^8„dQhR\R\/#r5r)rNs"rOrPrPå s÷pñpœðp¤ñprQcóšT;'gRPRR4PRR4PRR4PRR4#) ryrrÚ"z&quot;r r
r r )ros&rOÚ _escape_attrrbå sEØ KˆK Ñ   gÓ 6°s¸HÓ E× MÈcÐSYÓ Z× bÐcfÐhnÓ orQc ó`V^8„dQhR\R\R\R\R\R\/#)rLr[ÚbgÚ
text_colorr4r\r)rNs"rOrPrPé s<÷ ñ œsð ¬ð ´#ð Ä3ð ÔTWð ô^añ rQcóLVP4'dVP4'gR#\VP44pVP4PRR4PRR4PRR4pRV RV R V R
V R V R V R
V RV RV R2#)ryrrr r
r r 
<table role="presentation" cellpadding="0" cellspacing="0" border="0" style="margin:22px 0 6px;">
<tr><td align="left">
<!--[if mso]>
<v:roundrect xmlns:v="urn:schemas-microsoft-com:vml" xmlns:w="urn:schemas-microsoft-com:office:word" href="z\" style="height:48px;v-text-anchor:middle;width:240px;" arcsize="50%" stroke="f" fillcolor="z4">
<w:anchorlock/>
<center style="color:zV;font-family:Arial,sans-serif;font-size:14px;font-weight:bold;letter-spacing:0.04em;">zV</center>
</v:roundrect>
<![endif]-->
<!--[if !mso]><!-- -->
<a href="zO" style="display:inline-block;padding:14px 28px;border-radius:999px;background:r9z
;font-family:zZ;font-size:14px;font-weight:700;text-decoration:none;letter-spacing:0.04em;mso-hide:all;">z/</a>
<!--<![endif]-->
</td></tr>
</table>)r‰rbro)r[rdrer4Úsafe_urlÚ
safe_labels&&&&& rOÚ_bulletproof_buttonrié Ø ;‰;=Š= § ¡ § ¢ ÙܘCŸI™I›KÓ(€HØ—+‘+“-ß‘7˜3 Ó©°°fÓ)=¿g¹gÀcÈ6Ó>RððpðqyÐoyðzVðWYðVZðZà&˜<Ð'}ðIð~JðJðˆfÐgiÐfjÐjqÐr|Ðq}ð~KðLVðKWðWqðr|ðq}ð} ð
ð
 rQcóœV^8„dQhR\R\R\R\R\R\R\R\R \R
\R \/ #) rLÚ template_idÚheadingrŽÚ cta_labelÚcta_urlÚ sub_headingrÚsign_offÚ footer_noteÚfont_idr\r)rNs"rOrPrPÿ ÷d ñd Üðd ä
ðd ô ðd ôð d ô
ð d ô ð
d ôðd ôðd ôðd ôðd ô ñd rQc
óV\PV\R,4p
\PV \R,4p V R,p V R,p
V R,pV
R,pV
R,pV
R,pV
R,pV
R ,pV
R
2026-05-18 22:25:43 +12:00
,pV
2026-06-17 21:51:29 +12:00
R ,pV
R ,pV
2026-05-18 22:25:43 +12:00
R
,pV
2026-06-17 21:51:29 +12:00
R,pV
R,pV
R,pV
R,pV
R,pV
2026-05-18 22:25:43 +12:00
R,pV
2026-06-17 21:51:29 +12:00
R,pV
2026-05-18 22:25:43 +12:00
R,pV
R,p V
2026-06-17 21:51:29 +12:00
R,p!T;'g
2026-05-18 22:25:43 +12:00
V
R,P4p"T;'g
V
2026-06-17 21:51:29 +12:00
R,P4p#T;'gV
2026-05-18 22:25:43 +12:00
PRR4P4p$T;'g
V
2026-06-17 21:51:29 +12:00
R,P4p%T;'g
V
R,P4p&T;'g
V
2026-05-18 22:25:43 +12:00
R,P4p'\ V'V VV4p(RV R V R!V( R"2p)Rp*V&'dR#V R$V R%V R&V R'V& R(2 p*\ W4VVV 4p+Rp,V#'d
R)V
R*V R+V# R,2p,Rp-V'd
R-V R.V R/V R02p-Rp.V'd
2026-06-17 21:51:29 +12:00
R-V R1V R/V R02p.R2T R3T R4T R5V!'d
V!R6,MR V R72
p/Rp0V'dR8V R92p0RP
.R:NV0 NR;NV" NR<NV NR=NV NR>NT#;'gT" NR?NV NR@NV NRANV NRBNV NRCNV NRDNV NREN\ NRFNV- NRGNV NRHNV/ NRINV
NRJNV NRKNV" NRLNV, NRMNV) NRMNV* NRMNV+ NRMNV$'d;RNV ,RO,V,RP,V,RQ,V$,RR,MR NRSNV. NRTNV NRUNV NRVNV NRWNV NRQNT;'gRX NRYNV%'dRZV%,R",MR NR[N4#)\rórWr(r+r*r r
r r r
rrrrrrrrrrrrrrrrrryr rrz<div style="font-family:r9z";font-size:16px;line-height:1.7;">r|
<table role="presentation" cellpadding="0" cellspacing="0" border="0" width="100%" style="margin:8px 0 18px;">
<tr><td style="background:z;border-left:4px solid zK;padding:14px 18px;border-radius:8px;">
<p style="margin:0;font-family:z';font-size:14px;line-height:1.55;color:z;font-weight:600;">
z
</p>
</td></tr>
</table>z'
<p style="margin:0 0 22px;font-family:z8;font-style:italic;font-size:16px;line-height:1.5;color:z;">
z
</p>z-
<tr>
<td align="center" style="background:z\;padding:18px 24px 0;font-family:Arial,sans-serif;font-size:13px;letter-spacing:0.4em;color:z;line-height:1;">
z
</td>
</tr>z\;padding:0 24px 22px;font-family:Arial,sans-serif;font-size:15px;letter-spacing:0.4em;color:z}
<table role="presentation" cellpadding="0" cellspacing="0" border="0" style="margin:0 0 18px;">
<tr><td style="background:z2;border-radius:999px;padding:8px 16px;font-family:z&;font-size:11px;font-weight:700;color:z7;letter-spacing:0.12em;text-transform:uppercase;">
z &nbsp; z
</td></tr>
</table>z<!--[if !mso]><!--><link href="z3" rel="stylesheet" type="text/css"><!--<![endif]-->a(<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xmlns:v="urn:schemas-microsoft-com:vml" xmlns:o="urn:schemas-microsoft-com:office:office" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta name="viewport" content="width=device-width,initial-scale=1">
<meta name="x-apple-disable-message-reformatting">
<meta name="format-detection" content="telephone=no,address=no,email=no,date=no">
<!--[if mso]>
<xml><o:OfficeDocumentSettings><o:PixelsPerInch>96</o:PixelsPerInch><o:AllowPNG/></o:OfficeDocumentSettings></xml>
<![endif]-->
<title>z<</title>
</head>
<body style="margin:0;padding:0;background:z£;width:100%;-webkit-text-size-adjust:100%;-ms-text-size-adjust:100%;">
<div style="display:none;max-height:0;overflow:hidden;font-size:1px;line-height:1px;color:z
;opacity:0;">zn</div>
<table role="presentation" cellpadding="0" cellspacing="0" border="0" width="100%" style="background:zÁ;">
<tr><td align="center" style="padding:24px 12px;">
<table role="presentation" cellpadding="0" cellspacing="0" border="0" width="600" style="max-width:600px;width:100%;background:zd;border-radius:18px;overflow:hidden;">
<tr>
<td align="center" style="background:z;padding:14px 20px;font-family:z,;font-size:13px;letter-spacing:0.18em;color:z ;font-weight:700;">
z
</td>
</tr>
<tr>
<td align="center" style="background:#213021;padding:22px 24px;">
<img src="z¯" width="161" height="32" alt="Goodwalk" style="display:block;max-width:161px;height:auto;border:0;outline:none;text-decoration:none;">
</td>
</tr>
z/
<tr>
<td style="background:z&;padding:30px 30px 8px;">
z4
2026-05-19 23:36:58 +12:00
<h1 style="margin:0 0 14px;font-family:z=;font-size:32px;line-height:1.1;letter-spacing:-0.02em;color:z";font-weight:700;">
2026-06-17 21:51:29 +12:00
z
</h1>
r}z&<p style="margin:24px 0 0;font-family:z&;font-size:14px;line-height:1.6;color:z&;">With love,<br><strong style="color:rZz
</strong></p>z(
</td>
</tr>
z>
<tr>
<td align="center" style="background:z$;padding:22px 24px 18px;font-family:z&;font-size:12px;line-height:1.6;color:zX;">
2026-05-18 22:25:43 +12:00
<div style="font-size:14px;letter-spacing:0.3em;margin-bottom:8px;color:u🾠· 🾠· ðŸ¾z</div>
2026-06-17 21:51:29 +12:00
z<div style="font-weight:600;">zY
</td>
</tr>
</table>
</td></tr>
</table>
</body>
</html>)ÚMESSAGE_TEMPLATESr‡Ú
MESSAGE_FONTSr‰r^rirvr-)1rkrlrmrnrorrprqrrÚtmplÚfontr4Úheading_font_stackÚ font_linkr r
2026-05-19 23:36:58 +12:00
r r r
rrrrrrÚfooter_text_colorrrÚhighlight_text_colorrrrÚemojiÚshÚsoÚfnÚhlrWÚbody_html_innerr+Úhighlight_htmlÚcta_htmlÚsub_heading_htmlÚornament_top_htmlÚornament_bottom_htmlÚ kicker_htmlÚfont_link_htmls1&&&&&&&&&& rOÚ_render_message_htmlrŠÿ sHô × Ñ  Ô.?À Õ.JÓ K€DÜ × Ñ ˜W¤m°HÕ&=Ó >€DØg•€JؘoÕØV• €IØ
(^€FØ%€KØ9o€GØ9o€GؘÕ)€MØ#€JØ%€KØ9o€GØ!€IØÐ-€OØ!€IؘؘÕ'€LØÐØÐ 0ÕØ˜Õ'€LØÐ-€OØ
2026-06-17 21:51:29 +12:00
(^€FØ Õ €Eà × +Ð ++×4€AØ
×
4˜Ð4× ;Ñ ;Ó =€BØ
×
2026-05-18 22:25:43 +12:00
6d—h1°2Ó6× =Ñ =Ó ?€BØ
×
2026-06-17 21:51:29 +12:00
4˜Ð4× ;Ñ ;Ó =€BØ
×
5˜DÐ!4Õ5× <Ñ <Ó >€BØ×-˜˜-×6€Iä# I¨z¸:ÀvÓN€Oà
" : ,¨g°j°\ÐAcØ Ð
Ø
ð ðð €Nß ðà)˜NÐ*AÐBRÐASðT$Ø$. <Ð/VÐWkÐVlðmØ €dð ð  ˆô# 9°v¸{ÈJÓW€HàÐß ð 'Ø'9Ð&:Ð:rÐs~Ðrð@Ø€$ððÐð
Ðßð!(à(/ 1MðNTðMUðUØ€Nðð ÐðÐßð$(à(/ 1MðNTðMUðUØÐðð Ððà#˜HÐ$VÐWaÐVbðcIðJUðIVðVß"€eˆ¨Ð+¨F¨8ð4 ð €Kð€Nßà-¨i¨[Ð8kÐ  ÷> ó> ðð> ðÐð> ð
ð> ð ˆð> ð
> ð-4¨9ð> ð5]ð> ð^eÐ\eð> ðfsð> ðtv×szÐszÐyzÐr{ð> ð|hð> ðipÐgpð> ðqFð> ð$GNðFOð%> ð$O0ð%> ð*18¨yð+> ð*9Xð+> ð*YcÐWcð+> ð*dPð+> ð*QZðP[ð+> ð*[
ð+> ð,Ð ð-> ð,ð-> ô8 jð9> ð8! ð9> ð@
ÐðA> ð@!ðA> ðF")  ðG> ðF*
ðG> ðHˆMðI> ðH4ðI> ðJ5GÐ3GðK> ðJHEðK> ðJFSðETðK> ðJTðK> ðLˆcðM> ðL
ðM> ðPÐ ðQ> ðP
ðQ> ðRˆKðS> ðR
ðS> ðTÐ ðU> ðT
ðU> ðVˆJðW> ðV
ðW> ÷X\^Ð6¸ÕCÐFnÕnÐq|Õ@hõhðkxõxð{@õ@ðCEõEðHWöWðdfð
gðY> ðXg ðY> ð`
Ðða> ð`0ða> ðf1:¨{ðg> ðf;_ðg> ðf`jÐ^jðg> ðfkQðg> ðfRcðQdðg> ðfdUðg> ðhVgÐTgði> ðhhkði> ðhl{÷lUðlUðUðkVði> ðhV
ði> ÷jDFÐÕ3°hÖ>È2Ð Nðk> ðj Oôk> ð> rQz/owner/message-templatescó$V^8„dQhR\/#)rNs"rOrPrP§ s÷@ñ@¬7ñ@rQcƒó"\V4GRjxL
\P4Uu.uFzpRVR,RVR,RVR,RVR,RVR,RVR,R VR
,R VR ,R
VR,RVR,RVPRR4RVR,/ NK| pp\P4Uu.uF)pRVR,RVR,RVR,RVR,/NK+ ppRRRVRV/#Lëuupiuupi5i)NrJrrr Ú bannerEmojirÚdefaultSubjectrÚdefaultHeadingrÚdefaultSubHeadingrÚ defaultBodyrÚdefaultHighlightrÚdefaultSignOffrryÚdefaultFooterNoter r*r(TÚ templatesÚfonts)rrtrNr‡ru)rÚtr•Úfrs& rOÚowner_message_templatesr™¦ s5éä
˜
'×#×ñ,ˆAð
!D•'Ø Af•IØ ˜1˜ •kØ ˜1˜^Õ ˜aÐ 1Õ ˜aÐ 1Õ  Ð#8Õ!9Ø ˜1˜  Ð"5Õ 6Ø ˜aŸe™eÐ$6¸Ó  Ð#8Õ!9ó
ñðô&×
á'ˆ
ˆqw˜  &¥ ¨6°1°Vµ9¸gÀqÈÅzÓ
ð
ð
  Y°¸Ð ?ñ-(ùòùò"
ùs-D C=D ¬BC?Â,D Ã/DÃ3 D Ã?
D z/owner/render-messagecó0V^8„dQhR\R\/#©rLrr)rEr )rNs"rOrPrPÂ s÷&Ô%9ð&ÄGñ&rQc
ƒóv"\V4GRjxL
VP\9d\RRR7h\ VPVP
VP VPVPVPVPVPVPVPR7
pRRRV/#L¥5i)Nr8úUnknown template.r
2026-05-19 23:36:58 +12:00
©rorrprqrrTr.)rÚ
2026-06-17 21:51:29 +12:00
templateIdrtr rlÚctaLabelÚctaUrlÚ
subHeadingÚ
highlightTextÚsignOffÚ
footerNoteÚfontId)rrr.s&& rOÚowner_render_messager§Á séä
2026-05-18 22:25:43 +12:00
˜
2026-06-17 21:51:29 +12:00
'× Ô¨Ð4GÔ Ø Ø Ø ‰ Ø
Ø Ø—O‘OØ×Ø—O‘OØ ô €Dð
 Ð (ùsB9B7B&B9z/owner/render-welcome-packcó0V^8„dQhR\R\/#r©rJr )rNs"rOrPrPÖ s÷&Ô*Að&ÌGñ&rQc ƒó"\V4GRjxL
\VP4P4P 4p\
2026-05-19 23:36:58 +12:00
P
V/4p\VP
2026-06-17 21:51:29 +12:00
RR44P4p\VP
RR44P4p\VV\VP4\VP4\VP44pRRRV/#Lë5i)z;Render the welcome pack email as HTML for in-modal preview.NrÿryrTr.) rrvr‰r~r‡Ú serviceTypeÚ priceDetailsÚ startDate©rrr.s&& rOÚowner_render_welcome_packr¯Õ éô ˜wÓ
2026-05-19 23:36:58 +12:00
'× 
2026-05-18 22:25:43 +12:00
‹O× #× +€EÜ×" 5¨"Ó-€GÜW—[[ ¨RÓ1×9€JÜ7—;;˜y¨"Ó.×6€Hä ØÜ××Ó ó  €Dð
2026-06-17 21:51:29 +12:00
 Ð (ùsC?C=C,C?z/owner/render-birthday-emailcó0V^8„dQhR\R\/#r©r>r )rNs"rOrPrPê s÷  &Ô,@ð &Ì7ñ &rQcƒó²"\V4GRjxL
\VP4P4P 4p\
P
V/4pV'g\RRR7h\VP
RR44P4p\VP
RR44P4p\WE4pRR R
V/#LÃ5i) z7Render the birthday email as HTML for in-modal preview.NrHúClient profile not found.r
rÿryrTr.) rrvr‰r~r‡r r­s&& rOÚowner_render_birthday_emailr´é éô ˜wÓ
'× 
‹O× #× +€EÜ×" 5¨"Ó-€Gß Ü¨Ð4OÔW—[‘[ ¨RÓ1×9€JÜ7—;;˜y¨"Ó.×6€HÜ  
Ó 5€DØ  Ð (ùsCCCCz/owner/send-messagecó0V^8„dQhR\R\/#r)rIr )rNs"rOrPrPú s#÷EAñEAÔ#5ðEAÄñEArQcƒó "\VPR\P!4PR,4p\ V4GRjxL
pVP \9d\RRR7h\VP4pV'g\RRR7h\VP4pVP;'g.Uu.uFKp\V4P4'gK$\V4P4P!4NKM ppV'gV'g\RRR7h\#VP VP$VP&VP(VP*VP,VP.VP0VP2VP4R7
pV'dm\7VP8;'g.Uu.uFp\V4NK up4p R \:R
V R \<R R
V 2RV/p
\?V
RVR7GRjxL
RRRR/#R \:R
\FP!4P!4.RVR \<R VRV/p
\?V
RVR7GRjxL
\BPH!RY P \KT44\LPN!RY#\QT4RRTP R TR \KT4R!T/R"7GRjxL
RRR \KT4/#EL«uupiuupi\@d0p \BPD!RY+RR7\RRTRR/R7hRp ? ii;i\@d0p \BPD!RY+RR7\RRTRR/R7hRp ? ii;iLž5i)#rkNr8rr
zPlease enter a subject.z%Please choose at least one recipient.ržrdrHrerIz
[PREVIEW] r.Úbulk_message_previewriz$[%s] bulk message preview failed: %sTr:éörzThe preview could not be sent.rŽÚ bulk_messagez[%s] bulk message failed: %szThe message could not be sent.z1[%s] bulk message sent: template=%s recipients=%dÚowner_message_sentrŸÚrecipientCountrË©rkrjr$r ))rr´rrtr rIr!rvr‰r~rlr ÚpreviewRecipientsr+r6rZrr;r<r1) rrrkr¸rIÚ
is_previewrÚrecipient_emailsr.r[r“s && rOÚowner_send_messagerÀù s3é䘟¨ ´d·j²j³l×6FÑ6FÀrÕ6JÓK€JÜ,¨WÓ5€Kà Ô¨Ð4GÔt—|‘|Ó$€Gß Ü¨Ð4MÔd—l#€JØ9=¿¹×9NÐ9NÈBÐ9NÓbÑ9N°1ÔSVÐWXÓSY×S_ÑS_×SaÔ˜AŸ ×.Ñ9NÐРרÐ4[Ô Ø Ø Ø ‰ Ø
Ø Ø—O‘OØ×Ø—O‘OØ ô €D÷Ü8È4×KaÑKa×KgÐKgÐegÐKgÓ9iÑKgÀQ¼#¸a¾&ÑKgÑ9iÓà ”JØ Ð œØ ˜ G 9Ð  
ˆð AܘgÐ-CÐPZÔ[× d˜I  
Ø Œ{× Ò Ó"×
ÐØ”HØð
€Gð}ܘÀJÔO×
 ‡KCÀZ×Q`ÑQ`ÔbeÐfvÓbwÔ
×
Ò
ؼ7À7Ó;KÐTXà ˜$Ÿ/™/Ø  œcÐ"2Ó Ð
ô ÷ ð ð
(¬#Ð.>Ó*?Ð @òG6ùòcùò$:jñ
\øÜô AÜ LŠLÐÐ[_Õ ¨C¸ÀzÐS\Ð^~Ð8ôAð
Aûð Aúñ PøÜ ô}Ü Š Ð3°ZÈtÕ¨°\À:ÈyÐZzÐ4{Ô|ûð}úñ
ùsÃA
2026-05-19 23:36:58 +12:00
NÁ K7Á
A7NÃNÃ
!K:Ã0+K:ÄNÄ-B%NÇNÇK?Ç,NÈ LÈLÈLÈ!>NÉ MÉ1MÉ2MÉ6A-NË#NË$NË:
NÌLÌ MÌ*L;Ì;MÍNÍMÍ M?Í*M:Í:M?Í?Nz/owner/client-enquirycó$V^8„dQhR\/#)rNs"rOrPrPC
2026-06-17 21:51:29 +12:00
s÷@ñ@¬ñ@rQcƒód"\V4GRjxL
VPPR4;'gRP4P 4pV'g\ RRR7h\ PV4pV'g\ RRR7h\VPR4\4'dVPR4MRpV'R VPR
2026-05-18 22:25:43 +12:00
R4R VPR R4R VPR R4RTR
VPR
2026-05-19 23:36:58 +12:00
R4RVPRR4RVPRR4R\VPR4\4'dVPR.4M.RRRRRR/ p\P!V4GRjxL
pRRRVRV/#EL5i)Nrïryr8úEmail is required.r
rHrIÚ lastEnquiryÚ submittedAtÚ
2026-06-17 21:51:29 +12:00
lastEnquiryAtrôrÿrrrrrrrrenquiryr) rÚ query_paramsr‡r‰r~r r}rÚget_submission_journey)rrs& rOÚowner_client_enquiryrÊB
swéä
˜
'×
×
!×
% 
.×
4°"× =× E€Eß Ü¨Ð4HÔ×" )€Gß Ü¨Ð4GÔHÜ,6°w·{±{À=Ó7QÔSW×,XÒ,Xˆgk‰k˜(Ð^b€Gß ð
˜7Ÿ;™; ¸Ó ˜7Ÿ;™; }°bÓ ˜Ÿ  J°Ó  W—[[ ¨"Ó w—{{ 9¨bÓ ˜Ÿ  J°Ó ´zÀ'Ç+Á+ÈjÓBYÔ[_×7`Ò7`˜Ÿ  J°Ô3ÐfhØ  ˜Ø  
ˆô"×3°EÓ:×:€GØ $˜  7¨I°wÐ ?ò9(ñ6;ùs:F0F+%F0¸&F0Á)F0Â A F0ÃCF0ÆF.Æ
F0Æ.F0z/owner/client-onboarding-viewcó$V^8„dQhR\/#)rNs"rOrPrPd
s÷LñL´ñLrQcƒóÌ"\V4GRjxL
pVPPR4;'gRP4P 4pV'g\ RRR7h\ PV4pVf\ RRR7h\PV/4p\P!R V\V4R
R V/R 7GRjxL
R
R
RVRVRV/#L5i)u Read-only snapshot of a single client's onboarding view, used by the
Control Panel "view as client" feature.
Returns the same ``{email, profile, draft}`` shape the client receives from
``/auth/verify`` so the owner can render an exact replica of what the client
sees. This endpoint performs NO writes to client data and never mints a
client session — it is purely a read. Any submit from the impersonation
run-through is routed to ``/owner/onboarding-preview-submit`` instead, which
also never touches the real client.Nrïryr8r
rHrIÚowner_client_viewrŽ©rjr$r TrîrR) rr‡r‰r~r rK)rr¸rRs& rOÚowner_client_onboarding_viewrÏc
éô-¨WÓ5€KØ
×
!×
2026-05-04 20:32:24 +12:00
% 
2026-05-19 23:36:58 +12:00
.×
4°"× =× E€Eß Ü¨Ð4HÔ×" )€GØÜ¨Ð4GÔ K‰K˜˜ "€EÜ
×
Ò
2026-05-04 20:32:24 +12:00
ØÜ  ØØ˜%Ð ô  ÷ðð
 ¨ °7¸GÀUÐ ùs-C$C %C$¸&C$ÁA2C$ÃC"ÃC$Ã"C$z /owner/onboarding-preview-submitcó0V^8„dQhR\R\/#r©rDr )rNs"rOrPrP
2026-05-19 23:36:58 +12:00
s÷>Lñ>LÔ0Dð>LÌwñ>LrQc ƒó>"\V4GRjxL
p\VPR\P!4P
2026-06-17 21:51:29 +12:00
R,4p\
V4p\VPPRR44pVPPR4;'gRP4P4pV'd\PV4'g\RRR 7h\!V4\#WV4pR
\$RV.R \&R R
VP( RVP* R2RV/p.p \-VP*VP.VP(V4p
V
'dV P1V
4\2'dD\5V4p \7W°P(RV4GRjxL
p V 'dV P1V 4V 'dW˜R&\9VRVR7GRjxL
2026-05-19 23:36:58 +12:00
\<P@!RY2TPBT4\DPF!RY2TRR\ITPB4RT/R 7GRjxL
2026-05-04 20:32:24 +12:00
RRRTRT/#ELFLn \:d0p
2026-05-19 23:36:58 +12:00
\<P>!RY=RR7\RRTRR/R 7hRp
?
2026-05-18 22:25:43 +12:00
ii;iLP5i)!uOwner-only "impersonation preview" submit.
2026-05-19 23:36:58 +12:00
The owner can walk a client's onboarding all the way to the end. This
endpoint renders the onboarding result exactly like a real submission but
sends it ONLY to the owner-supplied preview address (``?to=...``). It never
writes to the client profile, never emails the client, never registers the
address and records no submission — so a full run-through has zero effect on
the real client. Skips honeypot/timing/rate-limit checks (owner is trusted
and authenticated).Nrkú
user-agentryrHr8z*A valid preview email address is required.r
rdrerIu%[PREVIEW] Onboarding run-through — rfrgr.rÚ attachmentsÚowner_onboarding_preview_emailriz([%s] onboarding preview email failed: %sTr:r¸rz=The preview could not be delivered. Please try again shortly.u=[%s] onboarding preview sent by owner=%s for client=%s → %sÚowner_onboarding_previewrŽÚ
2026-06-17 21:51:29 +12:00
preview_tor¼)%rrr´rXr
r‡r‰r~r r<r+r6rÿrrr"Ú!ONBOARDING_PDF_ATTACHMENT_ENABLEDr,r>rZrr;r<rv)rrr¸rkrjrVr×Ú
owner_htmlÚpreview_payloadrÔÚbirthday_attachmentÚpdf_htmlÚpdf_attachmentr“s&& rOÚowner_onboarding_preview_submitrÞ
sOéô-¨WÓ5€KܘŸ¨ ´d·j²j³l×6FÑ6FÀrÕ6JÓK€JÜ Ó €BܘŸ×+¨L¸>€Gà×&×*¨4Ó0×6°B×G€Jß œYŸ_™_¨ZרÐ4`Ô$ °'Ó:€Jà
Ø ˆzˆlØ”HØÐ:¸4¿=¹=¸ÈDÏLÉLÈ>ÐYZÐ
ð €Oð!€KÜ2°4·<±<ÀÇÁÈdÏmÉmÐ]gÓߨ×ÑÐ,¨TÓ2ˆÜ:¸8Ç]Á]ÐT`ÐblÓß Ø × Ñ ˜~Ô Ø)4˜
Ñ
2026-05-19 23:36:58 +12:00

2026-06-17 21:51:29 +12:00
ܘ/Ð1QÐ^hÔ ‡K‚KØ §¡¨Zôô ×
2026-05-19 23:36:58 +12:00
Ò
2026-06-17 21:51:29 +12:00
ظ2ÀdØœ#˜dŸj™j›/¨<¸Ð ÷ðð
$˜  j°,À
Ð Kòi6ñ2nñ jøÜ ô
Ü Š ÐÐ[_ÕØà˜jØÐô
2026-06-17 21:51:29 +12:00
ð
ûð
úñùs„JIB7JÃ
JÃ%B&JÆ %JÆ1IÆ2 JÆ>JÇJÇIÇ-IÇ.IÇ2AJÉ
JÉ
2026-06-17 21:51:29 +12:00
JÉJÉIÉ JÉ)*JÊJÊJz/owner/activitycó$V^8„dQhR\/#)rNs"rOrPrPÃ
s÷*¤'ñ*rQcƒó8"\V4GRjxL
VPp\VPRR44pVPR4;'gVPR4pV'd \V4MRp\ VPRR44;'gRp\ VPRR44;'gRp\ P!VVVVR7GRjxL
pR R
R V/#\d^dpLÃi;i \dRpLi;iL25i) limitÚ100ÚbeforeIdÚ before_idÚ eventTyperyÚ
actorEmail)events)rr‡r<Ú list_events)rÚqpráÚ
before_id_intrás& rOÚowner_activityrëÂ
séä
2026-06-17 21:51:29 +12:00
˜
'×× Ñ €BðÜB—F‘F˜7 EÓ+ˆð"×9 b§f¡f¨[Ó&9€Iðß*3œ˜¸ˆ
ô˜"Ÿ&™& ¨bÓ2×:°d€Jܘ2Ÿ6™6 Ó4×<¸€KÜ×ØØØô ÷€Fð
$˜  )ñ'(øô ôØŠðûô
ôØŠ
ðúñùóyDC0D£C2¾DÁDÁ)DÁ1
DÁ>!DÂ $DÃ DÃ%DÃ& DÃ2
DÃ?DÄDÄDÄ
DÄDÄDÄDz/owner/submissionscó$V^8„dQhR\/#)rNs"rOrPrPÛ
2026-06-17 21:51:29 +12:00
s÷-¤Wñ-rQcƒó8"\V4GRjxL
VPp\VPRR44pVPR4;'gVPR4pV'd \V4MRp\ VPRR44;'gRp\ VPRR44;'gRp\ P!VVVVR7GRjxL
pR R
R V/#\d^dpLÃi;i \dRpLi;iL25i) Nrár8ry)r8 submissions)rr‡r<Úlist_submissions)rr8Ú email_filterÚrowss& rOÚowner_submissionsróÚ
séä
˜
'×× Ñ €BðÜB—F‘F˜7 EÓ+ˆð"×9 b§f¡f¨[Ó&9€Iðß*3œ˜¸ˆ
ô B—FF˜6  '× /¨4€DܘBŸF™F 7¨BÓ8°D€LÜרØ
Øô ÷ €Dð
$˜
  ,ñ'(øô ôØŠðûô
ôØŠ
ðúñ ùrìz/owner/pending-onboardingcó$V^8„dQhR\/#)rNs"rOrPrPó
2026-06-17 21:51:29 +12:00
s÷))4¬Gñ)4rQcƒópa"\V4GRjxL
RRlo.p\P4EF_wr#V\P!4P 48XdK0VP
R4'dKI\V4'gK\TPRTRVP
RR4RVP
RR4RVP
RR4R VP
R R4R
VP
R
R4R \VP
R 4\4'dVP
R .4M.R VP
2026-06-17 21:51:29 +12:00
R R4R
VP
R
R4R\VP
R4\4'dVP
R/4M//
4EKb VPV3RlR7RRRV/#EL¡5i)Ncó0V^8„dQhR\R\/#r5©r )rNs"rOrPÚ.owner_pending_onboarding.<locals>.__annotate__ö
ó÷ñœsð¤uñrQcó°\V\4'd V'g^#\P!V4P 4# \
d^#i;i©r©r}rvrr;Ú timestampr<s&rOÚ_sort_timestampÚ1owner_pending_onboarding.<locals>._sort_timestampö
2026-06-17 21:51:29 +12:00
óEܘ%¤×%¯UÙð Ü×)¨%Ó0× <øÜô Úð úó¢#AÁ AÁAr[rÿryrrrr rÚwelcomePackSentAtÚwelcomePackOffercóœ<VPRR4R8gS!VPR44)VPRR4P43#)rryrÿ©r‡r~©rs&€rOrDÚ*owner_pending_onboarding.<locals>.<lambda>sGø€Ø H‰HÐ(¨"Ó Ñ
˜TŸX™X 
H‰HZ Ó $× 
rQ©clients)
rr¿r1r‰r~r‡r'r}rÚsort)rÚpending_clientsrïs& @rOÚowner_pending_onboardingr ò
sˆøéä
˜
'×ð-/€OÜ*×2‰ˆØ ”K×'× Ø ;‰;Ð Ü# G× à×ÑØ  ˜Ÿ  J°Ó W—[[ ¨"Ó w—{{ 9¨bÓ w—{‘{ 9¨bÓ ˜Ÿ  J°Ó ´zÀ'Ç+Á+ÈjÓBYÔ[_×7`Ò7`˜Ÿ  J°Ô3ÐfhØ ˜WŸ[™[¨¸"Ó  §¡Ð-@À"Ó!EØ ÄzÐRY×R]ÑR]Ð^pÓRqÔsw×GxÒGx § ¡ Ð,>ÀÔ CðAð
÷ ñ3ð*×Ñô
2026-06-17 21:51:29 +12:00
ðôð
$˜   3òQ(ùsƒF6F3“A&F6Á:D:F6z/owner/completed-onboardingcó$V^8„dQhR\/#)rNs"rOrPrP s÷?ñ?¬gñ?rQcƒó¾a
"\V4GRjxL
RRlo
\^\VPP RR444p\
^\^\VPP RR4444p.p\P4EFwrEV\P!4P48XdK0VP R4'gKI\V4'gK\VPRVR VP R R
4R VP R R
4R VP R R
4R
2026-06-17 21:51:29 +12:00
VP R
R
4RVP RR
4RVP RR
4RVP RR
4R\\\!VP RR
4444/ 4EK VP#V
3RlR7\%V4p\^Wb,^,
V,4p\
2026-06-17 21:51:29 +12:00
W4pV^,
V,pW,p RRRW8V RRVRVRVRV//#EL \
d^pELøi;i \
d^
pELÒi;i5i)Ncó0V^8„dQhR\R\/#r5)rNs"rOrPÚ0owner_completed_onboarding.<locals>.__annotate__#rQcó°\V\4'd V'g^#\P!V4P 4# \
d^#i;is&rOÚ3owner_completed_onboarding.<locals>._sort_timestamp#rrrÚ1Ú page_sizeÚ10r[rÿryrrrr r"r\ÚhasBirthdayInvitecót<S!VPR44)VPRR4P43#)r\rÿryrrs&€rOrDÚ,owner_completed_onboarding.<locals>.<lambda>Js4ø€Ù
˜TŸX™XÐ&=Ó
H‰HZ Ó $× 
rQrTr Ú
paginationÚpageSizeÚtotalÚ
totalPages)rr‡r<Úminrær¿r1r‰r~r'r!rvr
) rrrÚcompleted_clientsrïrÚ total_pagesÚstartÚendrþs & @rOÚowner_completed_onboardingr"s=øéä
˜
'×ðÜ1”c˜'×.×2°6¸ðܘœC ¤3 w×';Ñ';×'?Ñ'?À ÈTÓ'RÓ#SÓUˆ ð/1ÐÜ2‰ˆØ ”K×'× Ø{‰{Ð Ü# G× à× Ñ Ø  ˜Ÿ  J°Ó W—[[ ¨"Ó w—{{ 9¨bÓ w—{‘{ 9¨bÓ ˜Ÿ  J°Ó g—k‘k (¨BÓ # W§[¡[Ð1HÈ"Ó%MØ ¤¤h¬s°7·;±;¸Ó3LÓ/MÓ&NÓ!Oð
"
÷
2026-05-19 23:36:58 +12:00
ñ3ð(×Ñô
ðôô
Ð "€EÜa˜+¨aÕ/°IÕ>€KÜ ˆ !€DØ
AX˜Õ "€EØ
Õ
€Cð
ˆdØÐ$¨3ÐØ  ˜ Ø  ˜+ð 
2026-05-19 23:36:58 +12:00
ð ð òk(øô ôØðûô ôØ‹ ðüsXƒIH2
Iž/H5Á9I ÂAIÃ$EIÈ5
IÉIÉIÉIÉ
2026-06-17 21:51:29 +12:00
IÉIÉIÉIz/owner/all-clientscó$V^8„dQhR\/#)rNs"rOrPrPcs÷>ñ>¤Wñ>rQcƒóBa "\V4GRjxL
RRlo \^\VPP RR444p\
^\^\VPP RR4444p.p\P4EF\wrEV\P!4P48XdK0\VP R4\4'dVP R4MRpTPRTR VP R R
4R VP R R
4R VP R R
4R
2026-06-17 21:51:29 +12:00
VP R
R
2026-05-19 23:36:58 +12:00
4RVP RR
4RVP R4'dRMRRT;'g RRRR
RR
RR
/RVP RR
4;'g-VP RR
4;'gVP RR
4RVP RR
2026-06-17 21:51:29 +12:00
4/
4EK_ VPV 3RlR7\!V4p\^Wr,^,
V,4p\
W4pV^,
2026-05-19 23:36:58 +12:00
V,p W,p
RRRW9V
R RVR!VR"VR#V//#ELb \
2026-06-17 21:51:29 +12:00
d^pEL:i;i \
2026-05-19 23:36:58 +12:00
d^ pELi;i5i)$Ncó0V^8„dQhR\R\/#r5)rNs"rOrPÚ'owner_all_clients.<locals>.__annotate__frQcó°\V\4'd V'g^#\P!V4P 4# \
d^#i;is&rOÚ*owner_all_clients.<locals>._sort_timestampfrrrrrÚ12r#rÿryrrrr r$r[Ú completedrSÚactivertÚ changedAtÚ changedByÚlastActivityAtr\rcóš<VPR4R8gS!VPR44)VPRR4P43#)r$rSr.rÿryrrs&€rOrDÚ#owner_all_clients.<locals>.<lambda>sEø€Ø H‰H  
˜TŸX™XÐ&6Ó
H‰HZ Ó $× 
rQrTr rrrr)rr‡r<rr¿r1r‰r~r}rr
) rrrr r#rrr r!s & @rOÚowner_all_clientsr1bs™øéä
2026-06-17 21:51:29 +12:00
˜
'×ðÜ1”c˜'×.×2°6¸ðܘœC ¤3 w×';Ñ';×'?Ñ'?À ÈTÓ'RÓ#SÓUˆ ð%'€GÜ*×0×2‰ˆØ ”K×'× ä0:¸7¿;¹;À{Ó;SÔUY×0ZÒ0ZG—KK  Ô,Ð`dˆ ØØ  ˜Ÿ  J°Ó W—[[ ¨"Ó w—{{ 9¨bÓ w—{‘{ 9¨bÓ ˜Ÿ  J°Ó  W§[¡[Ð1F×%GÒ%GkÈYØ ˜×j ¸8ÀRÈÐVXÐZeÐgiÐ&jØ ˜gŸk™kÐ*AÀ2ÓSðSÈ'Ï+É+ÐVeÐgiÓJj÷SðSÐnu×nyÑnyð{NðPRóoSØ  §¡Ð-@À"Ó!Eð 
÷ ñ 3ð$ ‡L
ðôô
‹L€EÜa˜+¨aÕ/°IÕ>€KÜ ˆ !€DØ
AX˜Õ "€EØ
Õ
€Cð
ˆdØÐØ  ˜ Ø  ˜+ð 
ð ð òi(øô ôØðûô ôØ‹ ðüsjƒJI4
Jž/I7Á9J ÂC<JÆ JÆ#JÆ5JÇB&JÉ7
JÊJÊJÊJÊ
JÊJÊJÊJz/owner/client-profilecó0V^8„dQhR\R\/#r)r?r )rNs"rOrPrP¥s÷5ñ5Ô%8ð5Ä7ñ5rQcƒóæ"\VPR\P!4PR,4p\ V4GRjxL
2026-05-19 23:36:58 +12:00
p\
VP4P4p\
VP4P4p\
VP4P4p\
VP4P4p\
VP4P4P4p\
VP4P4P4p V'g\RRR7hV'g\RRR7h\!VV RVRVR VR
V/4GRjxL
p
\"P$!R VV\'V4R R
VRV RVR
V/R7GRjxL
2026-05-19 23:36:58 +12:00
R RRRT RV
P)RR4RV
P)RR4R V
P)R R4R
V
P)R
R4RV
P)RR4RV
P)RR4R\+V
P)R4\,4'dV
2026-05-19 23:36:58 +12:00
P)R/4//#///#ELL¸5i)rkNr8úPlease enter the owner name.r
2026-06-17 21:51:29 +12:00
zPlease enter the dog name.rÿrrrÚowner_client_profile_updatedrŽÚ
previousEmailrïTrÀryr rr)rr´rrvrÿr‰rrrr~Ú nextEmailr rXr‡r}r) rrrkr¸r7rrÚ
current_emailrCs && rOÚowner_client_profiler9¤s6é䘟¨ ´d·j²j³l×6FÑ6FÀrÕ6JÓK€JÜ,¨WÓ5×5€KäD—M"×*€IÜ4—< ×(€HÜ 
2026-05-18 22:25:43 +12:00
2026-06-17 21:51:29 +12:00
‹O× #€EÜ$—,×'€GܘŸ
“O×3€MÜT—^4€Jç ܨÐ4RÔ Ü¨Ð4PÔØà ˜ Ø   
ó ÷ €Gô ×
Ò
ØØÜ  Øà ˜]Ø  ˜ Ø 
ô
÷ ð ð
ˆdØØ  ˜Ÿ  J°Ó W—[[ ¨"Ó w—{{ 9¨bÓ w—{‘{ 9¨bÓ ˜Ÿ  J°Ó  §¡Ð-@À"Ó!EØ ÄzÐRY×R]ÑR]Ð^pÓRqÔsw×GxÒGx § ¡ Ð,>ÀÓ Cð 
ð ð ðAð 
ð ð òO ñ ùs>A
2026-05-04 20:32:24 +12:00
I1Á I*Á
DI1Å%I1ÆI-Æ4I1Æ6I/Æ7B4I1É-I1É/I1z/owner/add-clientcó0V^8„dQhR\R\/#r)rCr )rNs"rOrPrPÞs÷gñgÔ!1ðg¼GñgrQcƒó´ "\VPR\P!4PR,4p\ V4GRjxL
p\
2026-06-17 21:51:29 +12:00
VP4P4P4p\
VP4P4p\
VP4P4p\
VP4P4p\
VP4P4p\
VP4P4p \
2026-05-18 22:25:43 +12:00
VP4P4p
2026-06-17 21:51:29 +12:00
V'g\!RRR7hV\"P!4P48Xd\!RRR7hV\$9d\!RR R7h\&P(!4P+R
R 7p \-V4GRjxL
\/VR VR
2026-05-19 23:36:58 +12:00
VRVRVRV RV
2026-06-17 21:51:29 +12:00
RV RV RV/ 4GRjxL
2026-05-18 22:25:43 +12:00
\0P2!RTT\5V4RRTR TRT
2026-06-17 21:51:29 +12:00
;'gR/R7GRjxL
Rp VP6'Ed\8P:!4'g!RRRRRR/p \<P>!RV4M”\@PB!\8PDVVVVV
R 7GRjxL
p
RRR!V
PGR!R"4/p \/VR#V
PGR!R"4R$\&P(!4P+R
R 7/4GRjxL
\0P2!R&TT\5V4V PGR4'dRMR'RV/V CR7GRjxL
\$PGV/4p\MVPGR(4\N4'dVPGR(4MRpRRR)T R*RTR VPGR R"4R
VPGR
R"4RVPGRR"4RVPGRR"4RVPGRR"4R+VPGR,4'dR-MR.R(T;'g R+R/R0R"R1R"R2R"/R3VPGRR"4R4VPGR4R"4/
/#EL8EEL{ELAEELc \Hd2pRRR\
T4/p \<PJ!R%Y.4Rp?EL˜Rp?ii;iEL[5i)5zãCreate a client by hand (leads from Instagram / Facebook / referrals that
never used the public enquiry form). Registers the email in the allowed-users
list so the client can sign in to the onboarding form, and seeds a profile.rkNr8r4r
z.That email is reserved for the business owner.rJz(A client with that email already exists.r`rarÿrrrr ÚsourcerÆÚaddedByOwnerAtÚaddedByÚowner_client_addedrŽÚmanualr¼skippedTrz#MYOB integration is not configured.z2[%s] add-client: MYOB requested but not configured)r7rÚstreetr<ÚuidryÚmyobCustomerUidÚ myobSyncedAtz0[%s] add-client: MYOB customer create failed: %sÚowner_client_myob_syncr<r#rr$r[r*rSr+rtr,r-r.r)(rr´rrvr‰r~rÿrrrr r<r r1rrdrr/Ú createInMyobrÚ