santifer/career-ops · error · Error
radancy: cannot resolve search-jobs URL for ${entry.name}
Error message
radancy: cannot resolve search-jobs URL for ${entry.name} What it means
The radancy provider's fetch() throws when resolveListUrl(entry) returns null. resolveListUrl reads entry.api || entry.careers_url, parses it, requires an http: or https: protocol, and normalizes the path to a /<lang>/search-jobs endpoint. Because Radancy hosts branded career sites on arbitrary domains, detect() always returns null — the provider must be wired explicitly with provider: radancy plus a search-jobs api/careers_url.
Source
Thrown at providers/radancy.mjs:273
function resolveMaxJobs(entry) {
const v = entry?.max_jobs;
if (Number.isInteger(v) && v > 0) return v;
return DEFAULT_MAX_JOBS;
}
/** @type {Provider} */
export default {
id: 'radancy',
detect() {
// Branded hosts carry no stable Radancy token in the URL — wire explicitly
// with `provider: radancy`. No auto-detection.
return null;
},
async fetch(entry, ctx) {
const listUrl = resolveListUrl(entry);
if (!listUrl) throw new Error(`radancy: cannot resolve search-jobs URL for ${entry.name}`);
const origin = new URL(listUrl).origin;
const wait = (ms) => (ctx.sleep ? ctx.sleep(ms) : new Promise((r) => setTimeout(r, ms)));
const maxPages = resolveMaxPages(entry);
const maxJobs = resolveMaxJobs(entry);
const jobs = [];
const seen = new Set();
// Proof of life across BOTH transports: any resolved request — including a
// fragment 200 that parses to zero rows — proves the tenant is reachable,
// so a later HTML page-1 failure must not read as "unreachable".
let succeededOnce = false;
// ── Preferred transport: the JSON results fragment ───────────────────────
// Tried first because on legacy-markup tenants the ?p=N HTML page carries a
// multi-megabyte facet blob per page (see the transport note up top). Any
// failure here — non-JSON, no results, endpoint absent — falls through to
// the HTML walk below, so tenants without this endpoint are unaffected.
if (typeof ctx.fetchJson === 'function') {View on GitHub (pinned to 9b17a8ac97)
Solutions
- Add an api: or careers_url: to the entry pointing at the tenant's search-jobs page (e.g. https://careers.munichre.com/search-jobs or https://careers.acme.com/en/search-jobs).
- Confirm the entry is tagged provider: radancy — auto-detection is intentionally disabled for branded hosts.
- Verify the URL string is a well-formed absolute http(s) URL with no leading/trailing whitespace.
- Run detect(entry) before fetch; since detect always returns null for radancy, ensure you are dispatching by the explicit provider field instead.
Example fix
# before — portals.yml entry with provider but no URL - name: Munich Re provider: radancy # after - name: Munich Re provider: radancy api: https://careers.munichre.com/search-jobs
Defensive patterns
Strategy: validation
Validate before calling
// radancy detect() always returns null — must dispatch by explicit provider field
function shouldRunRadancy(entry) {
if (entry.provider !== 'radancy') return false;
const raw = entry.api || entry.careers_url || '';
try {
const u = new URL(raw);
return u.protocol === 'http:' || u.protocol === 'https:';
} catch { return false; }
}
if (!shouldRunRadancy(entry)) {
console.warn(`skip ${entry.name}: radancy needs provider:radancy + http(s) api/careers_url`);
} Type guard
null
Try / catch
try {
await provider.fetch(entry, ctx);
} catch (e) {
if (/cannot resolve search-jobs URL/.test(e.message)) {
console.warn(`[skip] ${entry.name}: add api/careers_url for radancy`);
} else throw e;
} Prevention
- Always set provider: radancy explicitly — auto-detection is intentionally disabled.
- Include an api: or careers_url: pointing at the tenant's search-jobs page in every radancy entry.
- Validate the entry has an http(s) URL before invoking fetch.
When it happens
Trigger: fetch() is called on an entry missing both api and careers_url; the URL is unparseable by new URL(); the protocol is neither http: nor https: (e.g. a mailto: or relative path); detect() was bypassed and fetch invoked directly on a non-Radancy entry.
Common situations: A portals.yml row sets provider: radancy but forgets the api: or careers_url: line; the entry was built from an API response that did not include a careers_url; the URL has a leading space or smart-quote characters from copy-paste.
Related errors
- pinpoint: cannot derive API URL for ${entry.name}
- recruitee: cannot derive API URL for ${entry.name}
- rheinmetall: cannot resolve vacancies URL for ${entry.name}
- rippling: cannot derive API URL for ${entry.name}
- justjoin: careers_url or api must be a trusted justjoin.it U
AI-assisted analysis of santifer/career-ops@9b17a8ac97 (2026-08-13).
Data as JSON: /api/errors/8f0c7e4b4ca6fb68.
Report an issue: GitHub.