Entities & Proxies¶
Almost everything you touch on the WiseFood Data API is an entity proxy: a thin, typed Python object wrapping a single record’s JSON. Understanding this one model unlocks every resource — articles, guides, textbooks, FCTables, and artifacts all behave the same way.
Note
This page describes the WiseFood Data API object model (DataClient). The
WiseFood API
(Client → households/members) uses a simpler property-based model documented in
Households & Members.
What an entity is¶
Every WiseFood Data API record is represented by a subclass of BaseEntity. The raw JSON lives
in entity.data; the typed attributes you use are descriptors that read and write
keys in that dict.
article = client.articles["some-article-slug"]
article.title # -> reads entity.data["title"]
article.dict() # -> the full underlying dict
article.json() # -> pretty-prints the JSON payload
article.show() # -> tabular view via pandas (transposed)
repr(article) # -> <Article urn='...'>
The Field descriptor¶
Attributes are declared on each entity class with Field, which maps an attribute name
to a key in entity.data:
class Article(BaseEntity):
title: str = Field("title", default="")
keywords: list = Field("keywords", default_factory=list)
id: str = Field("id", read_only=True)
default/default_factory— value returned when the key is absent.read_only=True— assigning to the attribute raisesAttributeError. System fields (id,urn,creator,created_at,updated_at, and oftentype) are read-only.
Auto-sync on write¶
By default an entity has sync=True. Assigning to a field immediately PATCHes the
change to the API:
article.title = "A clearer title" # <-- sent to the server right away
Each write also records the key in entity._dirty_fields. To batch several edits into a
single request, disable auto-sync, make your changes, then save:
article.sync = False
article.title = "New title"
article.description = "New description"
article.save(only_dirty=True) # one PATCH with just the changed fields
save() never sends immutable fields (IMMUTABLE_FIELDS), so system-managed values are
preserved.
Lazy loading¶
Some proxies hand you an entity that contains only its identifier (for example, a sliced collection — see Collections). The moment you read any field other than the identifier, the proxy fetches the full record automatically:
lazy = client.articles[0:50] # 50 lazy proxies, no per-item API calls
first = lazy[0]
first.title # <-- triggers a fetch for just this entity
CRUD operations¶
Through a collection proxy:
# Create
art = client.articles.create(title="A new study", doi="10.1234/example")
# Read
art = client.articles["a-new-study"]
# Update (auto-sync, or batch with save())
art.status = "active"
# Refresh from server
art.refresh()
# Delete
art.delete()
AI enhancement¶
Many entities support server-side enrichment by an AI agent. The call returns the updated entity:
# Via the collection proxy
enhanced = client.articles.enhance("summarizer", identifier="a-new-study")
# Or on a loaded entity
article.enhance_self(agent="summarizer")
Inspection helpers¶
Method |
What it does |
|---|---|
|
Returns the full underlying |
|
Pretty-prints the JSON payload to stdout. |
|
Prints a transposed pandas table of all fields. |
|
The value of the identifier field ( |
|
The URN (raises if the entity has none). |
Read-only / immutable fields¶
Every entity defines IMMUTABLE_FIELDS, which by default includes urn, id,
creator, created_at, and updated_at. Some entities extend it — e.g. guides and
textbooks also make type immutable. These are never sent on save() and assigning to a
read_only field raises AttributeError.