Skip to content

Instructions & instructability

An instruction is your decision on one patent event: renew it, skip it this time, or abandon the patent. It is the single write operation of the patent surface. Everything else in the API exists to help you make this decision and to prove what happened after you made it.

This page explains the three decisions, the instructability object that tells you when you can act, the DIRECT execution mode, batching rules, and the instruction receipt you get back.

What an instruction is

You submit instructions with POST /api/v2/external/patent-instructions, one entry per event:

bash
curl -X POST "https://api.renewr.example/api/v2/external/patent-instructions" \
  -H "x-api-key: $RENEWR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "instructions": [
      { "eventId": "8a4f2c1e-9b3d-4e7a-a1c5-6d2f8e0b4a91", "decision": "PROCEED" }
    ]
  }'

Instructions are write-only by design. There is no GET /patent-instructions, no update, no delete. The flow is: POST your decision, then observe its effects on the resources you already read:

  1. The 201 response is an instruction receipt, your proof of order.
  2. The event reflects the outcome: GET /patents/{patentId}/events/{eventId} shows appliedDecision (the decision you gave) and processingStatus (how far Renewr has taken it; see Lifecycle).
  3. The receipt PDF is downloadable at GET .../events/{eventId}/documents/instruction-receipt. See Downloading documents.

Scope

This endpoint requires the patents:instructions:write scope on your API key. See Authentication.

The three decisions

The decision field takes one of three values:

DecisionMeaningEffect on future events
PROCEED"Pay this annuity." Renewr executes the renewal: payment to the office/agent, invoicing, receipts.None. The chain continues; the next annuity will come due and be presented for instruction as usual.
SKIP_THIS_TIME"Not through Renewr this time." This occurrence is handled elsewhere (by you or another provider); Renewr does not pay.Future events are kept. The chain continues; the next annuity will be presented normally.
DROP"Abandon: never renew this patent again."Terminal. All remaining un-instructed future events of the patent are deleted, and the right will lapse at the office.

DROP is irreversible

Executing a DROP immediately deletes every remaining un-instructed future event of the patent. There is no API operation to undo it, and once the office deadline passes the patent right itself lapses, normally beyond recovery. Reserve DROP for a confirmed, final abandonment decision. If the annuity is merely being paid through another channel, use SKIP_THIS_TIME.

Instructability: "can I act on this event right now?"

Every event returned by the API (on GET /patents/{patentId}/events, GET .../events/{eventId}, and the cross-portfolio GET /patent-events) carries an instructability object:

json
{
  "isAllowed": true,
  "allowedDecisions": ["PROCEED", "SKIP_THIS_TIME", "DROP"],
  "blockedReason": null,
  "opensAt": "2026-07-01",
  "mode": "DIRECT"
}
FieldTypeDescription
isAllowedbooleanWhether an instruction can be POSTed on this event right now.
allowedDecisionsarrayThe decisions valid right now. Empty when isAllowed is false; a lapsed event drops PROCEED.
blockedReasonenum, nullableWhy the event is blocked: ALREADY_INSTRUCTED | TOO_EARLY | EARLIER_EVENT_PENDING. null when allowed.
opensAtdate, nullableCalendar date the instruction window opens (YYYY-MM-DD). A past date means the window is already open.
modeenumHow an instruction would be processed now. DIRECT is the only value today (open enum).

The rules, in evaluation order

The server evaluates these rules in order and reports the first one that blocks:

  1. ALREADY_INSTRUCTED: the event already has an executed decision. allowedDecisions is empty; re-posting yields 409 instruction_already_set. Read the outcome on the event's appliedDecision instead.

  2. TOO_EARLY: the instruction window has not opened yet. The window opens on opensAt = the first day of the month two months before the due month. Concretely: an event with dueDate: "2026-09-30" becomes instructable on opensAt: "2026-07-01".

  3. EARLIER_EVENT_PENDING (the order rule): only the chronologically earliest un-instructed event of a patent can be instructed. If an earlier event of the same patent is still waiting for a decision, this one is blocked; instruct that one first. Already-instructed earlier events don't block anything.

  4. Allowed, but lapsed: no PROCEED. When an event's duePeriod is LAPSED (the grace period is over), isAllowed stays true but allowedDecisions shrinks to ["SKIP_THIS_TIME", "DROP"]: the office no longer accepts payment, so "renew it" is not offered. You can still record that the annuity was handled elsewhere, or abandon.

The window is calendar-anchored, so trust instructability over duePeriod

opensAt is derived from the due date. The event's duePeriod bucket plays no part in the calculation. An event whose duePeriod still reads UPCOMING can already be instructable. Always use instructability.isAllowed and opensAt to decide when to act; treat duePeriod as informative context.

A blocked event looks like this:

json
{
  "isAllowed": false,
  "allowedDecisions": [],
  "blockedReason": "TOO_EARLY",
  "opensAt": "2026-10-01",
  "mode": "DIRECT"
}

The golden rule

Never send a decision that is not in allowedDecisions. The POST validator applies exactly the same rules that compute instructability (one rule, two consumers), so what you see on the read side is precisely what will be enforced on the write side. Each violation maps 1:1 to a stable error code:

You violatedRead-side signalError on POST
Event already instructedblockedReason: "ALREADY_INSTRUCTED"409 instruction_already_set
Window not open yetblockedReason: "TOO_EARLY"422 instruction_too_early
An earlier event is pendingblockedReason: "EARLIER_EVENT_PENDING"422 instruction_skipped
Decision not offered (e.g. PROCEED on a lapsed event)decision missing from allowedDecisions422 instruction_lapsed

All errors use the application/problem+json envelope with these stable code values. See Errors for the full catalog and envelope shape.

Execution mode: DIRECT

mode: "DIRECT" is the only mode on the external API today. A direct instruction is executed immediately and synchronously inside the POST: by the time you receive the 201, the decision has been applied to the event, the instruction receipt has been issued, and the corresponding invoice line has been created. There is no pending state to poll for the instruction itself. Subsequent payment progress is tracked on the event's processingStatus (see Lifecycle).

The flip side: a direct instruction is not modifiable via the API afterwards. There is no endpoint to amend or cancel it. If you believe an instruction was submitted in error, contact Renewr support.

mode is an open enum

A SCHEDULED mode (instructions registered ahead of time) may appear in a future version. Treat mode as an open enum and tolerate values you don't recognize. See Conventions.

Batching instructions

The instructions array accepts multiple entries, so one call can instruct events across many patents:

bash
curl -X POST "https://api.renewr.example/api/v2/external/patent-instructions" \
  -H "x-api-key: $RENEWR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "instructions": [
      { "eventId": "8a4f2c1e-9b3d-4e7a-a1c5-6d2f8e0b4a91", "decision": "PROCEED" },
      { "eventId": "c1d0e9f8-7a6b-4c5d-8e2f-3a4b5c6d7e8f", "decision": "PROCEED" },
      { "eventId": "5e6f7a8b-9c0d-4e1f-a2b3-c4d5e6f7a8b9", "decision": "SKIP_THIS_TIME" }
    ]
  }'

Two rules govern batches:

  • Many patents per call, but only one event per patent. This follows directly from the order rule: only the earliest un-instructed event of each patent is actionable, so a second event of the same patent in the same batch is validated against pre-execution state and fails with 422 instruction_skipped. Instruct the next event of that patent in a later call.
  • All-or-nothing. If any entry fails validation, the entire batch rolls back; there is no partial execution. The error response identifies the offending entry (validation failures carry RFC 6901 JSON Pointers such as /instructions/2/eventId; see Errors).

Batch defensively

Build batches only from events whose instructability.isAllowed is true and whose decision is in allowedDecisions at the time you POST. Because a single bad entry rolls back the whole batch, pre-filtering against instructability is the difference between one clean call and a retry loop. The monthly renewal cycle guide shows this end to end.

The instruction receipt

A successful POST returns 201 Created with an instruction receipt, the durable proof of your order:

json
{
  "object": "instructionReceipt",
  "issueDate": "2026-07-22",
  "reference": "REC-2026-0142",
  "number": 142,
  "instructions": [
    {
      "object": "instruction",
      "id": "f3b8d6a2-1c4e-4f9a-b7d0-5e8c2a9f6b31",
      "decision": "PROCEED",
      "status": "EXECUTED",
      "executedAt": "2026-07-22T09:14:03.512Z",
      "scheduledForExecutionAt": null,
      "renewedDesignatedCountries": null,
      "excludedDesignatedCountries": null
    }
  ]
}
FieldTypeDescription
object"instructionReceipt"Object type discriminator.
issueDatedate, nullableDate the receipt was issued (YYYY-MM-DD).
referencestring, nullableStable display reference of the receipt.
numberinteger, nullableSequential receipt number.
instructionsarrayOne entry per instruction carried by this receipt.

Each entry in instructions[]:

FieldTypeDescription
object"instruction"Object type discriminator.
idUUIDOpaque Renewr UUID of the instruction.
decisionenum, nullablePROCEED | SKIP_THIS_TIME | DROP.
statusenumLifecycle status: PENDING | SCHEDULED | EXECUTED | SUPERSEDED. With mode DIRECT, instructions come back EXECUTED on the 201.
executedAttimestamp, nullableWhen the instruction was executed (ISO 8601 UTC).
scheduledForExecutionAtdate, nullableWhen the instruction is scheduled to execute; null for DIRECT instructions.
renewedDesignatedCountriesarray, nullableAlways null for patent instructions (reserved field).
excludedDesignatedCountriesarray, nullableAlways null for patent instructions (reserved field).

The PDF version of the receipt is available per event at GET /patents/{patentId}/events/{eventId}/documents/instruction-receipt. Later in the pipeline, the same document family gives you the per-event invoice (.../documents/invoice) and, once the office confirms payment, the official receipt (.../documents/official-receipt). See Downloading documents.

After a PROCEED, the billed amounts appear on the event's fees (GET .../events/{eventId}/fees) once invoiced. See Fees & FX for how estimates become invoiced amounts.

Renewr External API v2. Access on invitation.