Email-to-Label on ShipStation
Unattended email-to-label pipeline on ShipStation: parse order emails, place on retailer sites without an API, rate-shop, label and track. The same intake layer points at Extensiv and NetSuite for 3PL ship-from (targets).
- Logistics/3PL
- ShipStation
- Extensiv
- NetSuite
- Gmail
- Order Intake
Operational outcome
Email-to-Label on ShipStation
Automation
Measured result
Process that consumed staff hours every day now runs unattended
Overview
The project at a glance
Orders arrived as unstructured emails and were retyped by hand, then again in the shipping platform. We built an unattended pipeline that reads order emails, places orders on retailer sites without an API, then rate-shops, labels and tracks each shipment through ShipStation, with every stage persisted so it resumes after a failure. The same intake → label layer points at Extensiv and NetSuite when a 3PL needs ship-from automation (targets for new work).
Origin pattern: A shipping-automation build: order email → label → tracking. Do not read this as a 3PL client engagement. The source is a legacy 2015-2020 repo with no linked Notion project. No client name is used here.
What the engagement had to achieve
- Ingest unstructured order emails into a structured order
- Place orders where no API exists (retailer sites without an API), with an explicit re-place path
- Rate-shop, buy labels and push tracking via ShipStation
- Persist every stage so an unattended worker resumes after failure without double-processing
The story
Email in, label out — still done by hand
What was at risk
The Challenge
Plenty of fulfilment operations still receive orders as emails: forwarded confirmations, HTML order summaries, PDFs. A person reads each one, re-keys it where it needs to go (sometimes a supplier or retailer site with no API), then re-keys it again in the shipping platform to compare rates, buy a label and push tracking back out. Every hand-off is a place for typos, missed orders and late labels. Because it's manual, nothing resumes on its own when something breaks halfway through.
Order details live in HTML emails and attachments. Staff retype them twice — once for placement, once for shipping.
Some retailer or supplier sites expose no order API. Manual browser work fills the gap — fragile and hard to resume cleanly after a mid-flow failure.
EDI 940/945/856 order and ship-confirm flows are not part of this build and are not claimed.
How we responded
The Solution
Persist every stage; resume instead of restart
Gmail API reads order emails. MimeKit and HtmlAgilityPack parse and sanitize the HTML into a structured order.
Per-site browser automation (Selenium + ChromeDevTools), with an explicit re-place path for failed or changed orders. Described as sites without an API — not as a recommended practice; third-party site automation has ToS implications.
Rate shopping → label generation → tracking. ShipStation is the only shipping platform we have code for in this build.
Every stage is persisted to SQL Server, so an unattended job worker picks up where it stopped instead of double-processing.
The same intake → normalize → rate/label → track pipeline today would run against carrier and shipping APIs (and WMS order APIs) wherever an API exists. EasyPost, ShipHero, Extensiv and regional carrier APIs are common equivalents — market analogues, not delivered.
What we built
The concrete capabilities designed, built, and shipped in this engagement.
Gmail email ingestion and HTML parse
Gmail API reads order emails; MimeKit and HtmlAgilityPack parse and sanitize HTML into a structured order.
Browser placement for sites without an API
Per-site Selenium + ChromeDevTools automation places orders on retailer sites that have no order API, with an explicit re-place path for failed or changed orders.
ShipStation rate-shop → label → track
Shipping via ShipStation API: rate shopping, label generation, and tracking — the only shipping platform we have code for in this build.
SQL Server stage persistence
Every pipeline stage is persisted to SQL Server so progress survives restarts and retries.
Unattended resumable job worker
.NET job worker picks up where it stopped instead of double-processing — the pipeline runs unattended end to end.
Explicit non-claims held on-page
No EDI/ASN. No invented client name. No 3PL-client claim. Extensiv and NetSuite appear only as integration targets.
The stack
The tools behind the build, and the role each one played.
ShipStation
Gmail
.NET
SQL Server
Selenium
Extensiv
Integration target — not delivered in this build.
NetSuite
Integration target — not delivered in this build.
MercuryGate
Integration target — not delivered in this build.
FreightPOP
Integration target — not delivered in this build.
QuickBooks
Integration target — not delivered in this build.
Descartes
Integration target — not delivered in this build.
Courier POD images
Integration target — not delivered in this build.
What changed
Beyond the launch
Lasting improvements
The changes that keep paying off after the engagement ended.
- Qualitative only (Notion/repo wording): "A process that consumed staff hours every day now runs unattended"
- Design/process outcome: Resumable stage persistence — every stage saved to SQL Server so retries do not double-process
- Design/process outcome: Explicit re-place path for failed or changed orders on retailer sites without an API
- No quantitative metrics claimed
Swipe to see more
All case studiesWant an outcome like this one?
A short introductory call covers what's holding you up, whether we can help, and the first thing worth building.