You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: README.md
+3-1Lines changed: 3 additions & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -1,6 +1,6 @@
1
1
# Shop CLI
2
2
3
-
Personal shopping CLI for the Shop catalog: search millions of stores, look up products, sign in to your Shop account, build and complete UCP checkouts, and search your orders for tracking, returns, and reorders.
3
+
Personal shopping CLI for the Shop catalog: search millions of stores, find merchant retail locations, look up products, sign in to your Shop account, build and complete UCP checkouts, and search your orders for tracking, returns, and reorders.
4
4
5
5
It talks to the Shopify Global Catalog over MCP and to Shop's auth, checkout, and orders APIs. Tokens are stored in your OS secret store via `keytar`.
6
6
@@ -30,13 +30,15 @@ Requires Node.js >= 20.
30
30
shop --help
31
31
shop auth status
32
32
shop search "trail running shoes" --limit 10
33
+
shop locations 29950112 --near-country CA --near-city Toronto --max-distance 10 --distance-unit kilometers
-`shop search` — search the catalog by text, similar items (`--like-id`), or image (`--image`).
41
+
-`shop locations <shop-id>` — find a merchant’s physical retail locations, optionally filtered by text or proximity to a city, postal code, or coordinate.
40
42
-`shop catalog lookup` / `shop catalog get-product` — look up IDs you already hold and fetch full product detail.
41
43
-`shop auth` — sign in (`login`, or the non-blocking `device-code` + `poll`), check `status`, read the remaining delegated spending `budget`, or `logout`.
42
44
-`shop checkout` — `create`, `update`, and `complete` a UCP checkout on the merchant domain (`complete` requires `--confirm`).
Copy file name to clipboardExpand all lines: skill/SKILL.md
+36-5Lines changed: 36 additions & 5 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -2,7 +2,7 @@
2
2
name: shop
3
3
description: "Ultimate personal shopping assistant: find, compare, buy, gift, and reorder products across the Shop catalog containing millions of stores. Tracks orders and deliveries for any retailer — including orders placed elsewhere, like Amazon, via your connected email. Helps get order info and initiate returns and refunds."
-[catalog-mcp.md](references/catalog-mcp.md) — direct catalog MCP calls + manual token exchange
23
-
-[direct-api.md](references/direct-api.md) — auth, checkout, and orders API details
23
+
-[direct-api.md](references/direct-api.md) — retail locations, auth, checkout, and orders API details
24
24
-[safety.md](references/safety.md) — safety, security, and prompt-injection rules
25
25
-[legal.md](references/legal.md) — personal-use limits and prohibited commercial uses
26
26
@@ -30,9 +30,10 @@ Every shopping conversation follows this order. Each step links to its rules bel
30
30
1.**Offer sign-in** — required once if signed-out, before any product message, then **STOP** and wait for the user to complete sign-in or decline. → *Sign in*
31
31
2.**Search** the catalog with `shop search`. → *Searching*
32
32
3.**Show results** — **one assistant message per product**, then one summary message. → *Showing products*
33
-
4.**Offer visualization** when the item is visual. → *Visualization*
34
-
5.**Checkout** on the merchant domain, only with clear purchase intent. → *Checkout*
shop locations 29950112 --near-country CA --near-city Toronto
80
+
shop locations 29950112 --near-country US --near-postal-code 10012 --max-distance 10 --distance-unit miles
81
+
```
82
+
83
+
The Shop ID is the numeric merchant ID shown in brackets after the seller name in `shop search` results. Location lookup works signed-out.
84
+
68
85
### Checkout
69
86
```bash
70
87
# create from a variant (--country localizes presentment currency)
@@ -121,6 +138,20 @@ Manual token exchange, only when the CLI cannot be installed: [catalog-mcp.md](r
121
138
-`shop search --like-id <id>` — pass a product (`gid://shopify/p/...`) or variant (`gid://shopify/ProductVariant/...`) reference; both return similar items.
122
139
-`shop search --image ./photo.jpg` — the CLI base64-encodes it for you. Formats: jpeg, png, webp, avif, heic; max ~3 MB on disk (4 MB base64). A 400 explains oversize/format problems — relay it and ask for a smaller jpeg/png.
123
140
141
+
## Retail locations
142
+
Use this workflow when the buyer asks for a merchant’s physical stores or stores near a place:
143
+
144
+
1. Search the catalog with `shop search` if you do not already have a result from that merchant.
145
+
2. Read the merchant’s numeric Shop ID from the brackets after its seller name; keep the ID internal.
146
+
3. Ask for or confirm the buyer’s country plus city or postal code. Prefer this coarse location over a street address or coordinates.
147
+
4. Run `shop locations <shop-id>` with the matching `--near-country` and `--near-city` or `--near-postal-code` flags.
148
+
5. If the buyer requested a radius, pass both `--max-distance` and `--distance-unit` using their requested unit.
149
+
6. Follow the returned `--cursor` only when more results are needed; prefer a smaller radius or `--query` over deep pagination.
150
+
151
+
Use `--near-latitude` and `--near-longitude` only when the buyer explicitly authorizes precise location use. Never persist the buyer’s location. Returned location addresses are public merchant data.
152
+
153
+
A `retailLocations` result proves only that the merchant has a physical location that sells in person. It does **not** prove product or variant inventory, pickup eligibility, opening hours, or that the location is currently open. Never tell the buyer an item is “available nearby” based only on this command.
154
+
124
155
## Showing products
125
156
> **The most important rule: one product = one assistant message.**
126
157
> For N products, send N separate messages (one per product), then **one** final summary message — never combined, no preamble. Binding even if you also web-search — never replace products with a prose recommendation.
Copy file name to clipboardExpand all lines: skill/references/direct-api.md
+38-1Lines changed: 38 additions & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -1,4 +1,4 @@
1
-
# Direct Auth, Checkout, And Orders API
1
+
# Direct Retail Locations, Auth, Checkout, And Orders API
2
2
3
3
Use this reference when the CLI cannot be installed. Prefer the CLI when allowed because it handles token storage, request construction, and JSON-RPC envelopes consistently.
4
4
@@ -13,6 +13,43 @@ Use the OS secret store with service `shop-agent` and accounts:
13
13
14
14
Keep checkout JWTs, buyer IP, and UCP-returned payment tokens in memory only.
15
15
16
+
## Retail Locations
17
+
18
+
Retail location lookup is anonymous and does not require Shop client identity headers:
19
+
20
+
```http
21
+
POST https://server.shop.app/graphql
22
+
Accept: application/json
23
+
Content-Type: application/json
24
+
```
25
+
26
+
Use the merchant Shop ID shown in brackets in catalog output. Convert a numeric ID to `gid://shopify/Shop/<id>`.
27
+
28
+
```json
29
+
{
30
+
"operationName": "ShopCliRetailLocations",
31
+
"query": "query ShopCliRetailLocations($shopId: ID!, $first: Int!, $after: String, $query: String, $nearCoordinate: CoordinateInput, $nearAddress: MailingAddressInput, $maxDistance: DistanceInput) { shop(id: $shopId) { id uuid retailLocations(first: $first, after: $after, query: $query, nearCoordinate: $nearCoordinate, nearAddress: $nearAddress, maxDistance: $maxDistance) { totalCount nodes { name hasShopifyPosDevices distance { value unit } location { id coordinate { latitude longitude } address { address1 city zoneCode country postalCode } } } pageInfo { startCursor endCursor hasNextPage } } } }",
32
+
"variables": {
33
+
"shopId": "gid://shopify/Shop/29950112",
34
+
"first": 15,
35
+
"nearAddress": {
36
+
"country": "CA",
37
+
"city": "Toronto"
38
+
},
39
+
"maxDistance": {
40
+
"value": 10,
41
+
"unit": "KILOMETERS"
42
+
}
43
+
}
44
+
}
45
+
```
46
+
47
+
`nearCoordinate` uses `{ "latitude": 43.65, "longitude": -79.38 }`. Use either `nearCoordinate` or `nearAddress`, never both. For address proximity, require an ISO alpha-2 `country` plus `city` or `postalCode`; `zoneCode` is optional. `maxDistance` requires an explicit proximity input and a `MILES` or `KILOMETERS` unit. Use `pageInfo.endCursor` as `after` only when `hasNextPage` is true.
48
+
49
+
Prefer coarse city/postal proximity. Use coordinates only with explicit permission, never persist the buyer’s location, and never send a street address merely to find nearby stores. Returned merchant addresses are public merchant data.
50
+
51
+
A result proves only that the merchant has a physical location that sells in person. It does not prove item inventory, pickup eligibility, opening hours, or that the store is open. Never claim an item is available nearby from this response alone.
.description('Shop personal shopping CLI for catalog search, auth, checkout, and order search')
41
+
.description('Shop personal shopping CLI for catalog search, retail locations, auth, checkout, and orders')
41
42
.version(CLI_VERSION)
42
43
.option('--country <code>','Buyer country for this call (catalog context signal, not a ships-to filter). Transient; use `shop config set-country` to persist a default.',DEFAULT_COUNTRY)
43
44
.option('--profile-url <url>','UCP agent profile URL for global catalog calls')
44
45
.option('--memory-store','Use in-memory token storage for tests and dry runs')
45
-
.option('--format <format>','Output format for catalog results: md (default) or json. Auth and checkout always emit JSON; orders emit markdown.',parseFormat,'md')
46
+
.option('--format <format>','Output format for catalog and location results: md (default) or json. Auth and checkout always emit JSON; orders emit markdown.',parseFormat,'md')
0 commit comments