Accounting Rules

An accounting rule is a standing instruction to the Snapbooks automation: “when this happens, do this”. A company writes rules for its own books, and an accounting firm (regnskapsbyrå) writes rules for the companies it keeps the books for, optionally narrowed to an industry. Snapbot carries out a rule when a document arrives, when a bank transaction arrives, or on a schedule.

Rules are written with Snapbot, in the app’s chat or through the save_accounting_rule tool on the MCP server. The API does not create or edit rules. It lists and reads them, and it switches a rule on or off.

Versions

Rules are versioned. Editing a rule retires the live row (it gets a deleted_at and is_deleted: true) and inserts a new row with the same sequence_number. Each version has its own id, so a run of a rule can point to the version it carried out. The list returns live versions by default. GET /api/v2/accounting-rules/{id} returns any version, live or retired.

Who can read a rule

Scope Readable by
CLIENT Users of the owning company, and staff of accounting firms with contract access to it
PROVIDER Active members of the owning firm only. A company’s own users never see their firm’s rules

Endpoints

List Accounting Rules

GET /api/v2/accounting-rules

Returns a paginated list of the rules the caller may read, ordered by owner, then rule number, then version.

Query Parameters

Parameter Type Required Description
client_account_id integer No Only rules owned by this client account. Without it, every rule the caller may read is returned
applies_to_client_account_id integer No Only rules that apply to this company: its own CLIENT rules, plus the PROVIDER rules of the firm holding its active accounting contract whose industry codes match it, whether active or not. A company’s own users still get only its CLIENT rules
scope string No PROVIDER or CLIENT
sequence_number integer No Only versions of the rule with this number. Combine with client_account_id and is_deleted=null to get a rule’s full history
is_active boolean No true or false. null or omitted returns both
is_deleted boolean No false (default) returns live versions, true returns retired versions, null returns both
page integer No Page number (default: 1)
per_page integer No Items per page (default: 100)
with string No Related data to include: client_account, created_by, industries

Example Request

GET /api/v2/accounting-rules?client_account_id=456&scope=PROVIDER&with=industries
Authorization: Bearer <token>

Response

{
  "data": [
    {
      "id": 812,
      "client_account_id": 456,
      "sequence_number": 3,
      "scope": "PROVIDER",
      "industry_codes_lv": ["86"],
      "name": "Helfo settlements",
      "is_active": true,
      "trigger": "BANK_TRANSACTION_RECEIVED",
      "condition": "Incoming payments from Helfo",
      "schedule": null,
      "instruction": "Post the payment against account 3110 with no VAT.",
      "created_at": "2026-11-02T09:14:00Z",
      "created_by_id": 789,
      "updated_at": null,
      "updated_by_id": null,
      "deleted_at": null,
      "deleted_by_id": null,
      "is_deleted": false,
      "industries": [
        { "code": "86", "name": "Helsetjenester" }
      ]
    }
  ],
  "meta": {
    "page": 1,
    "pages": 1,
    "per_page": 100,
    "records": 1
  }
}

Get Accounting Rule

GET /api/v2/accounting-rules/{id}

Returns one version of a rule, live or retired.

Path Parameters

Parameter Type Description
id integer The ID of the rule version

Query Parameters

Parameter Type Required Description
with string No Related data to include: client_account, created_by, industries

Response

A single rule object. A scheduled rule has a schedule and no condition:

{
  "id": 915,
  "client_account_id": 123,
  "sequence_number": 1,
  "scope": "CLIENT",
  "industry_codes_lv": [],
  "name": "Monthly accruals",
  "is_active": true,
  "trigger": "SCHEDULE",
  "condition": null,
  "schedule": "0 7 1 * *",
  "instruction": "Accrue last month's rent and reverse it on the first of the next month.",
  "created_at": "2026-11-10T12:00:00Z",
  "created_by_id": 789,
  "updated_at": null,
  "updated_by_id": null,
  "deleted_at": null,
  "deleted_by_id": null,
  "is_deleted": false
}

Switch a Rule On or Off

PATCH /api/v2/accounting-rules/{id}

Switches the live version of a rule on or off in place, without creating a new version. The body must contain is_active and nothing else. Any other field, or a value that is not a JSON boolean, is rejected with accounting_rule.unsupported_update. Sending the state the rule already has changes nothing, including updated_at and updated_by_id.

Who may switch a rule:

  • A PROVIDER rule: active members of the owning firm.
  • A CLIENT rule: the company’s users with an owner (CA or AA) or bookkeeper (BK) role, and staff of accounting firms with contract access to it.

Request Body

Field Type Required Description
is_active boolean Yes true to switch the rule on, false to switch it off

Example Request

{
  "is_active": false
}

Response

The updated rule object.

The Accounting Rule Object

Field Type Description
id integer ID of this version
client_account_id integer The owner: the firm for a PROVIDER rule, the company for a CLIENT rule
sequence_number integer The rule’s number within its owner. Every version of a rule keeps its number
scope string Whose books the rule is for (see below)
industry_codes_lv string[] SN2025 industry code prefixes a client’s code must start with for a PROVIDER rule to cover it. Empty means every client. Always empty for a CLIENT rule
name string Short name of the rule (max 100 characters)
is_active boolean Whether the rule runs
trigger string When the rule runs (see below)
condition string | null What the rule applies to, in the words of the person who wrote it. null for a SCHEDULE rule
schedule string | null For a SCHEDULE rule: five crontab fields in Norwegian time (Europe/Oslo), at most once a day. null otherwise
instruction string What Snapbot should do with what the rule applies to
created_at string When this version was saved (ISO 8601)
created_by_id integer User who saved this version
updated_at string | null When the version was last switched on or off
updated_by_id integer | null User who last switched it
deleted_at string | null When the version was retired by a newer one
deleted_by_id integer | null User who retired it
is_deleted boolean Whether the version is retired
client_account object The owning client account. Only with with=client_account
created_by object The user who saved the version. Only with with=created_by
industries object[] Each of industry_codes_lv with its official SN2025 name, as {"code", "name"}. Only with with=industries

Scope Values

Value Description
PROVIDER The owner is an accounting or auditing firm, and the rule is for the companies it keeps the books for under an active accounting contract, optionally narrowed by industry_codes_lv
CLIENT The rule is for the owner’s own books

Trigger Values

Value Description
DOCUMENT_RECEIVED Runs when a document arrives and waits for its posting, if the document matches condition
BANK_TRANSACTION_RECEIVED Runs when a bank transaction arrives, before its ordinary matching, if the transaction matches condition
SCHEDULE Runs at the times schedule gives, for each company the rule covers

Which Rule Wins

When several rules match the same document or bank transaction, the most specific level with a match wins: the company’s own CLIENT rules first, then the firm’s PROVIDER rules by longest matching industry code, then the firm’s rules without industry codes.

Error Responses

Status Code Description
400 common.validation_error An invalid scope value
400 accounting_rule.unsupported_update The PATCH body is not exactly {"is_active": true\|false}
400 accounting_rule.retired PATCH on a retired version. Switch the live version instead
403 accounting_rule.access_denied No access to client_account_id or applies_to_client_account_id, the caller may not read the rule, or (on PATCH) may not change it
404 accounting_rule.not_found No rule version with this ID

See Error Handling for the error envelope.

  • MCP server - get_accounting_rules and save_accounting_rule, the tools that read and write rules
  • Worker Tasks - each run of a rule is an ACCOUNTING_RULE worker task
  • Contracts - the accounting contracts that decide which companies a firm’s rules cover
  • Client Accounts - rule owners