silpo-agent-cli
CLI wrapper over the Silpo MCP server (https://mcp.silpo.ua/mcp) for
grocery shopping: rebuild your cart from what you typically buy, check and
edit what's actually in it, and see what's on sale — without leaving the
terminal.
Primary use case: pair it with an AI agent. This is a plain,
scriptable CLI on purpose — every command has a stable --help, flags do
one thing, and output carries the product slugs needed for follow-up calls.
Point an agent (e.g. Claude Code) at .claude/skills/silpo-cli-usage/ and
it can turn "reorder my usual groceries, budget 1500" into the right
invocation, read the result, and handle prompts — you don't have to
memorize flags or babysit the terminal yourself. See
Claude Code skills below.
Setup
uv sync
First run of any command that talks to the MCP server opens a browser for a one-time OAuth2.1+PKCE login; the token is cached in the OS keyring afterward, so you won't be re-prompted until it expires.
Commands
Run uv run silpo-agent --help for the full list, or <command> --help
for a command's flags and examples. Every command is interactive where it
matters (address/item confirmation) — run them somewhere you're watching,
not backgrounded.
reorder — rebuild the cart from your typical items
uv run silpo-agent reorder --last 10 --threshold 0.5
Looks at your recent online orders, works out which products you buy consistently, checks they're still in stock, handles substitutions and (optionally) loyalty bonuses, and fills your real Silpo cart.
--last N— how many of your most recent online orders to consider.--threshold T— minimum share of those orders a product must appear in to count as a "typical item" (e.g.0.5= bought in at least half).--budget UAH— optional spend cap; trims your least-frequently-bought items first until the total fits. Omit it to add everything and just see the total.--optimize promos— opt-in; applies any available loyalty bonuses to the cart. Omitting this flag makes zero promo-related calls.--yes/-y— non-interactive: auto-confirms the proposed delivery address, auto-confirms adding to a non-empty cart, and auto-picks the first candidate on any substitution with multiple replacements. Every auto-answered prompt is still printed, and the report still lists the address used, substitutions made, and items added.
Confirms your delivery address, warns and asks before proceeding if your
cart's delivery context has a real error (e.g. a stale timeslot), warns
before touching a non-empty cart, and asks which replacement you want when
an out-of-stock item has more than one candidate. --budget counts what's
already in the cart (its own payable total) against the cap, not just the
new items, so reordering onto a non-empty cart can't blow past budget.
smart-cart — typical items, discounted favorites, and norm top-up
uv run silpo-agent smart-cart --last 10 --threshold 0.5
uv run silpo-agent smart-cart --people 5 --basket-type premium --budget 1500
Runs the same typical-items pipeline as reorder (address confirmation,
substitution, non-empty-cart guard), then layers on two more sources:
- Any of your favorited products currently on discount that aren't already in the resulting cart — deduplicated by product id, so a favorite that's also a typical item is never added twice.
- A norm top-up: for any grocery category (vegetables, fruits, protein,
dairy, grains, pantry) with no real product-id overlap with what's
already going into the cart, proposes an addition sized to
--people Nand--basket-type basic|eco|premium, shown as its own list with a separate[y/N]confirmation before joining the cart (typical items and favorites-deals don't get this extra gate — they're known purchases, norms are a guess).
--last N/--threshold T— same asreorder.--people N— household size the norm top-up scales to (default1).--basket-type basic|eco|premium— norm generosity (defaulteco).--budget N— likereorder --budget, but trims across all three sources in priority order when over budget: norm items drop first, then favorited deals, then typical items as a last resort.--yes/-y— same asreorder: non-interactive, every auto-answered prompt (including the norm top-up confirmation) still printed.
The report lists all three sources separately ("Added N typical item(s)" /
"Added M favorited deal(s)" / "Added K norm item(s)"), and a --budget
trim's "Trimmed" section is labeled by which source each dropped item came
from.
cart — view, edit, and check promos on your current cart
uv run silpo-agent cart # read-only: items, payable total, bonus balance, validations
uv run silpo-agent cart promos # read-only: real promo alternatives for every item in the cart
uv run silpo-agent cart edit # interactive: replace one item (free-text search or promo browse)
uv run silpo-agent cart edit --replace <old-slug> <new-slug> # non-interactive swap
uv run silpo-agent cart edit --add <new-slug> [--quantity N] # non-interactive add, no swap
uv run silpo-agent cart edit --qty <slug> <num> # set an existing line's quantity (absolute, not a delta)
uv run silpo-agent cart edit --remove <slug> # delete a line, nothing added back
Running silpo-agent with no subcommand at all is the same as cart — it
shows the current real cart (delivery address/type/timeslot, items, payable
total, bonus balance) instead of just printing help.
cart edit is the only command besides reorder that mutates the real
cart. --replace is a remove-then-add swap (Silpo has no in-place
quantity/item update); --quantity and --qty's <num> both accept a
fractional number (e.g. 0.5) for weighted products sold by kg. It
validates the replacement is resolvable, or the slug is actually a cart
line, before mutating anything, so a failed lookup or bad slug never leaves
the cart missing an item.
Products are addressed by slug. Every read-only command prints each
product's slug at the end of its line, and that is exactly what --replace
takes — copy one straight across:
- Молоко «Ферма» ультрапастеризоване 2,5% x2 @ 49.9 (stock: 189) moloko-ferma-ultrapasteryzovane-2-5-576829
Slugs are generated by Silpo and cannot be derived from a product name, so
always copy a printed one rather than constructing it. The old slug is
matched against your cart locally; the new one is resolved through
silpo_get_product_details.
deals — best current discounts store-wide
uv run silpo-agent deals --limit 10 # default 10
uv run silpo-agent deals --category "Овочі" # scope to one category
uv run silpo-agent deals --list-categories # list every real category title
Independent of your cart — scans active promotion categories and shows the
top discounts by percentage off. --category is matched against real
category titles (exact match preferred, else the shortest title containing
it) — if it falls back to that fuzzy match, the actual matched title is
printed before results so a near-miss (e.g. "Вино" matching "Виноград") is
never silent. --list-categories shows every real title to pick from,
read-only, no deals fetched.
favorites-deals — your favorites that are currently discounted
uv run silpo-agent favorites-deals
coupons — your active loyalty coupons
uv run silpo-agent coupons
Read-only list of what's active and what buying-condition triggers each one. Coupons apply automatically server-side when their condition is met — there's no "activate" step this tool can perform.
delivery — set address, delivery type, and timeslot
uv run silpo-agent delivery
Interactive: address (existing saved address, pick a different one, or
enter a new one) → delivery type (DeliveryHome, SelfPickup, or
NovaPoshta) → timeslot, applied in one real update to your account. Prints
which of your current cart items are now unavailable in the new context
afterward — informational only, nothing gets swapped automatically.
clear-context — wipe local reorder history, substitution memory, and cached login
uv run silpo-agent clear-context # asks for confirmation first
uv run silpo-agent clear-context --yes # skip the confirmation prompt
Wipes the local Reorder Log and Substitution Memory, and clears the cached OAuth token from your OS keyring — a full reset that also logs you out. The next command needing a token triggers a fresh browser login. Never touches your real Silpo cart or calls the MCP server.
Claude Code skills
.claude/skills/silpo-cli-usage/(this repo) — the intended way to drive this tool day to day. Mirrors every command's--helpoutput so an agent can turn a plain-language ask ("reorder my usual groceries, budget 1500", "what's in my cart", "swap the milk for something on promo") into the right invocation, handle the interactive prompts, and know this tool's quirks (cart-only scope inreorder, slugs vs. product names, where local history lives). Ships portable — no machine-specific paths — so it works from wherever you clone this repo.
See CONTRIBUTING.md if you're extending the tool itself (TDD-first, test seams, PR expectations).
Local state
Past reorder runs (items added, substitutions, confirmed address, total,
timestamp) and remembered substitution choices are logged to
~/.silpo-agent/reorder_log.json, append-only. Nothing here feeds back into
what counts as a "typical item" — only your confirmed online orders do.
clear-context wipes this file.
Tests
uv run pytest
Project docs
CONTEXT.md— domain glossary (Typical item, Substitution decision, Cart Editor, Promo Scanner, etc.) — read this before the code if a term is unclear.- The original PRDs and live-verified MCP schema notes this project was
built from aren't in this public repo — they're working notes, not
reference docs, and may contain incidental account details. Ask in an
issue if you need context beyond
CONTEXT.mdand the code itself. - Build status lives in the repo's GitHub issues (
MIt9/silpo-agent-cli), not a local TODO file — every ticket that shipped is closed there, with the PR that implemented it linked.
Known limitations
- Substitution Resolver's availability check searches by the typical item's
name when known, otherwise falls back to a raw product-id UUID as the
search query — which usually returns nothing useful. A
reorderrun reporting every item "unavailable" is likely this gap, not genuine across-the-board out-of-stock. Seedocs/mcp_schema.md(issue #18). reorder --optimize promosonly applies loyalty bonuses — swapping an item for a cheaper promo equivalent automatically was dropped there (no reliable per-product "find the promo version of X" tool exists). Manual promo discovery is still possible viacart promos/cart edit's promo-browse path, which use Silpo's own similar-products engine instead of a name-matching guess.week(recipe-plan-based cart) from the original idea list was never built — the MCP server has no recipe/meal-planning tool.delivery's NovaPoshta branch resolution assumes exactly one servicing branch nationwide (true for every account tested so far); if that's ever false for an account, the first one found is used, with a printed note rather than a picker.
License
MIT — see LICENSE.
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file silpo_agent_cli-0.2.0.tar.gz.
File metadata
- Download URL: silpo_agent_cli-0.2.0.tar.gz
- Upload date:
- Size: 1.4 MB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.5.9
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
e1c0212b298c12befa74aa7d52de0fb845080d984713a6dcd16feb01b26867b7
|
|
| MD5 |
80bf319a96f6b32df238d23b7c94692a
|
|
| BLAKE2b-256 |
a857ef9fba3898cab38d28f21297bc33b92bde3f2007059d28af4bbd6ad394fd
|
File details
Details for the file silpo_agent_cli-0.2.0-py3-none-any.whl.
File metadata
- Download URL: silpo_agent_cli-0.2.0-py3-none-any.whl
- Upload date:
- Size: 69.8 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.5.9
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
43a11ddbc897fa957ba0f72e92951feef81cdf3aeee31113a0668347fb7adabc
|
|
| MD5 |
2b75ea7a2f7942a64251e66b6f78edd9
|
|
| BLAKE2b-256 |
018ad240a96675f57cd83ce557c4f91de42c3974c2f1885c10bf558d2d5f648f
|