Skip to content

Add barcodes to custom foods - #69

Merged
rwestergren merged 2 commits into
rwestergren:mainfrom
Denniso2:custom-food-barcodes
Oct 13, 2026
Merged

rwestergren merged 2 commits into
rwestergren:mainfrom
Denniso2:custom-food-barcodes

Conversation

@Denniso2

Copy link
Copy Markdown
Contributor

Custom foods can now carry product barcodes, so a food created through
the MCP server is found when its package is scanned in the Cronometer
app.

Cronometer keeps barcodes on the food object as a list of bare digit
strings: get_food on a branded food returns e.g. ["602652270284"],
and on a custom food []. Verified against the live API on a throwaway
custom food, using the same add_food payloads this change sends:

  • creating the food with a barcode in the payload stored it
  • re-saving the full food object with a different list replaced the
    barcode and left nutrients and measures unchanged
  • scanning a generated barcode for the saved code with the mobile app
    found the custom food
  • find_food (search_foods) does not match barcodes, so the tool
    docs say so

Changes:

  • client: create_custom_food and update_custom_food take
    barcodes. On update it replaces the whole list ([] clears it,
    None leaves it alone) and is validated before the food is fetched,
    like the serving arguments.
  • client: _normalize_barcodes strips the spaces and dashes
    barcodes are printed with, requires 8, 12, 13 or 14 digits and
    verifies the GS1 check digit, so a digit misread off a label (for
    instance by a model reading a photo) is rejected instead of saved as
    a code that never scans. 8-digit codes are accepted as EAN-8 or as
    UPC-E. A UPC-E check digit belongs to the UPC-A it abbreviates, so
    without the expansion the real 8-digit codes on small packages would
    fail the check.
  • server: both tools expose barcodes, and get_food_details now
    returns the food's barcodes so a caller can add one to the existing
    list.
  • README: the tool table rows mention barcodes.

Notes:

  • create_custom_food now always sends "barcodes" ([] when none
    are given). Every custom food edit already re-sends barcodes: []
    through add_food, so the server accepts it.
  • Codes are stored as given. A UPC-A and the same code written as a
    13-digit EAN with a leading 0 are not merged, since it is untested
    whether the app's lookup treats the two forms as the same.

Cronometer keeps barcodes on the food object as a list of bare digit
strings, and add_food accepts that list on create and on the full-object
re-save that edits use. A custom food saved with a barcode is found when
that barcode is scanned in the mobile app.

create_custom_food and update_custom_food take `barcodes` (on update it
replaces the whole list; [] clears it). Codes are normalized and their
GS1 check digit verified, so a digit misread off a label is rejected
instead of saved as a code that never scans. get_food_details now
returns the food's barcodes.

@rwestergren rwestergren left a comment

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good - just an organization change

Comment thread src/cronometer_api_mcp/client.py Outdated
As requested in review: normalize_barcodes and its check-digit helpers now live in their own module, with their tests in tests/test_barcode.py. normalize_barcodes drops the leading underscore since client.py imports it across modules; the code is otherwise unchanged.

@rwestergren rwestergren left a comment

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good, thanks for the contribution

@rwestergren
rwestergren merged commit d76372f into rwestergren:main Oct 13, 2026
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants