Skip to content
Rigel docs
Open Rigel

Correct a saved trip

shopping.trip.update

POST/api/v1/households/{household_id}/commands/shopping.trip.update

  • Command
  • Rigel runs it
  • Applies offline

Sets only the fields given on a saved trip: its store (null for none), date, total, currency, receipt photo, order number and the day an order arrived. items corrects the trip's own items (product, amount, note, price, brand; each sets only the fields it gives) and remove_item_ids drops items the trip didn't actually buy. Doesn't touch inventory or the list, except that an order that has now arrived (or turns out not to be an order) has what it bought put away. currency must be set whenever the trip has a total or any item price. Fails with order_number_taken when another trip at the store has that order number.

Parameters#

Correct a saved trip: parameters
FieldDescription
household_idpathstringrequired

The household's ID.

Idempotency-Keyheaderstringoptional

The command's ID. Reuse it when retrying the same command.

Request body#

JSON, as application/json.

Correct a saved trip: request body fields
FieldDescription
trip_idstringrequired

A shopping trip ID, such as trp_01JC0000000000000000000000.

store_idstring or nulloptional

The store, or null for none.

shopped_onstring (date)optional

The day of the trip, YYYY-MM-DD, in the household's time zone.

total_minorinteger or nulloptional

Money in minor units of the currency: 499 is $4.99.

0 to 100,000,000
currencystring or nulloptional

An ISO 4217 currency code in capitals, such as USD.

pattern ^[A-Z]{3}$
receipt_file_idstring or nulloptional

The receipt photo, or null to detach it.

order_numberstring or nulloptional

The store's order number, or null when the trip wasn't an order after all.

at most 80 characters
arrived_onstring (date) or nulloptional

The day the order arrived, or null if it hasn't. Setting it puts away what the order still has to.

itemsarray of objectsoptional

Corrections to the trip's items. Each sets only the fields it gives.

at most 200 items
items[].item_idstringrequired

A shopping trip item ID, such as tri_01JC0000000000000000000000.

items[].product_idstringoptional

A product ID, such as prd_01JC0000000000000000000000.

items[].quantitynumber or nulloptional

How many, when said. Leave out when no amount was given.

greater than 0, at most 1,000,000
items[].unitone of: mg, g, kg, oz, lb, ml, l, tsp, tbsp, fl_oz, cup, pint, quart, gallon, pinch, dash, clove, slice, stick, sprig, head, bunch, stalk, can, jar, bottle, box, bag, package, carton, roll, null or nulloptional

A unit. Mass: mg, g, kg, oz, lb. Volume (US sizes): ml, l, tsp, tbsp, fl_oz, cup, pint, quart, gallon. Items, for a count of something other than the thing itself (2 cloves of garlic, 1 can of beans): pinch, dash, clove, slice, stick, sprig, head, bunch, stalk, can, jar, bottle, box, bag, package, carton, roll. Leave it out or null for a plain count of the things themselves (3 eggs).

items[].notestring or nulloptional

A note for whoever shops: "plain", "the big bag". Name a meal or recipe with meal_id or recipe_id, not here, as written, 1–500 characters.

at most 500 characters
items[].price_minorinteger or nulloptional

Money in minor units of the currency: 499 is $4.99.

0 to 100,000,000
items[].brandstring or nulloptional

The brand from the receipt: "Cabot", as written, 1–120 characters.

at most 120 characters
remove_item_idsarray of stringsoptional

Items the trip didn't actually buy. Doesn't touch inventory.

at most 200 items

Response#

200 The command was applied.

Correct a saved trip: response fields
FieldDescription
resultobjectrequired

What the command returned, such as the IDs it created.

versionintegerrequired

The household version after the command.

Errors#

Every error has the same envelope: error.code, error.message, error.details, error.recovery and error.request_id.

Correct a saved trip: errors
StatusCodeWhen
400validation_failedA field is missing, misspelled or out of range. details.fields lists each problem.
401unauthenticatedThe request has no valid session.
404trip_not_foundAn unknown trip is refused.
404store_not_foundAn unknown store is refused.
404file_not_foundAn unknown receipt file is refused.
404trip_item_not_found
  • An item from another trip is refused.
  • Removing an item from another trip is refused.
404product_not_foundAn unknown product is refused.
404not_foundThe household doesn't exist, or you aren't a member of it.
409order_number_takenAn order number another trip at the store has is refused.
409idempotency_key_reusedThe Idempotency-Key was already used for a different command.

Examples#

These are real. Each scenario is one of the command's test cases, run on a household when this site was built, and the response is what the API returned.

Only the fields given change

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC0000000000000000000001",
  "shopped_on": "2025-11-02",
  "store_id": "sto_01JC000000000000000000000B",
  "total_minor": 500,
  "currency": "USD"
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC0000000000000000000001",
    shopped_on: "2025-11-02",
    store_id: "sto_01JC000000000000000000000B",
    total_minor: 500,
    currency: "USD",
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC0000000000000000000001",
  "shopped_on": "2025-11-02",
  "store_id": "sto_01JC000000000000000000000B",
  "total_minor": 500,
  "currency": "USD"
}
Response, 200
HTTP/1.1 200 OK
Content-Type: application/json
X-Request-Id: req_01K9D9S2R04MYCF0SEV74JJDRG

{
  "result": {},
  "version": 1
}

Null clears the store and the receipt

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC0000000000000000000001",
  "store_id": null,
  "receipt_file_id": null
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC0000000000000000000001",
    store_id: null,
    receipt_file_id: null,
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC0000000000000000000001",
  "store_id": null,
  "receipt_file_id": null
}
Response, 200
HTTP/1.1 200 OK
Content-Type: application/json
X-Request-Id: req_01K9D9S2R0EM9F84KXP0WYP1HM

{
  "result": {},
  "version": 1
}

Items are corrected and removed

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC0000000000000000000001",
  "items": [
    {
      "item_id": "tri_01JC0000000000000000000001",
      "product_id": "prd_01JC000000000000000000000C",
      "quantity": null,
      "note": null,
      "price_minor": 299,
      "brand": "Hood"
    }
  ],
  "remove_item_ids": [
    "tri_01JC0000000000000000000002"
  ]
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC0000000000000000000001",
    items: [
      {
        item_id: "tri_01JC0000000000000000000001",
        product_id: "prd_01JC000000000000000000000C",
        quantity: null,
        note: null,
        price_minor: 299,
        brand: "Hood",
      },
    ],
    remove_item_ids: [
      "tri_01JC0000000000000000000002",
    ],
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC0000000000000000000001",
  "items": [
    {
      "item_id": "tri_01JC0000000000000000000001",
      "product_id": "prd_01JC000000000000000000000C",
      "quantity": null,
      "note": null,
      "price_minor": 299,
      "brand": "Hood"
    }
  ],
  "remove_item_ids": [
    "tri_01JC0000000000000000000002"
  ]
}
Response, 200
HTTP/1.1 200 OK
Content-Type: application/json
X-Request-Id: req_01K9D9S2R0S66N1ZP3DDKFACZ3

{
  "result": {},
  "version": 1
}

A quantity without a unit keeps the unit

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC0000000000000000000001",
  "items": [
    {
      "item_id": "tri_01JC0000000000000000000001",
      "quantity": 2
    }
  ]
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC0000000000000000000001",
    items: [
      {
        item_id: "tri_01JC0000000000000000000001",
        quantity: 2,
      },
    ],
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC0000000000000000000001",
  "items": [
    {
      "item_id": "tri_01JC0000000000000000000001",
      "quantity": 2
    }
  ]
}
Response, 200
HTTP/1.1 200 OK
Content-Type: application/json
X-Request-Id: req_01K9D9S2R0H1PN11JKVJDJEMF1

{
  "result": {},
  "version": 1
}

Marking an order arrived puts away what it bought

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC000000000000000000000A",
  "arrived_on": "2025-11-07"
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC000000000000000000000A",
    arrived_on: "2025-11-07",
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC000000000000000000000A",
  "arrived_on": "2025-11-07"
}
Response, 200
HTTP/1.1 200 OK
Content-Type: application/json
X-Request-Id: req_01K9D9S2R00GEJDSYHEFHN6D8T

{
  "result": {},
  "version": 1
}

An order that hasn't arrived puts nothing away when other fields change

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC000000000000000000000A",
  "total_minor": 2500
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC000000000000000000000A",
    total_minor: 2500,
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC000000000000000000000A",
  "total_minor": 2500
}
Response, 200
HTTP/1.1 200 OK
Content-Type: application/json
X-Request-Id: req_01K9D9S2R09R4H2FDMM66KBRGZ

{
  "result": {},
  "version": 1
}

An unknown trip is refused

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC0000000000000000000001"
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC0000000000000000000001",
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC0000000000000000000001"
}
Response, 404
HTTP/1.1 404 Not Found
Content-Type: application/json
X-Request-Id: req_01K9D9S2R0JY4VAV37V1ZA7QKX

{
  "error": {
    "code": "trip_not_found",
    "message": "That trip isn't there any more. No changes were applied.",
    "details": {
      "trip_id": "trp_01JC0000000000000000000001"
    },
    "recovery": "Read the current state, then send a command that fits it.",
    "request_id": "req_01K9D9S2R0JY4VAV37V1ZA7QKX"
  }
}

An unknown store is refused

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC0000000000000000000001",
  "store_id": "sto_01JC000000000000000000000Z"
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC0000000000000000000001",
    store_id: "sto_01JC000000000000000000000Z",
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC0000000000000000000001",
  "store_id": "sto_01JC000000000000000000000Z"
}
Response, 404
HTTP/1.1 404 Not Found
Content-Type: application/json
X-Request-Id: req_01K9D9S2R0ECTCQKY3C9TR1ZY1

{
  "error": {
    "code": "store_not_found",
    "message": "That store isn't there any more. No changes were applied.",
    "details": {
      "store_id": "sto_01JC000000000000000000000Z"
    },
    "recovery": "Read the current state, then send a command that fits it.",
    "request_id": "req_01K9D9S2R0ECTCQKY3C9TR1ZY1"
  }
}

An unknown receipt file is refused

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC0000000000000000000001",
  "receipt_file_id": "fil_01JC000000000000000000000Z"
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC0000000000000000000001",
    receipt_file_id: "fil_01JC000000000000000000000Z",
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC0000000000000000000001",
  "receipt_file_id": "fil_01JC000000000000000000000Z"
}
Response, 404
HTTP/1.1 404 Not Found
Content-Type: application/json
X-Request-Id: req_01K9D9S2R01917CTN9W1HPQ3XD

{
  "error": {
    "code": "file_not_found",
    "message": "That file isn't there any more. No changes were applied.",
    "details": {
      "file_id": "fil_01JC000000000000000000000Z"
    },
    "recovery": "Read the current state, then send a command that fits it.",
    "request_id": "req_01K9D9S2R01917CTN9W1HPQ3XD"
  }
}

An item from another trip is refused

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC0000000000000000000001",
  "items": [
    {
      "item_id": "tri_01JC0000000000000000000001",
      "note": "x"
    }
  ]
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC0000000000000000000001",
    items: [
      {
        item_id: "tri_01JC0000000000000000000001",
        note: "x",
      },
    ],
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC0000000000000000000001",
  "items": [
    {
      "item_id": "tri_01JC0000000000000000000001",
      "note": "x"
    }
  ]
}
Response, 404
HTTP/1.1 404 Not Found
Content-Type: application/json
X-Request-Id: req_01K9D9S2R0GEZY9DMAJW76GZRE

{
  "error": {
    "code": "trip_item_not_found",
    "message": "That item isn't on this trip. No changes were applied.",
    "details": {
      "trip_id": "trp_01JC0000000000000000000001",
      "item_id": "tri_01JC0000000000000000000001"
    },
    "recovery": "Read the current state, then send a command that fits it.",
    "request_id": "req_01K9D9S2R0GEZY9DMAJW76GZRE"
  }
}

Removing an item from another trip is refused

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC0000000000000000000001",
  "remove_item_ids": [
    "tri_01JC0000000000000000000001"
  ]
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC0000000000000000000001",
    remove_item_ids: [
      "tri_01JC0000000000000000000001",
    ],
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC0000000000000000000001",
  "remove_item_ids": [
    "tri_01JC0000000000000000000001"
  ]
}
Response, 404
HTTP/1.1 404 Not Found
Content-Type: application/json
X-Request-Id: req_01K9D9S2R00A8FDG7S7VPAQQD3

{
  "error": {
    "code": "trip_item_not_found",
    "message": "That item isn't on this trip. No changes were applied.",
    "details": {
      "trip_id": "trp_01JC0000000000000000000001",
      "item_id": "tri_01JC0000000000000000000001"
    },
    "recovery": "Read the current state, then send a command that fits it.",
    "request_id": "req_01K9D9S2R00A8FDG7S7VPAQQD3"
  }
}

An unknown product is refused

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC0000000000000000000001",
  "items": [
    {
      "item_id": "tri_01JC0000000000000000000001",
      "product_id": "prd_01JC000000000000000000000Z"
    }
  ]
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC0000000000000000000001",
    items: [
      {
        item_id: "tri_01JC0000000000000000000001",
        product_id: "prd_01JC000000000000000000000Z",
      },
    ],
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC0000000000000000000001",
  "items": [
    {
      "item_id": "tri_01JC0000000000000000000001",
      "product_id": "prd_01JC000000000000000000000Z"
    }
  ]
}
Response, 404
HTTP/1.1 404 Not Found
Content-Type: application/json
X-Request-Id: req_01K9D9S2R0D6D02AH56W62RTYJ

{
  "error": {
    "code": "product_not_found",
    "message": "That product isn't there any more. No changes were applied.",
    "details": {
      "product_id": "prd_01JC000000000000000000000Z"
    },
    "recovery": "Read the current state, then send a command that fits it.",
    "request_id": "req_01K9D9S2R0D6D02AH56W62RTYJ"
  }
}

A total with no currency is refused

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC0000000000000000000001",
  "total_minor": 500
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC0000000000000000000001",
    total_minor: 500,
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC0000000000000000000001",
  "total_minor": 500
}
Response, 409
HTTP/1.1 409 Conflict
Content-Type: application/json
X-Request-Id: req_01K9D9S2R0DZ1FS0RMBXHAD1F6

{
  "error": {
    "code": "validation_failed",
    "message": "currency is required with total_minor or a price No changes were applied.",
    "details": {
      "trip_id": "trp_01JC0000000000000000000001"
    },
    "recovery": "Read the current state, then send a command that fits it.",
    "request_id": "req_01K9D9S2R0DZ1FS0RMBXHAD1F6"
  }
}

A price with no currency is refused

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC0000000000000000000001",
  "items": [
    {
      "item_id": "tri_01JC0000000000000000000001",
      "price_minor": 300
    }
  ]
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC0000000000000000000001",
    items: [
      {
        item_id: "tri_01JC0000000000000000000001",
        price_minor: 300,
      },
    ],
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC0000000000000000000001",
  "items": [
    {
      "item_id": "tri_01JC0000000000000000000001",
      "price_minor": 300
    }
  ]
}
Response, 409
HTTP/1.1 409 Conflict
Content-Type: application/json
X-Request-Id: req_01K9D9S2R03DS4G9QWFSYRT77D

{
  "error": {
    "code": "validation_failed",
    "message": "currency is required with total_minor or a price No changes were applied.",
    "details": {
      "trip_id": "trp_01JC0000000000000000000001"
    },
    "recovery": "Read the current state, then send a command that fits it.",
    "request_id": "req_01K9D9S2R03DS4G9QWFSYRT77D"
  }
}

An order number another trip at the store has is refused

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "trip_id": "trp_01JC000000000000000000000B",
  "order_number": "112-4839201-5551234"
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01JC000000000000000000000B",
    order_number: "112-4839201-5551234",
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "trip_id": "trp_01JC000000000000000000000B",
  "order_number": "112-4839201-5551234"
}
Response, 409
HTTP/1.1 409 Conflict
Content-Type: application/json
X-Request-Id: req_01K9D9S2R0T0RX25P8QAZ9P7F1

{
  "error": {
    "code": "order_number_taken",
    "message": "Another trip at this store already has that order number. No changes were applied.",
    "details": {
      "trip_id": "trp_01JC000000000000000000000A",
      "order_number": "112-4839201-5551234"
    },
    "recovery": "Read the current state, then send a command that fits it.",
    "request_id": "req_01K9D9S2R0T0RX25P8QAZ9P7F1"
  }
}

Say when an order arrived

arrived_on is the day it came, so Rigel can put what it brought away.

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01M6V9CS6GGVFCY7NAS8ZTQV95/commands/shopping.trip.update' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01M6V9CT8VJF2BA8P08MMKK2A1' \
  -d '{
  "trip_id": "trp_01M6V9CT8S4T83B9C9T7FBKE1N",
  "arrived_on": "2026-11-06"
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01M6V9CS6GGVFCY7NAS8ZTQV95/commands/shopping.trip.update", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01M6V9CT8VJF2BA8P08MMKK2A1",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    trip_id: "trp_01M6V9CT8S4T83B9C9T7FBKE1N",
    arrived_on: "2026-11-06",
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01M6V9CS6GGVFCY7NAS8ZTQV95/commands/shopping.trip.update HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01M6V9CT8VJF2BA8P08MMKK2A1

{
  "trip_id": "trp_01M6V9CT8S4T83B9C9T7FBKE1N",
  "arrived_on": "2026-11-06"
}
Response, 200
HTTP/1.1 200 OK
Content-Type: application/json
X-Request-Id: req_01M6V9CT8VZBZWEBGY88WXXTHP

{
  "result": {},
  "version": 288
}

For Rigel#

Rigel's tool for this command is shopping_trip_update. Rigel runs this on its own, then says what it did. The agent guide has the rest.

Rigel is in early access, and sign-up is by invitation. Open Rigel