Skip to content
Dylan San GabrielDylan
Get in touch

GET /api/experience

From the restaurant floor to the system the company runs on.

I'm the engineer at RMH3 Dental Supply. I designed, built and run the in-house ERP that replaced off-the-shelf software, a stack of spreadsheets, and an inbox somebody sorted by hand. It covers six sales channels and 32,000 products, and orders have roughly doubled while I've been here without adding anyone to operations.

Most of it started as a spreadsheet, a stack of emails, or a count somebody did on paper every morning. Those are the ones I like, because you find out fast whether the new version actually saved anyone time — the person who used to do it by hand will tell you.

How I got here

  1. 2020 – 24

    Computer Science coursework, George Mason University

    Dean's List. Four years of CS alongside a full-time job — everything below happened while I was in it. I left before the degree was conferred, so what's under it is what I have to show instead.

  2. 2021 – 22

    T-Mobile — sales associate, then store manager

    My first job. When the store manager was getting ready to leave he decided I was working harder than the rest of the floor and spent his last months training me to replace him. I got the job because the team trusted me to run the place, not because I was the best at selling phones.

  3. 2022 – 25

    The Qui, Korean BBQ & Grill — head server

    Promoted twice within months. I was studying for the CYDEO SDET program between shifts — Selenium, Cucumber, REST Assured. That's where the testing habits came from. I still write the test before I trust the fix.

  4. 2025

    RMH3 Dental Supply — hired off the restaurant floor

    They were regulars. They watched me work a section, decided I'd be a good fit for their company, and offered me a job. I started in inventory to learn the products, then shipping, and made it known that the technical work was what I wanted.

  5. 2025 – now

    From a customer-service spreadsheet to the ERP

    Customer service was entirely online, so consolidating it meant a spreadsheet — and the spreadsheet turned into a system. Pricing came next, because winning the buy box by hand doesn't scale. The ERP grew out of those two problems and now runs the company.

Experience

Jun 2025 — Present

Software Engineer · RMH3 Dental Supply, Chantilly, VA

The only engineer at a family-run dental distributor. Built and run the in-house ERP that replaced off-the-shelf software, spreadsheets and inbox triage across six sales channels.

Aug 2022 — Jun 2025

Head Server · The Qui, Korean BBQ & Grill, Fairfax, VA

Ran front-of-house and trained staff. Promoted twice within months. Studied for the SDET bootcamp on the side.

Jan 2021 — Aug 2022

Store Manager · Wireless Vision (T-Mobile), Vienna, VA

Promoted from sales associate to store manager in ten months. Beat performance targets by 30% with perfect customer-satisfaction scores.

Education

Feb – Oct 2024

SDET Bootcamp · CYDEO, Tysons, VA

Java, Selenium, Cucumber/Gherkin, REST Assured, SQL, Jenkins; two ten-person sprint teams automating live web apps.

2020 – 2024

Computer Science coursework · George Mason University, Fairfax, VA

Dean's List. Object-oriented programming, game design, essentials of CS; left before the degree was conferred.

GET/api/experience

Parameters

Request

curl "https://portfolio.dylansg0318.workers.dev/api/experience"
source: src/lib/site.ts

Response200 OK · 5.7 KB

{
  "path": [
    {
      "id": "gmu",
      "when": "2020 – 24",
      "what": "Computer Science coursework, George Mason University",
      "note": "Dean's List. Four years of CS alongside a full-time job — everything below happened while I was in it. I left before the degree was conferred, so what's under it is what I have to show instead."
    },
    {
      "id": "tmobile",
      "when": "2021 – 22",
      "what": "T-Mobile — sales associate, then store manager",
      "note": "My first job. When the store manager was getting ready to leave he decided I was working harder than the rest of the floor and spent his last months training me to replace him. I got the job because the team trusted me to run the place, not because I was the best at selling phones."
    },
    {
      "id": "thequi",
      "when": "2022 – 25",
      "what": "The Qui, Korean BBQ & Grill — head server",
      "note": "Promoted twice within months. I was studying for the CYDEO SDET program between shifts — Selenium, Cucumber, REST Assured. That's where the testing habits came from. I still write the test before I trust the fix."
    },
    {
      "id": "rmh3",
      "when": "2025",
      "what": "RMH3 Dental Supply — hired off the restaurant floor",
      "note": "They were regulars. They watched me work a section, decided I'd be a good fit for their company, and offered me a job. I started in inventory to learn the products, then shipping, and made it known that the technical work was what I wanted."
    },
    {
      "id": "erp",
      "when": "2025 – now",
      "what": "From a customer-service spreadsheet to the ERP",
      "note": "Customer service was entirely online, so consolidating it meant a spreadsheet — and the spreadsheet turned into a system. Pricing came next, because winning the buy box by hand doesn't scale. The ERP grew out of those two problems and now runs the company."
    }
  ],
  "jobs": [
    {
      "title": "Software Engineer",
      "org": "RMH3 Dental Supply",
      "place": "Chantilly, VA",
      "start": "Jun 2025",
      "end": "Present",
      "summary": "The only engineer at a family-run dental distributor. Built and run the in-house ERP that replaced off-the-shelf software, spreadsheets and inbox triage across six sales channels.",
      "bullets": [
        "Sole engineer for the in-house ERP that replaced SellerCloud and a stack of spreadsheets: order intake from six sales channels, inventory, shipping, customer service, returns, invoicing and a two-way QuickBooks Desktop sync.",
        "Daily orders grew from about 270 to about 520 on a 32,000-product catalog with no added operations headcount.",
        "Replaced a morning pricing spreadsheet with a repricing engine that re-evaluates every product every 60 seconds with cooldowns, floors and a no-price-war rule; 138,000+ price changes, each logged with its reason.",
        "Integrated eBay, Amazon SP-API, Shopify, Walmart, Net32 and three carriers: 300,000+ orders ingested, every raw payload stored before parsing, and a source-scan guard so channel code can never write the product catalog.",
        "Put barcodes and scanners on a pen-and-paper warehouse: GS1 parsing, a browser camera scanner, a JSON-to-ZPL label renderer and a self-updating Windows print agent with crash-loop rollback.",
        "Parsed a year of UPS and FedEx invoices into the ERP and surfaced about $26K a year in avoidable address-correction, re-weigh, printer-rental and late fees.",
        "Reconcile the ERP against QuickBooks at line level and settle each discrepancy once in a claims ledger; 2,721 automated tests and ~180 checkpointed scheduled jobs keep app and books in agreement through redeploys.",
        "Run 5–10 parallel Claude Code sessions on one repository behind file locks, hooks that block unrecoverable git operations, and second-model review of consequential changes."
      ]
    },
    {
      "title": "Head Server",
      "org": "The Qui, Korean BBQ & Grill",
      "place": "Fairfax, VA",
      "start": "Aug 2022",
      "end": "Jun 2025",
      "summary": "Ran front-of-house and trained staff. Promoted twice within months. Studied for the SDET bootcamp on the side.",
      "bullets": [
        "Ran front-of-house and trained new servers; promoted twice within months. Completed the CYDEO SDET program alongside full-time shifts."
      ]
    },
    {
      "title": "Store Manager",
      "org": "Wireless Vision (T-Mobile)",
      "place": "Vienna, VA",
      "start": "Jan 2021",
      "end": "Aug 2022",
      "summary": "Promoted from sales associate to store manager in ten months. Beat performance targets by 30% with perfect customer-satisfaction scores.",
      "bullets": [
        "Sales associate promoted to store manager in ten months; ran staffing, cash and inventory, beat targets by 30% over multiple months and raised customer satisfaction from 8.0 to 10/10."
      ]
    }
  ],
  "education": [
    {
      "title": "SDET Bootcamp",
      "org": "CYDEO",
      "place": "Tysons, VA",
      "when": "Feb – Oct 2024",
      "detail": "Java, Selenium, Cucumber/Gherkin, REST Assured, SQL, Jenkins; two ten-person sprint teams automating live web apps."
    },
    {
      "title": "Computer Science coursework",
      "org": "George Mason University",
      "place": "Fairfax, VA",
      "when": "2020 – 2024",
      "detail": "Dean's List. Object-oriented programming, game design, essentials of CS; left before the degree was conferred."
    }
  ],
  "certifications": [
    {
      "name": "Programming using JavaScript",
      "issuer": "Certiport",
      "id": "57SR-4Tp8"
    },
    {
      "name": "Programming using Python",
      "issuer": "Certiport",
      "id": "uadx-XMRJ"
    }
  ],
  "page": "https://portfolio.dylansg0318.workers.dev/about"
}

Live: this is the answer from this site’s API, not a mock. Send re-runs the request with your parameters; if the answer names a page, it opens.

What it ran on before

RMH3 has sold dental supplies since 1993, and it's a family business, not a technical one. When I arrived the work ran on QuickBooks for the books and SellerCloud for inventory, wired together roughly — plus Shopify apps, a stack of Google Sheets in Notion for orders and customer-service cases, CSVs for importing catalogues and product images, and pen and paper on the warehouse floor. No barcodes on the shelves and no scanners.

It wasn't for lack of trying. They had paid SellerCloud for custom API connections and hired contractors on and off for a couple of years to build around the gaps. None of it held, partly because Net32 — the channel that matters most to this business — offers very little API for prices or orders, so the hard part was never the part anyone quoted for. That's the situation the ERP replaced.

Who I work with

I'm the only engineer here, but that isn't the same as working alone. The owner runs the front of the business — branding, the storefront, the catalogue — and ships changes to it by directing AI agents. My job is to make that safe to do: I own the backend, the environments it all runs on (Shopify, Railway, GitHub, Harness) and the hooks and rules that decide what is allowed to land.

So most of what I build is for people who don't write code, and more and more of it is tooling that lets them build too. That's a different job from writing features, and it's most of what I do now. How that actually works

GET/api/work/{id}

Parameters

Request

curl "https://portfolio.dylansg0318.workers.dev/api/work/internal-erp?fields=problem%2Cunique"
source: src/content/projects/{id}

Response200 OK · 972 B · Open /projects/internal-erp

{
  "problem": "RMH3 Dental sells on Net32, eBay, Amazon, Shopify and Walmart, plus direct orders by phone and email. The business ran on off-the-shelf ERP software, a dozen spreadsheets and a shared inbox someone sorted by hand. Every job needed a second tool to finish, the systems disagreed about stock and money, and nobody could say which one was right. Orders were growing and the people weren't.",
  "unique": "I stopped treating it as a dashboard over the data and built it as the place the work actually happens: the order is picked in the page, the return is decided in the page, the bill is matched in the page. Everything hangs off seven daily loops the business runs on — intake, inventory, repricing, service, returns, financials and intelligence — and every job, page and background producer has to trace to one of them. Rules that had cost real money became rules in code.",
  "page": "https://portfolio.dylansg0318.workers.dev/projects/internal-erp"
}

Live: this is the answer from this site’s API, not a mock. Send re-runs the request with your parameters; if the answer names a page, it opens.

How I work

A wrong number is worse than a crash.

If a page breaks, someone tells me that morning. If a number is only a little bit off, it gets used for a month before anyone checks. So most of the work goes into the second one.

If they have to export it, it isn't finished.

Somebody dropping the data into a spreadsheet to finish their job means the screen didn't do what they needed. That's the part I go back and fix.

Save what the vendor sent, read it later.

Every payload gets stored exactly as it came in, before anything touches it. When someone asks a different question six months later, the answer is already sitting there.

Right now

Running a fleet of AI coding sessions against one codebase without them corrupting each other. It's mostly hooks and rules that make the dangerous operations impossible instead of just telling you not to. The write-up

Off the clock

Cooking, mostly. I play a bit of music. And I'll drive further than I should for a restaurant I haven't tried yet.

GET/api/dylan

Parameters

Request

curl "https://portfolio.dylansg0318.workers.dev/api/dylan?view=plain&fields=principles%2Copen_to%2Clooking_for"
source: src/lib/site.ts

Response200 OK · 1.0 KB · Open /

{
  "principles": [
    {
      "title": "A wrong number is worse than a crash.",
      "body": "If a page breaks, someone tells me that morning. If a number is only a little bit off, it gets used for a month before anyone checks. So most of the work goes into the second one."
    },
    {
      "title": "If they have to export it, it isn't finished.",
      "body": "Somebody dropping the data into a spreadsheet to finish their job means the screen didn't do what they needed. That's the part I go back and fix."
    },
    {
      "title": "Save what the vendor sent, read it later.",
      "body": "Every payload gets stored exactly as it came in, before anything touches it. When someone asks a different question six months later, the answer is already sitting there."
    }
  ],
  "open_to": "Open to backend / full-stack roles",
  "looking_for": "A backend or full-stack role, remote or in Northern Virginia. If that's what you're hiring for, let me know.",
  "page": "https://portfolio.dylansg0318.workers.dev/"
}

Live: this is the answer from this site’s API, not a mock. Send re-runs the request with your parameters; if the answer names a page, it opens.

What I work with

Ordered by how often I reach for it, not alphabetically.

Languages
TypeScript, JavaScript, SQL, Python, Java
Backend & data
Node.js, Express, PostgreSQL, REST APIs, SOAP, Flask, MySQL
Frontend
React, Vite, Tailwind CSS, Astro
Integrations
QuickBooks Desktop, Amazon SP-API, eBay, Shopify, Walmart, Net32, USPS / UPS / FedEx, Gmail API, ZPL
Testing
Jest, Selenium, Cucumber / Gherkin, REST Assured, JUnit / TestNG, PyTest, Postman
Ops & tooling
GitHub Actions, Docker, Railway, Cloudflare Workers, Harness, Jenkins, Jira, Claude Code

Certifications

  • Programming using JavaScript · Certiport · 57SR-4Tp8
  • Programming using Python · Certiport · uadx-XMRJ
based_in
Chantilly, VA
timezone
US Eastern
open_to
Backend · full-stack · remote or Northern Virginia
email
dylansg0318@gmail.com
GET/api/resume

Parameters

Request

curl "https://portfolio.dylansg0318.workers.dev/api/resume?format=json&fields=skills%2Ccertifications"
source: src/lib/site.ts

Response200 OK · 1.2 KB · Open /resume

{
  "skills": {
    "Languages": [
      "TypeScript",
      "JavaScript",
      "SQL",
      "Python",
      "Java"
    ],
    "Backend & data": [
      "Node.js",
      "Express",
      "PostgreSQL",
      "REST APIs",
      "SOAP",
      "Flask",
      "MySQL"
    ],
    "Frontend": [
      "React",
      "Vite",
      "Tailwind CSS",
      "Astro"
    ],
    "Integrations": [
      "QuickBooks Desktop",
      "Amazon SP-API",
      "eBay",
      "Shopify",
      "Walmart",
      "Net32",
      "USPS / UPS / FedEx",
      "Gmail API",
      "ZPL"
    ],
    "Testing": [
      "Jest",
      "Selenium",
      "Cucumber / Gherkin",
      "REST Assured",
      "JUnit / TestNG",
      "PyTest",
      "Postman"
    ],
    "Ops & tooling": [
      "GitHub Actions",
      "Docker",
      "Railway",
      "Cloudflare Workers",
      "Harness",
      "Jenkins",
      "Jira",
      "Claude Code"
    ]
  },
  "certifications": [
    {
      "name": "Programming using JavaScript",
      "issuer": "Certiport",
      "id": "57SR-4Tp8"
    },
    {
      "name": "Programming using Python",
      "issuer": "Certiport",
      "id": "uadx-XMRJ"
    }
  ],
  "page": "https://portfolio.dylansg0318.workers.dev/resume"
}

Live: this is the answer from this site’s API, not a mock. Send re-runs the request with your parameters; if the answer names a page, it opens.