Publish a policy
Publishes the project's policy for an operation as a new immutable revision, creating the policy on its first publish. The newest revision applies to the next time the operation runs; nothing already stored is re-evaluated, so a stricter password policy applies the next time a password is set.
The request is typed by operation: an unknown operation or setting, or
a value of the wrong type or outside its bounds, answers req.invalid
like any malformed request. The operation's template then checks the
config again, together with the rules that relate settings to each other
(a min_length above max_length), and answers pol.invalid. Its
details.details.violations lists everything that failed, settings
first, then rules: {"setting": "min_length"} for one setting, or
{"config_rule": "min_length_not_above_max_length", "settings": ["min_length", "max_length"]} for a rule across settings, with the
settings it reads. A setting left out is off, and {} switches every
rule off; there are no defaults.
oauth2 policy.writeAuthorizationBearer <token>Scope: policy.write
project_id*stringThe unique identifier of the project
^[a-zA-Z0-9_-]+$application/json- body
A publish of the password policy, checked before a password is set.
operation*"auth.factor.password.set"The operation the policy guards.
"auth.factor.password.set"config*The settings of an auth.factor.password.set policy. Every setting is
optional; a setting left out switches its rule off, and {} switches every
rule off. There are no defaults. The bounds are technical limits, not
recommendations; the server's template checks the same bounds.
The revision was published.
application/json- response
One revision of a project's auth.factor.password.set policy (ADR 066).
id is shared by every revision of the operation's policy; revision_id
names this revision.
id*policy-idThe identifier of a policy, shared by all of its revisions.
^pol_[a-zA-Z0-9_-]+$revision_id*policy-revision-idThe identifier of one immutable revision of a policy.
^polrev_[a-zA-Z0-9_-]+$project_id*project-idThe project the policy belongs to.
^[a-zA-Z0-9_-]+$operation*"auth.factor.password.set"The operation the policy guards.
"auth.factor.password.set"config*The settings of an auth.factor.password.set policy. Every setting is
optional; a setting left out switches its rule off, and {} switches every
rule off. There are no defaults. The bounds are technical limits, not
recommendations; the server's template checks the same bounds.
created_at*stringWhen the operation's policy was first published.
date-timeupdated_at*stringWhen this revision was published.
date-timeimport { createZitadelClient } from "@zitadel/api/client";const client = createZitadelClient({ baseUrl: process.env.ZITADEL_URL ?? "http://localhost:8080", token: process.env.ZITADEL_PROJECT_SECRET!, // server-side only});const result = await client.publishPolicy( { operation: "auth.factor.password.set", config: { min_length: 12, history_depth: 4 }, }, { project_id: "proj_01KWH1P4MYS7F0N9WD3P2E4YM5" },);{ "id": "pol_01KXA4F3Q8R7F0N9WD3P2E4YM5", "revision_id": "polrev_01KXB7C2M4N7F0N9WD3P2E4YM7", "project_id": "proj_01KWH1P4MYS7F0N9WD3P2E4YM5", "operation": "auth.factor.password.set", "config": { "min_length": 12, "history_depth": 4 }, "created_at": "2026-10-20T09:00:00Z", "updated_at": "2026-10-20T10:30:00Z"}Was this helpful?