santifer/career-ops · error · Error
oraclecloud: untrusted hostname "${parsed.hostname}" — must
Error message
oraclecloud: untrusted hostname "${parsed.hostname}" — must match *.fa[.<region>][.ocs].oraclecloud[1-99].com What it means
Thrown by oraclecloud's assertOracleUrl() when the hostname doesn't match ORACLE_HOST_RE (/^[a-z0-9-]+\.fa\.(?:[a-z0-9-]+\.)?(?:ocs\.)?oraclecloud(?:[1-9][0-9]?)?\.com$/i). Third SSRF gate: allows tenant subdomains of Oracle's FA (Fusion Applications) cloud (e.g. acme.fa.eu.oraclecloud.com, acme.fa.ocs.oraclecloud.com, acme.fa.oraclecloud1.com) while blocking everything else. The regex permits an optional region segment, an optional 'ocs.' segment, and an optional numeric suffix on 'oraclecloud'.
Source
Thrown at providers/oraclecloud.mjs:70
const PAGE_SIZE = 200;
const MAX_PAGES = 25; // safety cap (~5000 jobs); hard ceiling like workday
const RETRY_POLICY = { retries: 3 };
const INTER_PAGE_DELAY_MS = 150; // WAF-aware spacing between same-host pages
// facetsList is a fixed constant on the finder; %3B is the encoded ';' separator.
const FACETS_LIST = 'LOCATIONS%3BWORK_LOCATIONS%3BWORKPLACE_TYPES%3BTITLES%3BCATEGORIES%3BORGANIZATIONS%3BPOSTING_DATES%3BFLEX_FIELDS';
/** @param {string} url */
function assertOracleUrl(url) {
let parsed;
try {
parsed = new URL(url);
} catch {
throw new Error(`oraclecloud: invalid URL: ${url}`);
}
if (parsed.protocol !== 'https:') throw new Error(`oraclecloud: URL must use HTTPS: ${url}`);
if (!ORACLE_HOST_RE.test(parsed.hostname)) {
throw new Error(`oraclecloud: untrusted hostname "${parsed.hostname}" — must match *.fa[.<region>][.ocs].oraclecloud[1-99].com`);
}
return url;
}
// NaN-safe Date.parse — `|| undefined` would also coerce a valid epoch 0.
// (copied from greenhouse.mjs)
function toEpochMs(value) {
if (!value) return undefined;
const parsed = Date.parse(value);
return Number.isNaN(parsed) ? undefined : parsed;
}
function sleep(ms, ctx) {
if (typeof ctx?.sleep === 'function') return ctx.sleep(ms);
return new Promise((resolve) => setTimeout(resolve, ms));
}
/**View on GitHub (pinned to 9b17a8ac97)
Solutions
- Verify the URL matches the expected pattern: <tenant>.fa.<region>.oraclecloud.com — confirm the .fa. segment is present.
- Get the correct URL from the Oracle HCM career site: navigate to the company's career page and copy the full URL from the browser.
- If Oracle introduced a new URL format (new region, new subdomain), update ORACLE_HOST_RE at providers/oraclecloud.mjs:50 to match.
- Check for TLD confusion: must be .com, not .net or .cloud.
Example fix
// before — wrong URL shape careers_url: 'https://acme.oraclecloud.com/careers' // hostname 'acme.oraclecloud.com' fails: missing '.fa.' segment // after careers_url: 'https://acme.fa.eu.oraclecloud.com/hcmUI/CandidateExperience/en/sites/CX_1' // OR if Oracle introduced a new subdomain pattern, update the regex: // const ORACLE_HOST_RE = /^[a-z0-9-]+\.fa\.(?:[a-z0-9-]+\.)?(?:ocs\.)?oraclecloud(?:[1-9][0-9]?)?\.com$/i;
Defensive patterns
Strategy: validation
Validate before calling
const ORACLE_HOST_RE = /^[a-z0-9-]+\.fa\.(?:[a-z0-9-]+\.)?(?:ocs\.)?oraclecloud(?:[1-9][0-9]?)?\.com$/i;
/** Check hostname matches Oracle FA cloud pattern. */
function isOracleFaHost(url) {
try { return ORACLE_HOST_RE.test(new URL(url).hostname); } catch { return false; }
}
if (!isOracleFaHost(entry.careers_url)) {
console.warn(`oraclecloud entry ${entry.name} URL doesn't match *.fa.*.oraclecloud.com`);
continue;
} Type guard
/** @param {string} url @returns {boolean} */
function isOracleCloudUrl(url) {
const ORACLE_HOST_RE = /^[a-z0-9-]+\.fa\.(?:[a-z0-9-]+\.)?(?:ocs\.)?oraclecloud(?:[1-9][0-9]?)?\.com$/i;
try { return ORACLE_HOST_RE.test(new URL(url).hostname); } catch { return false; }
} Try / catch
try {
await oracleProvider.fetch(entry, ctx);
} catch (err) {
if (String(err.message).includes('untrusted hostname')) {
console.warn(`oraclecloud entry ${entry.name} wrong host — needs *.fa.*.oraclecloud.com`);
continue;
}
throw err;
} Prevention
- Verify Oracle URLs match <tenant>.fa.<region>.oraclecloud.com — the .fa. segment is mandatory.
- Copy career site URLs directly from the browser when visiting the company's Oracle HCM career page.
- Update ORACLE_HOST_RE if Oracle introduces new subdomain patterns.
- Distinguish OCI console URLs from HCM career site URLs — only the latter are valid.
When it happens
Trigger: The hostname is valid HTTPS but not an Oracle FA cloud host: e.g. 'oraclecloud.com' (bare, no tenant.fa. prefix), 'careers.oracle.com', 'acme.fa.oraclecloud.net' (wrong TLD), or an attacker-controlled domain. Common misforms: missing the '.fa.' segment, using '.oci.' instead of '.fa.', or a non-cloud Oracle domain.
Common situations: The entry points to a non-careers Oracle domain (oracle.com instead of oraclecloud.com). The tenant URL was copied incorrectly, missing the .fa. path segment. Oracle restructured their cloud URL format (e.g. new region or ocs subdomain) and the regex needs updating. A developer used an OCI (Oracle Cloud Infrastructure) console URL instead of the HCM career site URL.
Related errors
- personio: untrusted hostname "${parsed.hostname}" — must mat
- nodesk: untrusted hostname "${parsed.hostname}" - must be ${
- nofluffjobs: untrusted hostname "${parsed.hostname}" — must
- oraclecloud: invalid URL: ${url}
- oraclecloud: URL must use HTTPS: ${url}
AI-assisted analysis of santifer/career-ops@9b17a8ac97 (2026-08-13).
Data as JSON: /api/errors/680f9583ad9c09b1.
Report an issue: GitHub.