Public
Diamond deal analysis MVP with Rapaport pricing
Val Town is a collaborative website to build and scale JavaScript apps.
Deploy APIs, crons, & store data – all from the browser, and deployed in milliseconds.

Diamond Deal Desk

A small, internal-use wholesale offer comparator. Maintained directly in Val Town; this version is not automatically synchronized to the original GitHub repository.

Use the desk

The app opens with five clearly labeled example offers. Change a total asking price to recalculate automatically. Open a diamond or the details arrow to edit shape, weight, color, clarity and supplier, or see the calculation and list date. Supplier is optional. Prices are USD per whole stone, not per carat.

Search suppliers/specifications; filter above/below the reference; sort by discount, asking price or supplier. On smaller screens the table becomes individual offer cards. Offers are saved in this browser only, not synchronized between devices. Reset examples and removal require confirmation.

Live connection and access

Existing Rapaport credentials are preserved in encrypted Val Town environment settings. Sign in through Sign in for live prices with the omriluz Val Town account. Live-price requests are authorized server-side only for that owner. Guests and other accounts get an explicitly labeled synthetic demo. The public source contains no credentials or licensed price lists.

The hosted app uses std/oauth; platform-level restricted HTTP access was unavailable on this account's plan. The public app shell remains available for demonstrations, while licensed pricing is protected by the app's owner check. Do not remove that check merely to share the demo.

Only these existing environment variables are used:

👉 Add RAPAPORT_CLIENT_ID here: https://www.val.town/x/omriluz/diamond-dealdesk/environment-variables?key=RAPAPORT_CLIENT_ID

👉 Add RAPAPORT_CLIENT_SECRET here: https://www.val.town/x/omriluz/diamond-dealdesk/environment-variables?key=RAPAPORT_CLIENT_SECRET

On returning from settings, the app rechecks access and configuration. Live status is shown only after a successful price response. Bad credentials, access errors and unavailable prices remain errors; demo prices are never substituted for a failed live request.

Calculation and limitations

  • Total reference = Rapaport price per carat × carat weight.
  • Percent difference = (total asking price / total reference − 1) × 100.
  • Negative means below the reference, positive means above. Neither is profit or a buy recommendation.
  • No fictitious buyers, estimated resale values, profit scores, trade history or deal ratings.
  • Scope: natural white diamonds, 0.30–5.99 ct, colors D–J, listed clarity grades IF–SI2. Other categories are outside this prototype.
  • Round and Pear have their own Rapaport lists. Oval, Cushion, Emerald, Princess and Marquise use an explicitly labeled Pear-list proxy, not a shape-specific market price.
  • Cut, lab/report quality, fluorescence, condition, fees, taxes and buyer demand are not evaluated. Confirm these before a transaction.
  • Supplier names and asking prices in the examples are fictional, even when benchmark prices are live.

Rapaport documentation: https://raptech.rapaport.com/rapaport-price-lists/

Implementation

index.ts: Hono HTTP handler, JSON validation, owner-only live access, safe errors, no-store API responses.

rapaport.ts: server-side credentials, single-flight authentication/price requests, 12-second upstream timeouts, one reauthentication after 401, 15-minute bounded in-memory price cache. Refresh bypasses the cache. No secret or upstream response-body logging.

frontend/domain.ts: shared types, validation, examples, deterministic demo formula and arithmetic.

frontend/useDesk.ts: browser-only offer persistence, delayed recalculation, per-row cancellation, request versions/fingerprints to reject stale results.

frontend/components/: React UI, responsive offer sheet, explanation panels and accessible native dialogs. Frontend assets use versioned immutable URLs. Frontend asset serving is restricted to the frontend directory.

Verification

Run selftest.ts in Val Town: 29 assertions covering arithmetic, input validation, date/proxy behavior, authentication rejection, public demo, live API lookup with the saved credentials and caching. Its output reports success only, not credentials or licensed price values.

Run ui-selftest.ts: 14 React-renderer assertions covering initial calculation, editing, invalid values, stale-response protection, storage/reload, search, proxy explanations, failure handling, exact benchmark labeling and responsive component branches. All fixtures are synthetic.

Layout snapshots were checked locally at 1440, 1024, 768, 390 and 320 pixels, with no document-level horizontal overflow. These are isolated layout checks, not an end-to-end browser test of the hosted OAuth flow. Completing interactive Val Town login still requires the owner’s browser.

See PLAN.md for the redesign checklist.