Recommendation
Tell the engine about users, items and interactions, train a model, and ask what to show each user next.
The Recommendation engine learns from what your users do. You register users and items, send interaction events, train, and then ask for a ranked list for any user.
pip install aice-recommendationCreate a client
The base URL ends with your project's vertical (ecommerce, entertainment and so on), which the console shows on the project. Everything you send is scoped to it.
import os
from aice_recommendation import RecommendationClient
client = RecommendationClient(
base_url=os.environ["AICE_RECO_URL"], # http://localhost:6400/ecommerce
api_key=os.environ["AICE_API_KEY"],
user_id=current_user.id,
user_role="admin", # writing and training need admin or owner
)X-User-Role decides what the call may do: admin, owner and service_role can read, write and train. Any other role can only read.
The loop
Register users and items
Metadata becomes features the model can learn from, so include what describes them.
client.create_user("user-1", metadata={"country": "KE", "age": 29})
client.create_item("item-42", metadata={"category": "Electronics"})Track interactions
Send an event whenever a user does something that signals interest. Which event types count, and how much, is set in the project's configuration.
client.track("user-1", "item-42", "purchase")Train
Training runs in the background. Start it and poll the job:
import time
job = client.train(epochs=20)
while (status := client.job_status(job.job_id).status) not in ("completed", "failed"):
time.sleep(5)You can also train from the console's Training tab.
Recommend
result = client.recommend("user-1", n=10)
for rec in result.recommendations:
print(rec.rank, rec.item_id, rec.score)Each recommendation has an explanation when the engine can say why it was chosen.
Reference
Unlike the other services, this client returns typed objects rather than plain dictionaries.
| Method (Python / TypeScript) | Endpoint |
|---|---|
create_user / createUser | POST /users |
get_user / getUser | GET /users/{id} |
update_user / updateUser | PUT /users/{id} |
create_item / createItem | POST /items |
get_item / getItem | GET /items/{id} |
update_item / updateItem | PUT /items/{id} |
track | POST /ingest |
recommend | GET /recommend/{user_id}?n= |
train | POST /train |
job_status / jobStatus | GET /train/{job_id} |
get_config / getConfig | GET /config |
update_config / updateConfig | PUT /config |
list_verticals / listVerticals | GET /verticals |
get_vertical / getVertical | GET /verticals/{name} |
Endpoint paths are relative to the base URL, so /users is /{vertical}/users on the server.
Verticals live outside the vertical path
list_verticals and get_vertical call /verticals at the service root, but a client whose base URL ends in /ecommerce sends them to /ecommerce/verticals. Use a second client with the bare host (http://localhost:6400) for those two. They need no key.
Configuration
get_config returns the vertical's base settings, your project's overrides, and the effective result. update_config replaces the overrides, so send the whole set each time, or {} to go back to the vertical's defaults. The console's Configuration tab edits the same thing.
Not in the SDK yet
POST /{vertical}/ingest/batchfor sending events in bulk- the
persistoption on recommendations
Errors
The client raises the shared AICE errors. It also exports RecommendationError and friends under their old names for older code; they're the same classes.
Migrating from reco-sdk
Before 0.2.0 this package was aice-reco-sdk / @aice/reco-sdk with a RecoClient class. Only the names changed:
| Before | After |
|---|---|
from reco import RecoClient | from aice_recommendation import RecommendationClient |
import { RecoClient } from "@aice/reco-sdk" | import { RecommendationClient } from "@aiceafrica/recommendation" |
RecoError | RecommendationError |
Method names, arguments and responses are unchanged. The Python package also gained AsyncRecommendationClient.