Files
truenas-stacks/docs/operations/KITCHENOWL_RECIPE_IMPORT.md
2026-05-15 03:03:58 +00:00

4.1 KiB

KitchenOwl Recipe Import (Doris-managed)

Why this exists

KitchenOwl's built-in import/scrape flow is unreliable for the way John and Leanne actually send recipe links around.

This repo-side helper gives Doris a safer path:

  1. try KitchenOwl's native /recipe/scrape endpoint for sites it understands
  2. if that fails, fetch the page directly
  3. extract schema.org Recipe JSON-LD
  4. normalize ingredients/tags/timings into KitchenOwl's create-recipe payload
  5. optionally create the recipe through the KitchenOwl API

That means Doris can ingest recipe links from chat without depending on KitchenOwl's flaky native importer.

Script

automation/bin/kitchenowl_recipe_import.py

Default mode is dry-run. It prints the normalized KitchenOwl payload and does not create anything unless --create is passed.

Required env vars

Put these in a live .env file or export them ad hoc. Do not commit live secrets.

KITCHENOWL_BASE_URL=https://owl.paccoco.com
KITCHENOWL_API_TOKEN=CHANGE_ME
KITCHENOWL_HOUSEHOLD_ID=1

Notes:

  • KITCHENOWL_API_TOKEN should be a long-lived token for a user who can create recipes in the target household.
  • KITCHENOWL_HOUSEHOLD_ID for the current live instance is 1 (Stafford's) unless that changes later.

Usage

cd /home/fizzlepoof/repos/truenas-stacks
export KITCHENOWL_BASE_URL=https://owl.paccoco.com
export KITCHENOWL_API_TOKEN=...redacted...
export KITCHENOWL_HOUSEHOLD_ID=1

automation/bin/kitchenowl_recipe_import.py --pretty \
  "https://example.com/my-recipe"

Actually create the recipe

automation/bin/kitchenowl_recipe_import.py --pretty --create \
  "https://example.com/my-recipe"
automation/bin/kitchenowl_recipe_import.py --create --pretty \
  "https://example.com/recipe-1" \
  "https://example.com/recipe-2"

Behavior details

Strategy order

By default the helper tries:

  1. GET /api/household/<id>/recipe/scrape?url=...
  2. if KitchenOwl returns Unsupported website or otherwise fails, Doris falls back to direct HTML fetch + JSON-LD parse

If you want to skip the built-in scrape and go straight to Doris mode:

automation/bin/kitchenowl_recipe_import.py --skip-kitchenowl-scrape --pretty URL

Duplicate protection

Before creating a recipe, the helper loads existing household recipes and skips creation if it finds:

  • an exact matching source URL, or
  • an exact matching recipe name

To force duplicates anyway:

automation/bin/kitchenowl_recipe_import.py --create --allow-duplicates URL

Visibility

KitchenOwl visibility enum:

  • 0 = private (default)
  • 1 = link
  • 2 = public

Example:

automation/bin/kitchenowl_recipe_import.py --create --visibility 0 URL

What parses well

The fallback parser works best on recipe pages that expose proper schema.org Recipe JSON-LD, which many decent recipe sites do.

It pulls:

  • name
  • description
  • instructions
  • ingredient list
  • total/prep/cook time
  • yield/servings
  • categories/cuisine/keywords → KitchenOwl tags

Known limitations

  • Some sites block scraping aggressively; Doris first tries normal fetch, then falls back to curl headers for better odds.
  • Ingredient normalization is heuristic, not magic. It aims for a sane KitchenOwl item name plus a description/amount, but some weird ingredients may still need manual cleanup.
  • Image upload/import is not wired yet in this helper.
  • The helper expects structured JSON-LD. If a site hides the recipe entirely in client-side blobs or anti-bot nonsense, manual copy/paste may still be needed.
  • GET /api/settings on the live KitchenOwl instance currently returns 500, but that does not block recipe import.

Doris workflow expectation

Preferred operator flow when John or Leanne sends recipe links:

  1. Doris runs a dry-run first when the site is unfamiliar or suspicious.
  2. If the normalized payload looks sane, Doris reruns with --create.
  3. If the page is too messy, Doris asks for the raw ingredients/steps and imports it manually.

That keeps KitchenOwl as the recipe store while making Doris the reliable intake layer.