Skip to content
Rigel docs
Open Rigel

Replace a recipe's whole ingredient list

recipes.recipe.set_ingredients

POST/api/v1/households/{household_id}/commands/recipes.recipe.set_ingredients

  • Command
  • Rigel runs it
  • Applies offline

For big edits. Lines passed with an id keep that ingredient (and the steps that use it), updated to what's given. Lines without an id are new. Ingredients not in the list are deleted along with their links to steps. An id from another recipe is ingredient_not_found. Send every field you want kept: anything left out is cleared.

Parameters#

Replace a recipe's whole ingredient list: 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.

Replace a recipe's whole ingredient list: request body fields
FieldDescription
recipe_idstringrequired

A recipe ID, such as rcp_01JC0000000000000000000000.

ingredientsarray of objectsrequired

The new ingredient list in order, at most 200.

at most 200 items
ingredients[].idstringoptional

An ingredient already in this recipe, to keep it.

ingredients[].sectionstring or nulloptional

A group heading such as "For the paneer" or "Sauce", 1–80 characters.

1 to 80 characters
ingredients[].product_idstring or nulloptional

The product from the shared product list (inventory.product.search finds one), when the match is clear.

ingredients[].namestringrequired

The ingredient as written, 1–200 characters: "boneless chicken thighs".

1 to 200 characters
ingredients[].quantitynumber or nulloptional

How much, or null for 'to taste' or 'a pinch'.

greater than 0, at most 1,000,000
ingredients[].quantity_maxnumber or nulloptional

The top of a range such as 2–3 cloves; more than quantity. Null if it isn't a range.

greater than 0, at most 1,000,000
ingredients[].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).

ingredients[].preparationstring or nulloptional

How the ingredient is prepared, at most 200 characters: "diced", "at room temperature".

at most 200 characters
ingredients[].is_optionalbooleanoptional

Whether the ingredient can be left out. Defaults to false.

Response#

200 The command was applied.

Replace a recipe's whole ingredient list: response fields
FieldDescription
resultobjectrequired

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

result.ingredient_idsarray of stringsrequired

Every ingredient, in order.

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.

Replace a recipe's whole ingredient list: errors
StatusCodeWhen
400validation_failedA field is missing, misspelled or out of range. details.fields lists each problem.
401unauthenticatedThe request has no valid session.
404ingredient_not_foundAn ingredient from another recipe.
404recipe_not_foundA recipe that isn't there.
404not_foundThe household doesn't exist, or you aren't a member of it.
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.

Keeps one with its link, drops one with its link, adds one

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/recipes.recipe.set_ingredients' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "recipe_id": "rcp_01JC000000000000000000000A",
  "ingredients": [
    {
      "id": "rci_01JC000000000000000000000X",
      "name": "flour",
      "quantity": 2,
      "unit": "cup"
    },
    {
      "name": "butter",
      "quantity": 50,
      "unit": "g"
    }
  ]
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/recipes.recipe.set_ingredients", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    recipe_id: "rcp_01JC000000000000000000000A",
    ingredients: [
      {
        id: "rci_01JC000000000000000000000X",
        name: "flour",
        quantity: 2,
        unit: "cup",
      },
      {
        name: "butter",
        quantity: 50,
        unit: "g",
      },
    ],
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/recipes.recipe.set_ingredients HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "recipe_id": "rcp_01JC000000000000000000000A",
  "ingredients": [
    {
      "id": "rci_01JC000000000000000000000X",
      "name": "flour",
      "quantity": 2,
      "unit": "cup"
    },
    {
      "name": "butter",
      "quantity": 50,
      "unit": "g"
    }
  ]
}
Response, 200
HTTP/1.1 200 OK
Content-Type: application/json
X-Request-Id: req_01K9D9S2R0A0S6FA1XBC991CW2

{
  "result": {
    "ingredient_ids": [
      "rci_01JC000000000000000000000X",
      "rci_01JC4N0000MBGE5RJ6Q7V6V6T8"
    ]
  },
  "version": 1
}

Reordering renumbers positions

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/recipes.recipe.set_ingredients' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "recipe_id": "rcp_01JC000000000000000000000A",
  "ingredients": [
    {
      "id": "rci_01JC000000000000000000000Y",
      "name": "eggs",
      "quantity": 2,
      "quantity_max": 3
    },
    {
      "id": "rci_01JC000000000000000000000X",
      "name": "flour",
      "quantity": 2,
      "unit": "cup"
    }
  ]
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/recipes.recipe.set_ingredients", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    recipe_id: "rcp_01JC000000000000000000000A",
    ingredients: [
      {
        id: "rci_01JC000000000000000000000Y",
        name: "eggs",
        quantity: 2,
        quantity_max: 3,
      },
      {
        id: "rci_01JC000000000000000000000X",
        name: "flour",
        quantity: 2,
        unit: "cup",
      },
    ],
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/recipes.recipe.set_ingredients HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "recipe_id": "rcp_01JC000000000000000000000A",
  "ingredients": [
    {
      "id": "rci_01JC000000000000000000000Y",
      "name": "eggs",
      "quantity": 2,
      "quantity_max": 3
    },
    {
      "id": "rci_01JC000000000000000000000X",
      "name": "flour",
      "quantity": 2,
      "unit": "cup"
    }
  ]
}
Response, 200
HTTP/1.1 200 OK
Content-Type: application/json
X-Request-Id: req_01K9D9S2R0ERBA058PTYW99AFJ

{
  "result": {
    "ingredient_ids": [
      "rci_01JC000000000000000000000Y",
      "rci_01JC000000000000000000000X"
    ]
  },
  "version": 1
}

Changing a kept line updates it and clears what was left out

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/recipes.recipe.set_ingredients' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "recipe_id": "rcp_01JC000000000000000000000A",
  "ingredients": [
    {
      "id": "rci_01JC000000000000000000000X",
      "name": "plain flour",
      "quantity": 3
    },
    {
      "id": "rci_01JC000000000000000000000Y",
      "name": "eggs",
      "quantity": 2,
      "quantity_max": 3
    }
  ]
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/recipes.recipe.set_ingredients", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    recipe_id: "rcp_01JC000000000000000000000A",
    ingredients: [
      {
        id: "rci_01JC000000000000000000000X",
        name: "plain flour",
        quantity: 3,
      },
      {
        id: "rci_01JC000000000000000000000Y",
        name: "eggs",
        quantity: 2,
        quantity_max: 3,
      },
    ],
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/recipes.recipe.set_ingredients HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "recipe_id": "rcp_01JC000000000000000000000A",
  "ingredients": [
    {
      "id": "rci_01JC000000000000000000000X",
      "name": "plain flour",
      "quantity": 3
    },
    {
      "id": "rci_01JC000000000000000000000Y",
      "name": "eggs",
      "quantity": 2,
      "quantity_max": 3
    }
  ]
}
Response, 200
HTTP/1.1 200 OK
Content-Type: application/json
X-Request-Id: req_01K9D9S2R04DA1NR97WBBJYKPB

{
  "result": {
    "ingredient_ids": [
      "rci_01JC000000000000000000000X",
      "rci_01JC000000000000000000000Y"
    ]
  },
  "version": 1
}

An empty list removes every ingredient

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

{
  "recipe_id": "rcp_01JC000000000000000000000A",
  "ingredients": []
}
Response, 200
HTTP/1.1 200 OK
Content-Type: application/json
X-Request-Id: req_01K9D9S2R002268F3193ZQMXX9

{
  "result": {
    "ingredient_ids": []
  },
  "version": 1
}

An ingredient from another recipe

Request, curl
curl -X POST 'https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/recipes.recipe.set_ingredients' \
  -H "Cookie: rigel_session=$RIGEL_SESSION" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA' \
  -d '{
  "recipe_id": "rcp_01JC000000000000000000000A",
  "ingredients": [
    {
      "id": "rci_01JC000000000000000000000Z",
      "name": "oil"
    }
  ]
}'
Request, TypeScript
const response = await fetch("https://rigel.house/api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/recipes.recipe.set_ingredients", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Idempotency-Key": "cmd_01JC4N0000AAAAAAAAAAAAAAAA",
    Cookie: `rigel_session=${process.env.RIGEL_SESSION}`,
  },
  body: JSON.stringify({
    recipe_id: "rcp_01JC000000000000000000000A",
    ingredients: [
      {
        id: "rci_01JC000000000000000000000Z",
        name: "oil",
      },
    ],
  }),
});
const data = await response.json();
Request, HTTP
POST /api/v1/households/hh_01K9BKKP003AHRZ6DMV29GQY5C/commands/recipes.recipe.set_ingredients HTTP/1.1
Host: rigel.house
Cookie: rigel_session=<your session>
Content-Type: application/json
Idempotency-Key: cmd_01JC4N0000AAAAAAAAAAAAAAAA

{
  "recipe_id": "rcp_01JC000000000000000000000A",
  "ingredients": [
    {
      "id": "rci_01JC000000000000000000000Z",
      "name": "oil"
    }
  ]
}
Response, 404
HTTP/1.1 404 Not Found
Content-Type: application/json
X-Request-Id: req_01K9D9S2R0C1PNSS7HP3JY92SH

{
  "error": {
    "code": "ingredient_not_found",
    "message": "That ingredient isn't in this recipe. No changes were applied.",
    "details": {
      "ingredient_id": "rci_01JC000000000000000000000Z"
    },
    "recovery": "Read the current state, then send a command that fits it.",
    "request_id": "req_01K9D9S2R0C1PNSS7HP3JY92SH"
  }
}

A recipe that isn't there

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

{
  "recipe_id": "rcp_01JC000000000000000000000A",
  "ingredients": []
}
Response, 404
HTTP/1.1 404 Not Found
Content-Type: application/json
X-Request-Id: req_01K9D9S2R07ECKQSNER9F41P69

{
  "error": {
    "code": "recipe_not_found",
    "message": "That recipe isn't in the recipe box any more. No changes were applied.",
    "details": {
      "recipe_id": "rcp_01JC000000000000000000000A"
    },
    "recovery": "Read the current state, then send a command that fits it.",
    "request_id": "req_01K9D9S2R07ECKQSNER9F41P69"
  }
}

For Rigel#

Rigel's tool for this command is recipes_recipe_set_ingredients. 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