We will be undergoing planned maintenance on January 16th, 2026 at 1:00pm UTC. Please make sure to save your work.

Project Story

Inspiration: From Flaky Locators to Baseline-Safe Automation

Our journey with SafePath began with HakaPath, a Chrome extension we launched at Hakalab to tackle a universal pain point in QA automation: brittle XPath locators that shatter with every UI tweak. As described on HakaPath's page, the original tool analyzes web structures via DOM traversal to generate robust XPaths, saving testers hours of manual drudgery and integrating seamlessly with frameworks like Selenium and Cypress. But as we deployed it in real teams, we kept hearing the same gripe: "These work great in Chrome, but what about Firefox or Safari? One cross-browser run, and everything flakes."

Enter the Baseline Hackathon. We'd been geeking out over Google's Baseline initiative—its promise of "widely available" web features felt like a holy grail for stable testing. Inspired by the hackathon's call to reduce compatibility uncertainty, we spun off SafePath as a proof-of-concept: evolve HakaPath by adding dual XPath/CSS generation and real-time Baseline validation. It was our way of saying, "Let's not just generate locators—let's make them bulletproof across browsers." What started as a weekend hack has us hooked; we're already planning to fold these features into HakaPath v2 with even more bells (like Playwright templates and potential AI-suggested fallbacks as a future enhancement).

What We Learned: The Power (and Nuance) of Baseline

Diving into Baseline was eye-opening. We assumed it was just a checklist, but it's a goldmine of datasets—like the CSS selector compat JSON and HTML baseline mappings—that quantify why a feature like :has() is "limited" (e.g., Firefox <121 gaps). We learned how XPath's HTML roots make it surprisingly vulnerable to spec drifts, unlike CSS's more predictable evolution. Most crucially, Baseline isn't just defensive—it's offensive: it empowers devs to prioritize "high" support features upfront, cutting test maintenance by 40-50% in our trials.

This hackathon reinforced a bigger lesson: Tools like SafePath bridge the gap between "works on my machine" and "scales globally." We also picked up that QA isn't just about speed—it's about trust. Badges showing "Limited: Compat risk (Safari <16)" build that trust, turning uncertainty into actionable intel.

How We Built It: From HakaPath Core to Dual-Mode Magic

SafePath is a lean Chrome extension (Manifest v3) built on HakaPath's foundation: a content script captures clicked elements, background.js normalizes DOM snapshots, and the popup renders 4 variant slots. For the spinoff, we layered in Baseline smarts:

  1. Dual Generation: Always compute XPath (via document.evaluate on snapshots) and CSS (via buildCssCandidates with escapers for IDs/classes/attrs). Slots now parallelize them—left for XPath, right for CSS—no toggles needed.

  2. Baseline Integration: Fetched minified JSON datasets (baseline-compat-min.json for CSS, baseline-html-compat.min.json for HTML). For CSS, regex-match patterns like :has() against features; for XPath, parse elements/attrs to query HTML compat. onLocatorSet hooks trigger checkCssLocatorAgainstBaseline and checkXPathAgainstHtmlBaseline, aggregating "worst severity" (e.g., limited > low) for badges.

  3. UI Polish: Vanilla JS in baseline-hook.js binds inputs with debounced ticks (500ms interval). POM appends to a Python-only textarea for MVP simplicity (e.g., div_content = (By.CSS_SELECTOR, "#id")).

We iterated in VS Code with Chrome dev tools—total build: ~20 hours, leveraging HakaPath's battle-tested capture logic.

Challenges Faced: Parsing the Unparseable and Balancing Scope

XPath validation was our nemesis: Unlike CSS's clean selectors, XPath axes/functions defied simple regex, so we built a custom parser in baseline-client.js (extracting tags/attrs via state machine)—it works 90% but chokes on namespaces (future fix: integrate a lightweight lib). Merging Baseline datasets meant wrangling version comparisons (versionLt util) and edge cases like "unknown" support, which we mitigated with fallbacks to "neutral" badges.

Scope creep hit hard— we wanted multi-lang POM and Shadow DOM piercing, but hackathon deadlines forced ruthless cuts (RIP Supabase sync). Legacy HakaPath code (pre-Baseline) needed hydration without breaking users, teaching us the joy of backward compat.

In the end, these hurdles made SafePath tougher. We're launching HakaPath v2 next month with full Baseline fusion, plus refinements inspired by our learnings. Thanks to the hackathon for sparking this—Baseline isn't just data; it's a movement for reliable web dev. Can't wait to see where it takes us! 🚀

Built With

Share this project:

Updates