EcoWealth×OSHAcademy Findings · passive review · unlisted

A respectful, evidenced read of the public surface

The studying is already built for machines. The buying, the part people pay for, isn't yet.

OSHAcademy did the genuinely hard, generous thing: every course is free to study, and the individual course and program pages are marked up with real Course and EducationalOccupationalProgram schema, better than most training providers. This is not a teardown. It's a short list of places where a finished learner, or a company certifying a crew, hits friction on the way to paying, each with the exact public proof, and each fixable without touching the training itself.

↳ The through-line: everywhere an AI or a fast-scanning buyer would study, OSHAcademy is legible. Everywhere they'd buy the certificate, the catalog hub, the price, the checkout, the company account, it's legacy, split, or pointed at the wrong catalog.

First: what's already strong (and rare)

Free to study is a real differentiator

"All training materials, knowledge checks and activities are free"; you only pay for the certificate/documentation. Most training providers gate the learning. This is a genuine strength; every finding below protects it.

The leaf pages are marked up well

Course pages carry Course schema with an offers array; program pages carry EducationalOccupationalProgram with the full hasCourse breakdown. That's ahead of the field.

You already sell to agents

The Shopify store ships full agent-commerce (UCP 2026-04-08 + MCP (Model Context Protocol) + Shop Pay). You adopted agentic checkout early; most brands haven't. Finding 1 is just about where it points.

Clean, secure delivery

HSTS preload, X-Frame-Options: SAMEORIGIN, X-Content-Type-Options: nosniff, CSP upgrade-insecure-requests, Sucuri WAF, IACET-accredited. Zero page errors on the home page.

Before the findings: the plain-English money

The bottom line, in plain English

No jargon. Everywhere someone studies, OSHAcademy is already legible; these fixes are about the part people pay for, the certificate and the crew account. Here's what each is worth.

Point your agent-ready checkout at certificates → the sale a shopping assistant can actually complete

Your store is fully wired for hands-free AI purchase but stocked with shirts and water bottles, while the $16.99 certificate that earns the money routes to a legacy form, so an assistant told "get my crew the 30-hour certificate" can buy a mug but not the certificate.

A price the machine reads that matches checkout → no surprise that kills the sale

The certificate's structured price sits a dollar or two below what the page actually charges, so an assistant quotes low and the buyer meets a higher number at checkout, a small trust break right where the money changes hands.

A catalog and company page machines can read → high-intent buyers land where they can act

"Search OSHAcademy for confined-space courses" and "how do I certify my company" hit the two pages with no structured data, so your best, highest-value buyers arrive at a door that's blank to machines.

A bookable crew-certificate path → the safety manager buys instead of waiting for a callback

The highest-value buyer, certifying a whole team, ends at a "we'll contact you" form; a self-serve path lets that order complete the moment they're ready.

Four findings: where certificate revenue leaks

1

The one storefront an agent can check out from sells water bottles, not certificates.

What happens. Your Shopify store, store.oshacademy.com, is fully wired for agent-driven purchase: it publishes a UCP merchant profile (version 2026-04-08), an MCP endpoint, and Shop Pay + Google Pay handlers. But its catalog is apparel, water bottles, mousepads, gifts, guides, and an audiobook ("Gear Up with OSHAcademy · Apparel + Accessories"). The certificate and program business, the actual revenue, lives on www.oshacademy.com, which publishes no agent-commerce profile, and routes the purchase to a legacy registration flow.

Why it costs certificate sales: a buyer's agent asked to "get the 30-hour construction certificate for my crew" can hands-free check out a $29 shirt today, but cannot buy a $16.99 certificate the same way. The agentic-commerce capability you already paid for is aimed at the low-margin catalog.

The proof

200 store.oshacademy.com/.well-known/ucpucp.version "2026-04-08", MCP endpoint /api/ucp/mcp, handlers: Shop Pay, Google Pay
200 store.oshacademy.com/llms.txt → "This store implements the Universal Commerce Protocol… Search / Cart / Checkout"
store collections: /collections/oshacademy-apparel, /gifts-for-safety-professionals, /guides-handbooks-and-audio-resources, no certificates
404 www.oshacademy.com/llms.txt  ·  404 www.oshacademy.com/sitemap.xml  ·  no /.well-known/ucp
certificate purchase CTA on a course page → href="../../student/register/step-1.php" (legacy)
OSHAcademy Shopify store selling apparel and accessories
store.oshacademy.com, the fully agent-buyable storefront, pointed at merch. "Gear Up with OSHAcademy · Apparel + Accessories."
2

The catalog hub and the company door, the two surfaces that scale, carry no structured data.

What happens. Your leaf pages are well-marked, but the two pages an agent uses to discover many courses or buy for a team are blank to machines. The 1,000-course catalog hub (/courses/list/course-catalog.html) renders with zero JSON-LD (the structured-data markup search engines and AI assistants read), and the business-account page renders with zero JSON-LD. Course and program pages also carry no Open Graph tags (og = 0), so link previews and AI cards fall back to guesses.

Why it costs certificate sales: "search OSHAcademy for confined-space courses" or "how do I certify my company" are exactly the high-intent, high-value queries, and they land on the two pages with no ItemList / Course / Offer or Organization / Service data to read. The doors that scale are the blind spots.

The proof: rendered-DOM JSON-LD counts (post-JavaScript)

course page 105-hazard-communication-basic: ld+json = 1 (Course) · og = 0
program page 30-hour-construction: ld+json = 1 (EducationalOccupationalProgram) · og = 0
home page: ld+json = 1 (EducationalOrganization) · og = 9
catalog hub course-catalog.html: ld+json = 0 · og = 0
business-account page: ld+json = 0 · og = 0
3

The machine-readable certificate price is wrong, it under-quotes what a buyer actually pays.

What happens. Course 105's Course schema is present (good), but its offers prices don't match the live checkout. The schema lists PDF Certificate $15.99, Mailed $27.99, and "PDF & Mailed" $27.99, while the live page charges PDF $16.99 and PDF + Mailed (Best Value) $29.99. Every format's structured price is stale, and the schema prices the PDF+Mailed combo identically to mailed-only ($27.99), an internal data error. The visible prices are injected by JavaScript from a path your own robots.txt disallows (/programs/fees), so a non-JS crawler sees only a bare $.

Why it costs certificate sales: an assistant that trusts the schema quotes a price $1–$2 below the real one, a small surprise at checkout that erodes trust; an assistant reading raw HTML quotes no price at all. Either way the buyer's agent can't confidently commit.

// what the machine reads: Course schema Offer (105)      // what the human pays: live, rendered
"offers": [
  { "name":"PDF Certificate",      "price":"15.99" },     PDF Certificate ............ $16.99
  { "name":"Mailed Certificate",   "price":"27.99" },     PDF + Mailed (Best Value) .. $29.99
  { "name":"PDF & Mailed Certificate","price":"27.99" }    // = mailed-only price → data error
]

Also

robots.txtDisallow: /programs/fees (the path the live prices load from, invisible to crawlers)
OSHAcademy course 105 Certificate Options showing PDF $16.99 and PDF plus Mailed $29.99
Course 105, live "Certificate Options": PDF Certificate $16.99, PDF + Mailed (Best Value) $29.99. The Course schema on the same page says $15.99 / $27.99.
4

"Buy the certificates for my whole crew" ends at a legacy form and a callback.

What happens. When a learner finishes free study, the "buy your certificate" CTA drops them into /student/register/step-1.php, a legacy .php flow on the Sucuri-fronted custom site (a path your robots.txt disallows). And the company/group path, the highest-value buyer, is a "Request a Business or Educator Account" lead form that ends with "By submitting, you agree to be contacted about this request." It's a request, not a purchase.

Why it costs certificate sales: "buy certificates for my crew's completed courses" or "enroll my company in the 500-series" have no self-serve, agent-fulfillable path. The buyer most worth serving fast, a safety manager certifying a team, hits a callback funnel instead of a bookable checkout.

The proof

course CTA → href="../../student/register/step-1.php"  (robots.txt: Disallow: /student)
business page copy → "By submitting, you agree to be contacted about this request."
form is a lead capture (company, contact, employee count, min 2) → human follow-up, no checkout
OSHAcademy Request a Business or Educator Account lead form
The company/group door: "Request a Business or Educator Account." A contact form and a callback, not a bookable crew-certificate purchase.

Evidence log: method & dates

CheckMethodResult
Canonical served sitecurl -ILwww.oshacademy.com = 200; oshatrain.org = 307 (Sucuri), both behind Sucuri Cloudproxy
Agent-commerce on storeGET /.well-known/ucp, /llms.txtUCP 2026-04-08, MCP endpoint, Shop Pay/Google Pay, both 200
Agent-legibility on main siteGET /llms.txt, /sitemap.xmlboth 404; no /.well-known/ucp
Structured data (rendered DOM)Playwright (Chrome, 2× DPI)course=1 · program=1 · home=1 · catalog=0 · business=0
Certificate price integrityschema Offer vs renderedschema $15.99/$27.99/$27.99 vs live $16.99/$29.99
Purchase & company pathDOM href + page copy/student/register/step-1.php; "agree to be contacted" form
Errors (rendered)pageerror / console listenershome pageerror=0; gtag is not defined throws on course/program/catalog/business
Honesty note. Our probe's raw logs show ERR_FAILED console entries and failed requests, these were induced by our own webfont blocking during screenshotting (a standard trick to beat screenshot hangs), not OSHAcademy defects. The one meaningful client-side error is the ReferenceError: gtag is not defined thrown by the pages' own analytics on the course/program/catalog/business pages (not the home page), worth a look, since it's the tracking that would measure the certificate funnel. All recon was passive: normal-browser navigation and standard public GETs of pages OSHAcademy serves any visitor (plus the store's own published llms.txt / /.well-known/ucp discovery docs). No account was created, no form submitted, no endpoint probed, no robots.txt-disallowed path crawled, no wall routed around. Dates: 2026-07-12.

The opportunity

Four small, additive fixes, no change to the training, the courses, or the brand.

Reconcile the certificate price into one honest Offer; mark up the catalog hub and the company page; and put a bookable, agent-friendly certificate checkout where the "we'll contact you" form is, pointing the agent-commerce capability you already ship at the certificate business. The next two pages show it in your own brand, and hand you the files any AI needs to represent OSHAcademy accurately.

Provisioned by EcoWealth · Digital Provisioning Protocol · provenance‑sealed