Recipe: batching embed client with retry, normalise and check
Waits are simulated, not slept, so the example runs instantly. A real client sleeps for the wait, adds jitter and gives up after a maximum number of attempts.
Recipes to copy into any project: a batching embed client with retry and a unit-length check, a cache keyed by model and content, and a guard that refuses to query an index with the wrong model settings. Plus the checklist for changing models.
Change the code and press Run (Ctrl+Enter). Predict what will happen first, then break it on purpose and read what changes. Your edits are saved and match the lesson page.
Ready for more? This phase has 5 hands-on exercises with automatic checks.
Practice questions
Write the code in the editor, run it, then open the model answer to compare.
Write with_retry(fn, attempts) that calls fn() and retries when it raises RuntimeError, up to attempts calls in total, and re-raises the last error. Test it with a function that fails twice and then returns "ok", and print the result and the number of calls.
Write check_settings(stored, live) that returns a list of the names of the keys whose values differ. Print the result for stored = {"model": "v1", "dims": 384} and live = {"model": "v2", "dims": 384}.
Explain it without notes
What does a production embedding client do that a ten-line script does not?
Why store the index's settings next to the vectors?
Walk through the safe steps of switching to a new embedding model.
Why is checking that vectors have length 1 worth its own recipe?
Expected output
batch 1: 2 in batch, ok after 1 attempt(s)
batch 2: 2 in batch, ok after 2 attempt(s)
batch 3: 1 in batch, ok after 1 attempt(s)
5 vectors, all of length 1: yes
api calls: 4, simulated waiting: 200 ms