Add quote template dry-run wrapper checkpoint

This commit is contained in:
2026-05-05 18:56:21 +10:00
parent 868632bd21
commit 5993826b79
2 changed files with 52 additions and 9 deletions
+25 -3
View File
@@ -73,12 +73,17 @@ Current apply payload rules:
- stores/parses results
- applies any parsed Quote Template responses that are not already marked/applied
- logs each run under `logs/poll-and-apply-YYYYMMDD-HHMMSS.log`
- Safety option now available:
- `--dry-run` runs the same poll/selection flow, but previews the ServiceM8 `jobmaterial` payloads only
- dry-run does **not** write to ServiceM8
- dry-run does **not** mark quote responses as applied
- Examples:
- `./poll_and_apply_quote_templates.sh`
- `./poll_and_apply_quote_templates.sh --hours 48`
- `./poll_and_apply_quote_templates.sh --since '2026-05-04 08:00:00'`
- `./poll_and_apply_quote_templates.sh --dry-run --hours 48`
This is the proposed scheduled entry point for soft release, e.g. every 1030 minutes.
This is the proposed scheduled entry point for soft release, e.g. every 1030 minutes. For manual confidence checks, run it with `--dry-run` first, inspect the generated payloads/log, then rerun without `--dry-run` only when ready to apply.
## Live Webhook Receiver Status
@@ -140,13 +145,29 @@ Operational soft-release pieces are now in place:
- payload adjusted for current ServiceM8 requirements
- duplicate-apply guard in place
- wrapper script created for scheduled operation
- wrapper now has a first-class `--dry-run` mode
- inspector updated for progress visibility
### Checkpoint — 2026-05-05
Latest verified state:
- `poll_and_apply_quote_templates.sh --dry-run` added and documented.
- `bash -n /opt/webhooks/poll_and_apply_quote_templates.sh` passes.
- `--help` output includes `--dry-run` usage/examples.
- A future-since dry-run (`--dry-run --since '2099-01-01 00:00:00'`) confirmed:
- wrapper reports `Mode: dry-run`
- poll step performs no ServiceM8 writes
- apply step calls the Python apply tool without `--apply`
- payload rows are emitted as `would_create`
- responses are not marked applied by dry-run
- At checkpoint time, there were still several unapplied parsed Quote Template responses available for preview/apply; this is expected while the soft release remains manual.
## Not Yet Done / Next Steps
- Restart/reload the live inspector process so the new poll/apply pages are available in the active web viewer.
- Decide schedule interval for `poll_and_apply_quote_templates.sh` — likely every 10 or 30 minutes.
- Run the wrapper manually for a soft-release smoke test with a controlled recent form response.
- Run the wrapper manually in `--dry-run` mode against a controlled recent form response and inspect the payload/log.
- If payload is correct, rerun the wrapper without `--dry-run` for a controlled live apply smoke test.
- After confidence builds, wire the wrapper into cron/system scheduling.
- Future hardening: add reconciliation/update/delete behaviour if ServiceM8 quote form responses are edited after initial apply.
@@ -155,4 +176,5 @@ Operational soft-release pieces are now in place:
- Webhooks remain lightweight and non-mutating.
- Polling is now the reliable source of completeness.
- Applying to ServiceM8 is tracked locally and guarded against duplicates.
- The wrapper intentionally skips dry-run for soft release, but the underlying apply script still supports dry-run and duplicate protection.
- The wrapper defaults to live apply for scheduled soft release, but now supports `--dry-run` for manual preview/safety checks.
- The underlying apply script remains dry-run-by-default and provides the duplicate protection used by the wrapper.
+27 -6
View File
@@ -9,8 +9,10 @@ set -euo pipefail
# --since 'YYYY-MM-DD HH:MM:SS'
# --hours 48
#
# This wrapper intentionally skips dry-run and calls --apply. The apply script
# still refuses duplicate applies unless --force is explicitly passed through.
# By default this wrapper applies unapplied parsed responses. Use --dry-run to
# run the poll and preview each pending apply without writing to ServiceM8.
# The apply script still refuses duplicate applies unless --force is explicitly
# passed through.
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
POLL_SCRIPT="$SCRIPT_DIR/poll_form_responses_since.py"
@@ -22,20 +24,25 @@ QUOTE_TEMPLATE_FORM_UUID="${SERVICEM8_QUOTE_TEMPLATE_FORM_UUID:-3621b6be-1d19-47
SINCE=""
HOURS="24"
FORCE="0"
DRY_RUN="0"
usage() {
cat <<EOF
Usage: $0 [--since 'YYYY-MM-DD HH:MM:SS'] [--hours N] [--force]
Usage: $0 [--since 'YYYY-MM-DD HH:MM:SS'] [--hours N] [--dry-run] [--force]
Examples:
$0
$0 --hours 48
$0 --since '2026-05-04 08:00:00'
$0 --dry-run --hours 48
This will:
1. Poll /formresponse.json using timestamp gt SINCE
2. Store/parse Quote Template responses into $DB_PATH
3. Apply parsed responses that do not already have generated materials recorded
With --dry-run, step 3 previews the ServiceM8 jobMaterial payloads only; it does
not write to ServiceM8 or mark responses as applied.
EOF
}
@@ -53,6 +60,10 @@ while [[ $# -gt 0 ]]; do
FORCE="1"
shift
;;
--dry-run)
DRY_RUN="1"
shift
;;
-h|--help)
usage
exit 0
@@ -78,6 +89,7 @@ exec > >(tee -a "$LOG_FILE") 2>&1
echo "== ServiceM8 Quote Template poll/apply run =="
echo "Started: $(date --iso-8601=seconds)"
echo "Since: $SINCE"
echo "Mode: $([[ "$DRY_RUN" == "1" ]] && echo "dry-run" || echo "apply")"
echo "DB: $DB_PATH"
echo "Log: $LOG_FILE"
echo
@@ -121,15 +133,24 @@ printf 'Found %d unapplied Quote Template response(s):\n' "${#FORM_RESPONSE_UUID
printf ' - %s\n' "${FORM_RESPONSE_UUIDS[@]}"
echo
echo "== Applying to ServiceM8 =="
APPLY_ARGS=(--apply --pretty)
if [[ "$DRY_RUN" == "1" ]]; then
echo "== Dry-run preview only; no ServiceM8 writes =="
APPLY_ARGS=(--pretty)
else
echo "== Applying to ServiceM8 =="
APPLY_ARGS=(--apply --pretty)
fi
if [[ "$FORCE" == "1" ]]; then
APPLY_ARGS+=(--force)
fi
for uuid in "${FORM_RESPONSE_UUIDS[@]}"; do
echo
echo "-- Applying form_response_uuid=$uuid --"
if [[ "$DRY_RUN" == "1" ]]; then
echo "-- Dry-run form_response_uuid=$uuid --"
else
echo "-- Applying form_response_uuid=$uuid --"
fi
"$APPLY_SCRIPT" --uuid "$uuid" "${APPLY_ARGS[@]}"
done