commerce
Catalogue Semantic Search
A vector index and a GSI on one table, answering different questions.
These are complements, not competitors. 'Something warm for winter camping' is a similarity question and only the vector index can answer it. 'Everything under fifty pounds, cheapest first' is a key condition, and the GSI answers it exactly, completely, in order, and for a fraction of the cost. Most features need both, and the tell is whether you could write the question down as a rule.
The model
Product
One product, searchable by meaning and queryable by price.
- pk
- CATEGORY#<category>
- sk
- PRODUCT#<productId>
Attributes: category (S), price (N), inStock (S), name (S), embedding (L)
Access patterns
- SearchVectors · by-catalogueSomething like this, in stock
A similarity question, narrowed to what you can actually sell.
- Query · GSI1Everything in a price band
A key condition, answered exactly and in order by the GSI.
Design notes
Top-K is a ceiling, not a page sizecost
TopK caps at 100 and there is no LastEvaluatedKey behind it. Filter a Query's results in your application and you can always go back for more rows; filter a search's results and you are spending from a fixed budget with no way to top it up. Anything expressible as a key condition belongs in one.
inStock is a string because the index requires itmodelling
A SearchSchema attribute must appear in AttributeDefinitions, and DynamoDB attribute definitions only accept S, N or B. A BOOL cannot be an inline filter, so the flag is stored as 'yes' and 'no'. This is the sort of constraint that only surfaces at CreateTable.
Exact where AWS is approximateoperations
The engine here compares against every entry and returns the true nearest. AWS builds an approximate index and trades a little recall for speed at scale. The API, the costs and the refusals are identical; the completeness guarantee is not, so do not use a vector index where you need full recall.
Taught in the course
- A different key for a different question - A secondary index re-keys your items so you can Query them on a new axis.
These rows are real and already here. Running an operation against them downloads a DynamoDB-compatible engine, about 850 KB, and executes it in this tab.
A similarity question, narrowed to what you can actually sell.
Run an operation to see the raw engine response.
Transactions, streams, tags and TTL are among the operations the in-browser engine doesn't implement yet.