{"openapi":"3.1.0","info":{"title":"Factorial HR (BYOK) API","version":"0.1.0","description":"Factorial HR (BYOK) lets an AI assistant read your own Factorial HR data through the Factorial HR API with a key you supply (Factorial API key (admin)). Read-only: 12 tools (list_job_postings, list_applications, list_application_phases, list_hiring_stages, list_candidate_sources, list_rejection_reasons, list_teams, list_locations, list_company_holidays, list_leave_types, list_job_roles,...\n\nEvery operation is read-only or compute-only. The same tools are available over MCP (streamable HTTP) at https://byok-factorial.connectorbay.com/mcp.","contact":{"name":"Unify Dynamics LLC","email":"agent@connectorbay.com","url":"https://connectorbay.com/byok-factorial/docs"},"termsOfService":"https://connectorbay.com/byok-factorial/terms"},"servers":[{"url":"https://byok-factorial.connectorbay.com"}],"externalDocs":{"url":"https://connectorbay.com/byok-factorial/docs"},"security":[{"upstreamKey":[]}],"components":{"securitySchemes":{"bearer":{"type":"http","scheme":"bearer","description":"Optional. A Pro API key raises rate limits; no credentials are required."},"upstreamKey":{"type":"apiKey","in":"header","name":"X-Upstream-Key","description":"Your own key for the service this connector wraps (bring your own key). Used for that one call only; never stored, logged or cached."}},"schemas":{"Error":{"type":"object","properties":{"ok":{"const":false},"error":{"type":"object"}}}}},"paths":{"/v1/tools/list_job_postings":{"post":{"operationId":"list_job_postings","summary":"List job postings with title, status, contract type, category, workplace type, schedule, team and location ids. Use for ","description":"List job postings with title, status, contract type, category, workplace type, schedule, team and location ids. Use for \"Which Factorial job postings are published right now\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"status":{"anyOf":[{"enum":["draft","published","unlisted","archived","cancelled","deleted"],"type":"string"},{"type":"null"}],"default":null,"description":"Posting status: draft, published, unlisted, archived, cancelled or deleted.","title":"Status"},"team_id":{"anyOf":[{"maxLength":40,"type":"string"},{"type":"null"}],"default":null,"description":"Only postings of this team id.","title":"Team Id"},"location_id":{"anyOf":[{"maxLength":40,"type":"string"},{"type":"null"}],"default":null,"description":"Only postings at this location id.","title":"Location Id"}},"title":"list_job_postingsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_applications":{"post":{"operationId":"list_applications","summary":"List applications with job posting, candidate id, phase, qualified flag, rating, source and creation time (no contact de","description":"List applications with job posting, candidate id, phase, qualified flag, rating, source and creation time (no contact details, CV or cover letter). Use for \"How many applications does Factorial job posting 12 have\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"ats_job_posting_id":{"anyOf":[{"maxLength":40,"type":"string"},{"type":"null"}],"default":null,"description":"Only applications for this job posting id.","title":"Ats Job Posting Id"},"ats_application_phase_id":{"anyOf":[{"maxLength":40,"type":"string"},{"type":"null"}],"default":null,"description":"Only applications in this phase id.","title":"Ats Application Phase Id"},"qualified":{"anyOf":[{"type":"boolean"},{"type":"null"}],"default":null,"description":"True for qualified applications only, false for the rest.","title":"Qualified"},"limit":{"anyOf":[{"maximum":100,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"How many records to return (1 to 100).","title":"Limit"},"after_id":{"anyOf":[{"maxLength":80,"type":"string"},{"type":"null"}],"default":null,"description":"Cursor for the next page: the end_cursor value from the previous answer's meta.","title":"After Id"}},"title":"list_applicationsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_application_phases":{"post":{"operationId":"list_application_phases","summary":"List the hiring phases of job postings with type, position and counts of applications. Use for \"How many active applicat","description":"List the hiring phases of job postings with type, position and counts of applications. Use for \"How many active applications are in each phase of Factorial job posting 12\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"ats_job_posting_id":{"anyOf":[{"maxLength":40,"type":"string"},{"type":"null"}],"default":null,"description":"Only phases of this job posting id.","title":"Ats Job Posting Id"},"limit":{"anyOf":[{"maximum":100,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"How many records to return (1 to 100).","title":"Limit"},"after_id":{"anyOf":[{"maxLength":80,"type":"string"},{"type":"null"}],"default":null,"description":"Cursor for the next page: the end_cursor value from the previous answer's meta.","title":"After Id"}},"title":"list_application_phasesArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_hiring_stages":{"post":{"operationId":"list_hiring_stages","summary":"List the company's hiring stages (new, screening, interview, assessment, offer, hired) in order. Use for \"What hiring st","description":"List the company's hiring stages (new, screening, interview, assessment, offer, hired) in order. Use for \"What hiring stages does Factorial use\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"limit":{"anyOf":[{"maximum":100,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"How many records to return (1 to 100).","title":"Limit"},"after_id":{"anyOf":[{"maxLength":80,"type":"string"},{"type":"null"}],"default":null,"description":"Cursor for the next page: the end_cursor value from the previous answer's meta.","title":"After Id"}},"title":"list_hiring_stagesArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_candidate_sources":{"post":{"operationId":"list_candidate_sources","summary":"List the candidate source categories (job board, referral, agency ...) used to tag applications. Use for \"Where do Facto","description":"List the candidate source categories (job board, referral, agency ...) used to tag applications. Use for \"Where do Factorial candidates come from\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"limit":{"anyOf":[{"maximum":100,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"How many records to return (1 to 100).","title":"Limit"},"after_id":{"anyOf":[{"maxLength":80,"type":"string"},{"type":"null"}],"default":null,"description":"Cursor for the next page: the end_cursor value from the previous answer's meta.","title":"After Id"}},"title":"list_candidate_sourcesArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_rejection_reasons":{"post":{"operationId":"list_rejection_reasons","summary":"List the reasons used when rejecting applications, with who decided. Use for \"What rejection reasons are configured in F","description":"List the reasons used when rejecting applications, with who decided. Use for \"What rejection reasons are configured in Factorial\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"limit":{"anyOf":[{"maximum":100,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"How many records to return (1 to 100).","title":"Limit"},"after_id":{"anyOf":[{"maxLength":80,"type":"string"},{"type":"null"}],"default":null,"description":"Cursor for the next page: the end_cursor value from the previous answer's meta.","title":"After Id"}},"title":"list_rejection_reasonsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_teams":{"post":{"operationId":"list_teams","summary":"List teams with name, description, hierarchy depth and parent team (employee ids are not returned). Use for \"What teams ","description":"List teams with name, description, hierarchy depth and parent team (employee ids are not returned). Use for \"What teams exist in Factorial\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{},"title":"list_teamsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_locations":{"post":{"operationId":"list_locations","summary":"List company locations with name, address, country, timezone and whether it is the main one. Use for \"Which office locat","description":"List company locations with name, address, country, timezone and whether it is the main one. Use for \"Which office locations does the Factorial account have\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"main":{"anyOf":[{"type":"boolean"},{"type":"null"}],"default":null,"description":"True to return only the main location.","title":"Main"},"limit":{"anyOf":[{"maximum":100,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"How many records to return (1 to 100).","title":"Limit"},"after_id":{"anyOf":[{"maxLength":80,"type":"string"},{"type":"null"}],"default":null,"description":"Cursor for the next page: the end_cursor value from the previous answer's meta.","title":"After Id"}},"title":"list_locationsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_company_holidays":{"post":{"operationId":"list_company_holidays","summary":"List company holidays with date, name and location, optionally within a date range. Use for \"What company holidays are i","description":"List company holidays with date, name and location, optionally within a date range. Use for \"What company holidays are in Factorial next month\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"start_at":{"anyOf":[{"maxLength":10,"type":"string"},{"type":"null"}],"default":null,"description":"Only holidays on or after this date (YYYY-MM-DD).","title":"Start At"},"end_at":{"anyOf":[{"maxLength":10,"type":"string"},{"type":"null"}],"default":null,"description":"Only holidays on or before this date (YYYY-MM-DD).","title":"End At"},"limit":{"anyOf":[{"maximum":100,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"How many records to return (1 to 100).","title":"Limit"},"after_id":{"anyOf":[{"maxLength":80,"type":"string"},{"type":"null"}],"default":null,"description":"Cursor for the next page: the end_cursor value from the previous answer's meta.","title":"After Id"}},"title":"list_company_holidaysArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_leave_types":{"post":{"operationId":"list_leave_types","summary":"List time-off leave types with name, paid flag, approval requirement and active state (no employee balances). Use for \"W","description":"List time-off leave types with name, paid flag, approval requirement and active state (no employee balances). Use for \"What kinds of leave can people request in Factorial\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"active":{"anyOf":[{"type":"boolean"},{"type":"null"}],"default":null,"description":"True for leave types in use, false for retired ones.","title":"Active"},"payable":{"anyOf":[{"type":"boolean"},{"type":"null"}],"default":null,"description":"True for paid leave types, false for unpaid.","title":"Payable"},"limit":{"anyOf":[{"maximum":100,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"How many records to return (1 to 100).","title":"Limit"},"after_id":{"anyOf":[{"maxLength":80,"type":"string"},{"type":"null"}],"default":null,"description":"Cursor for the next page: the end_cursor value from the previous answer's meta.","title":"After Id"}},"title":"list_leave_typesArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_job_roles":{"post":{"operationId":"list_job_roles","summary":"List job roles from the job catalog with name, description and archived flag. Use for \"Which job roles are defined in th","description":"List job roles from the job catalog with name, description and archived flag. Use for \"Which job roles are defined in the Factorial job catalog\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"limit":{"anyOf":[{"maximum":100,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"How many records to return (1 to 100).","title":"Limit"},"after_id":{"anyOf":[{"maxLength":80,"type":"string"},{"type":"null"}],"default":null,"description":"Cursor for the next page: the end_cursor value from the previous answer's meta.","title":"After Id"}},"title":"list_job_rolesArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}},"/v1/tools/list_job_levels":{"post":{"operationId":"list_job_levels","summary":"List job levels from the job catalog with name, role and order. Use for \"What job levels exist for each role in Factoria","description":"List job levels from the job catalog with name, role and order. Use for \"What job levels exist for each role in Factorial\".","tags":["tools"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"properties":{"limit":{"anyOf":[{"maximum":100,"minimum":1,"type":"integer"},{"type":"null"}],"default":50,"description":"How many records to return (1 to 100).","title":"Limit"},"after_id":{"anyOf":[{"maxLength":80,"type":"string"},{"type":"null"}],"default":null,"description":"Cursor for the next page: the end_cursor value from the previous answer's meta.","title":"After Id"}},"title":"list_job_levelsArguments","type":"object"}}}},"responses":{"200":{"description":"Tool result. `ok: true` on success; `ok: false` with a structured `error` (provider_unavailable, upstream_error, bad_input) when the tool could not answer.","content":{"application/json":{"schema":{"type":"object","additionalProperties":true}}}},"422":{"description":"Arguments failed validation","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"429":{"description":"Rate limit exceeded (see Retry-After)","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"x-read-only":true}}}}