amir20/dozzle · error · Error
rule POST failed
Error message
rule POST failed
What it means
WelcomeModal.vue fires parallel POSTs to create notification rules and each POST's .then throws 'rule POST failed' when res.ok is false. Because the POSTs run via Promise.all, a single failing rule aborts the whole setup after earlier rules may already be saved (documented partial-failure behavior).
Solutions
- Check each failing POST's status and response body in devtools to find which rule and why
- Validate rule expressions (kind, expression syntax, cooldown/sampleWindow ranges) before submitting
- Replace Promise.all with Promise.allSettled if partial success should be reported per-rule
- Confirm auth is still valid and the data directory is writable for notifications.yml
Example fix
// before
}).then((res) => {
if (!res.ok) throw new Error("rule POST failed");
}),
// after
}).then((res) => {
if (!res.ok) throw new Error(`rule POST failed for "${rule.name}" (HTTP ${res.status})`);
}), Defensive patterns
Strategy: validation
Validate before calling
for (const rule of chosen) {
if (!rule.expression?.trim()) throw new Error(`Rule "${rule.name}" has an empty expression`);
if (!Number.isFinite(rule.cooldown) || rule.cooldown < 0) throw new Error(`Rule "${rule.name}" has invalid cooldown`);
} Try / catch
const results = await Promise.allSettled(chosen.map((rule) => postRule(rule)));
const failed = results.filter((r) => r.status === "rejected");
if (failed.length) showToast({ type: "warning", message: `${chosen.length - failed.length} of ${chosen.length} rules created` }); Prevention
- Validate rule expressions and numeric fields before submitting
- Use Promise.allSettled when partial success is acceptable
- Check notifications.yml writability once before batch-creating rules
- Include rule identity in thrown messages to identify the failing POST
When it happens
Trigger: Any rule-creation POST returns 4xx/5xx: invalid expression syntax for the rule kind, missing cooldown/sampleWindow fields, server validation rejecting the payload, or auth failure.
Common situations: A metric or event expression the backend validator rejects; notifications persistence directory not writable so the second+ rule fails; session expired between the dispatchers fetch and the rule POSTs.
Understand the failure class
Background: "API error: {status}" and "HTTP 401/403/404/429/5xx" errors: non-2xx HTTP responses explained — this error's family across 27 libraries.
Related errors
- Failed to save destination
- dispatchers fetch failed
- cloud dispatcher missing
- cloud dispatcher rate limited, retry after
- webhook notification failed
AI-assisted analysis of amir20/dozzle@d9463cbe21 (2026-09-07).
Data as JSON: /api/errors/2df6780c45a65c62.
Report an issue: GitHub.
Appendix: source
Thrown at assets/components/WelcomeModal.vue:577
await Promise.all(
chosen.map((rule) =>
fetch(withBase("/api/notifications/rules"), {
method: "POST",
headers: { "Content-Type": "application/json" },
signal,
body: JSON.stringify({
name: rule.ruleName,
enabled: true,
dispatcherId: cloud.id,
containerExpression: "true",
logExpression: rule.kind === "log" ? rule.expression : "",
eventExpression: rule.kind === "event" ? rule.expression : "",
metricExpression: rule.kind === "metric" ? rule.expression : "",
cooldown: rule.cooldown,
sampleWindow: rule.sampleWindow,
}),
}).then((res) => {
if (!res.ok) throw new Error("rule POST failed");
}),
),
);
createdCount.value = chosen.length;
reportUsage(false);
step.value = 3;
} catch (err) {
if ((err as Error)?.name === "AbortError") return;
close();
showToast({ type: "warning", message: t("notifications.default-alert-failed") }, { expire: 6000 });
router.push({ path: "/notifications", query: { action: "create-alert" } });
} finally {
creating.value = false;
}
}
function skipAlerts() {View on GitHub (pinned to d9463cbe21)