WW-81 (WING-78) — Search (BYO-key) vs Historic JOA (bulk) ingestion strategy¶
Spike research. Produced by fleet worker (grok kind, DESKTOP-D249KD4), 2026-07-24. Reviewed and committed by WT-2f62. Builds on WW-78.
Architecture ownership¶
| Concern | Owner |
|---|---|
| Live open jobs, ApplyURI, hiring-path filters, refresh-on-demand | UsaJobsSource + user BYO Search key |
| Scheduled bulk, local index, demo fixtures, MOS→series examples | WW-side Historic JOA ingest (optional Announcement Text for long text) |
| Codelists (hiring paths, series, opening statuses) | Unauth codelist endpoints — cache on WW or per client |
| Apply path | Deep-link only (WW-82) |
Staleness policy (Historic)¶
| Use | Acceptable lag |
|---|---|
| Demo / screenshots / offline browse | Days–weeks |
| MOS→series "example past roles" | Quarterly OK |
| "What's open for me this week?" | Not Historic — must be Search |
Suggested WW schedule: daily or weekly delta by StartPositionCloseDate / open-date windows;
store positionOpeningStatus; UI never promotes an "Accepting" Historic row to applyable.
Guided key connect flow (recommended UX)¶
Same pattern as an ATS/LinkedIn connection — never block first-run on it (kills GTM "value after
install"). A 3-step wizard: open the USAJOBS developer API request form → fill the 6 fields (we
suggest the "use description" text) → paste the key from email into WorkWingman. First Search run
uses the user's confirmed skills/series/location + HiringPath metadata chips (never sort keys —
WW-74/WW-79 Kerr rule). Deep-link out via ApplyURI/PositionURI; WW never Submits, never
touches login.gov.
Honest UI copy (recommended)¶
Card title: Connect USAJOBS (free API key)
Body:
To show open, applyable federal jobs, WorkWingman uses the official USAJOBS Search API with your free developer key — same idea as bringing your own data keys elsewhere. USAJOBS asks you to request a key on their site (name, email, phone, organization, a short use description, and their terms). It usually takes a few minutes once the key email arrives. We store the key only in your local vault and call USAJOBS from this machine.
What you get without a key:
You can still explore historical federal announcements for research and practice. Those are not live openings and cannot start an application here.
Suggested form "use description" snippet (≤255 chars):
Personal job search: find open federal roles matching my skills inside the WorkWingman desktop app on my computer; no redistribution.
Do not claim: "instant key," "no signup," or "we'll get the key for you." Do claim: free, official, public JOA data only; Public jobs by default; Status jobs may need extra USAJOBS authorization.
Go/no-go summary for P2¶
| Decision | Verdict |
|---|---|
| JSON-only Search discovery (no Playwright) | GO — designed for it |
| Per-user BYO Search key for DISCOVERY | GO — matches BYOK + ToS shape |
| Historic JOA for live applyable discovery | NO-GO (product + missing ApplyURI + weak query surface) |
| Historic JOA for demo/offline/corpus | GO — with non-applyable labeling |
| Block first-run on USAJOBS key | NO-GO — kills GTM "value after install" |
| Connect-key step like other integrations | GO — with honest multi-minute copy |
Bottom line for GTM: A veteran should feel value from MOS translation immediately. Live federal openings wait on a ~5–15 minute (if email is fast) free key connect, framed honestly like other integrations — not a dark-pattern wall, and not replaced by Historic "fake open" jobs.
Open questions¶
| # | Question | Why it matters | How to close |
|---|---|---|---|
| Q1 | Key email SLA — automated minutes vs human hours/days? | Friction estimate floor vs worst case; GTM copy honesty | One controlled key request, or email access@usajobs.gov |
| Q2 | Request/min or day limits per key beyond 10k rows/query? | Saved-search refresh budget, governor UI | Empirical 429/header capture under load |
| Q3 | WhoMayApply=Status/All authorization — how obtained? |
Veterans often need status/VEOA paths beyond Public | Document Status-key path; help-desk note on API Request page |
| Q4 | ToS "requesting company" + derivative works for desktop BYO vs optional WW-hosted cache | Whether any server-side Search proxy is allowed | Legal read of USAJOBS API ToS; default client-side BYO only |
| Q5 | Should constructable GetJob/ViewDetails/{controlNumber} ever be used from Historic "Accepting" rows? |
Tempting loophole for zero-key discovery | Recommend No for apply CTAs; optional "View on USAJOBS (verify status)" with strong offline labeling only after product review |
| Q6 | Historic full-corpus size / refresh cost (~3.2M rows × pages of 500) | Ops disk, first-sync time, CI fixtures | Sample strategy: series+agency slices + date windows; not full 3.2M on day one |
| Q7 | Announcement Text volume for corpus enrichment | Storage vs value for federal-résumé practice | Enrich on demand by control number, not full dump |
Evidence appendix¶
Official docs (fetched 2026-07-24)¶
- API Reference overview — three REST APIs; Search auth; paging 250 default / 500 max
- Authentication — API Request form; headers Host/User-Agent/Authorization-Key; codelists unauth
- Rate Limiting — Search: Public default, 10k rows/query, 500/page; Code List/Dynamic Search "No limits"
- GET /api/Search — currently open JOAs; ApplyURI; HiringPath values incl.
vet - GET /api/HistoricJoa — no auth; current + past; smaller fields; continuation tokens
- GET /api/HistoricJoa/AnnouncementText — no auth; long text
- API Access Request form
- Tutorials: Search Jobs, Past job announcements
- API Terms (embedded on developer site): key confidentiality; no key sharing; data for requesting company; OPM may limit transactions
Live probes (this session, 2026-07-24)¶
| Call | Result |
|---|---|
GET /api/search no headers |
401 |
GET /api/search fake Authorization-Key |
401 |
GET /api/historicjoa |
200, totalCount 3,187,813, pageSize 500 |
| Historic series 2210 closed Jan 2024 | Statuses: Candidate selected / canceled / under review / closed; no ApplyURI |
| Historic open-date last 7 days | Includes "Accepting applications" rows |
GET /api/codelist/positionopeningstatuses |
Codes: Accepting applications, Job closed, Reviewing applications, Job canceled, Hiring complete |
| AnnouncementText by control number | 200, long HTML text, no auth |
In-repo context¶
docs/technical/veteran-vertical-design.md— P2 BYO Search; Phase-2 spikes WW-78..83docs/technical/integration-keys.md— vault BYOK pattern for a new USAJOBS rowdocs/technical/ww82-federal-apply-path-reality.md— apply = login.gov deep-link out only