actions.py covers skip, donate, cart add/remove, subscriptions and vacation holds. Every mutating endpoint on the site is guarded by rotating per-render tokens, so each action re-derives them from a live page rather than storing anything; skip additionally compares the date the server states in its confirmation against the date it was asked to skip, and refuses on a mismatch. All actions default to dry_run. tools/compat.py records what the integration assumes about a site that offers no API and no stability contract, and CI asserts it daily. Only the unauthenticated surface is covered: checking the rest would mean putting a personal account password in public repo secrets.
4.3 KiB
4.3 KiB
Changelog
All notable changes to this project are documented here.
The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.
[Unreleased]
Added
actions.py: the write layer — skip a delivery, donate a box, add/remove cart items, subscribe/unsubscribe with a frequency, and add a vacation hold over a date range (distinct from skipping: three weeks away is one hold, not three skips). Parsers for current subscriptions and scheduled holds.tools/compat.pyplus a dailycompat.ymlworkflow: records every assumption this integration makes about freshharvest.com and asserts it against the live site, refreshing the matrix in README and opening an issue on drift.FreshHarvestClient.async_fetch, restored as the shared authenticated-fetch primitive that both the snapshot read and every write action build on.
Notes
- Actions default to
dry_run=Trueand report exactly what they would submit. Nothing has been executed against a live account yet.
[0.3.0] - 2026-08-03
Prepared for public release as a HACS custom repository.
Added
- Every cost component is now its own entity rather than an attribute: subtotal, box price, add-ons, tax, and delivery fee for the next delivery, plus a total and free-delivery-remaining for the open order.
binary_sensor.fresh_harvest_order_open, which turns off when the cutoff passes — the last moment to change the box.sensor.fresh_harvest_delivery_day.- Parsing for the driver tip, potential Bounty savings, and the free-delivery threshold, with the threshold carried across orders because the progress bar only renders on carts below it.
LICENSE(MIT),hacs.json, and a CI workflow running hassfest, the HACS action, and the test suite.tests/test_translations.py, which cross-checks every entity'stranslation_keyagainst both translation files and fails on an orphan or a missing name.
Changed
- Entities share a
FreshHarvestEntitybase and declare ascope(account,next_order,open_order), so a description states only the field it reads instead of repeating None handling. manifest.jsondocumentation and issue-tracker URLs now point at GitHub; they previously pointed at a private forge that no installer could reach.- Fixture cart identifiers replaced with placeholders.
[0.2.0] - 2026-08-03
Added
sensor.fresh_harvest_next_delivery_add_ons, the combined cost of the add-ons excluding the produce box.add_ons_totalandbox_priceattributes on the item-count sensor.- A test asserting
add_ons_total + box_priceequals the portal's own subtotal, so a mis-parsed price cannot pass silently.
Changed
add_onsattribute entries now carry quantity, unit, and extended price (4 Complete Recovery Smoothie 15.2 fl oz — $17.96) rather than a bare name. Templates reading these strings will need updating.- The test fixture's totals are now internally consistent, so the subtotal reconciliation is a real invariant rather than copied numbers.
[0.1.0] - 2026-08-03
Added
- Config flow taking freshharvest.com portal credentials.
- Session client implementing the two-step login handshake against
/s/popup/loginand/s/submit/login, including the per-sessionLoginSecurityandSubmitTokenanti-replay fields, with one automatic re-authentication when a session lapses. - Dashboard parser reading delivery day, next arrival date, both upcoming
carts, produce-box contents, add-ons, and order totals from a single
GET /p/dashboard/details. - Update coordinator polling every 6 hours, surfacing auth failures as
ConfigEntryAuthFailedso Home Assistant prompts for re-authentication. - Five sensors: next delivery date, next delivery total, next delivery item count, open order delivery date, and shopping window.
- Parser tests covering totals, contents, the locked/open distinction, money parsing, and year rollover on undated cart tabs.
- English translations under
translations/en.json, which is where custom integrations read entity and config-flow strings from. - Example dashboard view under
examples/dashboard-view.yaml: a three-section tab with a delivery countdown, order tiles, and the full box contents.