Skip to content

RobertsLab/lab-package-tracker

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

2 Commits
 
 
 
 
 
 
 
 
 
 

Repository files navigation

📦 Lab Package Tracker

A lightweight, shared web app for research labs to track incoming and outgoing packages so shipments never get lost in email threads again. Anyone in the lab can add a package; everyone can see its status. Perishable and overdue shipments are made impossible to miss.

Built as a zero-dependency static site (plain HTML/CSS/JavaScript) — no build step, no paid services, no login required for the prototype. It runs from a folder and deploys to GitHub Pages in minutes.


Features

  • Package entry form — tracking number, carrier, description, vendor, recipient, delivery location, expected date, notes, and a full perishable workflow (details, storage required, action-needed-by, emergency contact).
  • Dashboard — card layout showing status, tracking #, carrier, description, recipient, expected delivery, perishable status, and last updated. Perishable packages sort to the top.
  • Impossible-to-miss alerts
    • Red PERISHABLE badge on perishable packages.
    • Orange OVERDUE highlight when the expected date has passed.
    • A banner warns when a perishable package is delivered but not yet received (i.e. sitting on a dock warming up).
  • Filters — All / Active / Perishable / Overdue / Problem / Delivered.
  • Search — by tracking number, person, vendor, or description.
  • Auto-generated tracking links — a "Check tracking ↗" button opens the carrier's public tracking page in a new tab (UPS, FedEx, USPS, DHL, Amazon). No API key required.
  • Manual status pipeline — Ordered → Shipped → In transit → Out for delivery → Delivered → Received by lab, plus Problem/delayed and Lost/needs-follow-up. Every change is timestamped with an optional note.
  • Package history / timeline — see every status change on the Details view.
  • Mark received, Report missing, Edit, and per-package QR code for lab signage.
  • CSV export of the full package log.
  • Notification hooks — placeholder notifyEmail / notifySlack functions (log to console today; wire to a real service later).
  • Mobile-friendly — usable from the loading dock, hatchery, or field site.

Quick start (run locally)

Because the app is fully static, you just need to serve the folder over HTTP (opening index.html via file:// works too, but a local server avoids browser quirks).

# clone, then from the project folder:
python3 -m http.server 4173
# open http://localhost:4173

Any static server works equally well:

npx serve .           # Node
php -S localhost:4173 # PHP

On first load the app seeds four sample packages (see below). Use Reset sample data to restore them at any time.


Deploy

GitHub Pages

  1. Push this repo to GitHub.
  2. Repo Settings → Pages → Build and deployment.
  3. Source: Deploy from a branch, branch main, folder / (root).
  4. Your app is live at https://<user>.github.io/<repo>/.

No build step or configuration is needed.

Netlify / Vercel / Render

Point the service at this repo and set:

  • Build command: (none)
  • Publish / output directory: . (the repo root)

Sample data

The seed (see js/seed.js) includes exactly the four requested scenarios, with dates computed relative to today so the demo always looks live:

  1. Equipment — Benchtop microcentrifuge (UPS, in transit).
  2. Reagent — Taq polymerase + dNTP mix (FedEx, shipped, store at −20 °C).
  3. Perishable biological sample — Pacific oyster tissue for RNA extraction (USPS, out for delivery, dry ice, −80 °C, emergency contact).
  4. Delayed / lost — Custom antibody held at customs (DHL, overdue, flagged as a problem).

Project structure

lab-package-tracker/
├── index.html           # markup + modals
├── css/
│   └── styles.css       # clean academic style, mobile-first
└── js/
    ├── model.js         # data model: carriers, statuses, helpers (isOverdue…)
    ├── carriers.js      # tracking-URL builder + live-status API stub
    ├── notifications.js # email/Slack notification hook placeholders
    ├── seed.js          # sample data
    ├── store.js         # data-access layer (localStorage; swap for a backend)
    └── app.js           # UI controller: render, filter, search, modals, CSV

Each JS file is wrapped in an IIFE and exposes a single window.LPT_* object, so the files load in plain <script> tags with no bundler.


Data model

A Package (see the header comment in js/model.js):

Field Notes
id generated
tracking_number required
carrier UPS | FedEx | USPS | DHL | Amazon | Other
tracking_url derived from carrier + number
description required
vendor_or_sender, recipient, delivery_location free text / preset
expected_delivery_date YYYY-MM-DD
status see status pipeline above
is_perishable, perishable_details, storage_required, action_needed_by, emergency_contact perishable workflow
notes free text
history timeline of {ts, status, note, by}
last_updated, received_at, problem_flag bookkeeping

Upgrading the prototype

The app was designed so the two "prototype shortcuts" can be replaced without touching the UI.

1. Shared storage (replace localStorage)

Data currently lives in each browser's localStorage, so it is not shared between people — fine for a single kiosk/tablet, not for a whole lab. To make it truly shared, re-implement the six methods in js/store.js (getAll, get, add, update, remove, replaceAll) against a backend and await them in app.js. Good no-/low-cost options:

  • Supabase — hosted Postgres + REST/JS client, generous free tier.
  • Firebase Firestore — realtime sync, free tier.
  • SQLite + a tiny API — e.g. a small Express/FastAPI service on Render.

Because every read/write already flows through store, nothing else changes.

2. Real carrier tracking (replace manual status)

Status is updated manually today. js/carriers.js contains fetchLiveStatus(pkg) — a documented stub — and each carrier in model.js has a spot for an api block. Implement the fetch there, add a "Refresh from carrier" button, and merge the returned status via store.update(). Carrier API keys must live server-side, never in this client code.

3. Notifications

js/notifications.js logs to the console. Point notifyEmail / notifySlack at a serverless function (SendGrid/SES) or a Slack Incoming Webhook — keep all secrets server-side.


Notes & limitations

  • No authentication by design (prototype). Add auth when you move to a shared backend.
  • The QR code image uses a free public endpoint (api.qrserver.com) and needs internet; it degrades gracefully to a plain link offline. Bundle a local QR library to remove that dependency.
  • Amazon has no universal public tracking-by-number page, so its "Check tracking" link points to the orders page.

License

MIT — use it, adapt it, share it with your lab.

About

No description, website, or topics provided.

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

No releases published

Packages

 
 
 

Contributors