NAV Navbar
shell

Introduction

The Candidate Ingestion API enables sourcing partners with whom Greenhouse shares mutual customers to submit prospects and candidates.

The API allows partners to:

  1. Send candidates from the partner application to Greenhouse.
  2. Retrieve the current stage and status of candidates.
  3. Retrieve jobs on which the Greenhouse user is allowed to operate.

Note: The organization must be able to create prospects in order to create prospects using the Candidate Ingestion API.

Authentication

This API offers two methods of authentication: OAuth 2.0 and Basic Auth.

Authentication via OAuth 2.0

If the mutual customer’s users have accounts in both Greenhouse and the partner’s system, the preferred authentication method is OAuth 2.0. In this case, the partner would place an integration option on their website which would allow the user to authenticate in to Greenhouse via the partner’s application. This is similar to allowing people to register for a website using Facebook credentials. For a partner to configure this, they must supply Greenhouse with the following information:

  1. Application Name: The name of the application as it would appear in Greenhouse.
  2. Application URL: The URL to the primary application.
  3. Callback URL: This is the URL to which Greenhouse will send authenticated users.
  4. Logo Image: This is a 128x128 image that will be included in the permissions modal.

When Greenhouse receives this information, we will supply the partner with a consumer key, a consumer secret, a token URL, and an authorize URL. For example:

AttributeExample Value
Consumer KeybMipe4KWf987654321GrLG1Nfk1234567UshvloD
Consumer SecretLQdulabcdefghijklEZok2fE5xGzeBcDa123gNXtN
Token URLhttps://api.greenhouse.io/oauth/token
Authorize URLhttps://api.greenhouse.io/oauth/authorize

The partner should use this information to initiate an OAuth 2.0 flow in their application. Note the customer user can rescind this at any time.

When the user attempts to connect with Greenhouse, they will see a prompt asking them to confirm the connection. This prompt will then associate the user’s account in the partner system with their Greenhouse account.

Prompt Image

Once the OAuth process is complete and the user grants the partner permission to access their data on Greenhouse, the partner will receive an access token. This access token must be included in the Authorization header:

Authorization: Bearer <access_token>

Authentication via Basic Auth

If your users only have an account in Greenhouse and you will be submitting candidates as a partner (and not sourced by a user), you will likely want to authenticate via HTTP Basic Authentication. Users do not have to take any action to authorize your application to modify Greenhouse data. When using basic auth, you are required to set the On-Behalf-Of header for every request. The value should be the e-mail address of the user on behalf of whom you are taking action. For example:

On-Behalf-Of: john.smith@example.com

Normally, this will be a service user created specifically for this purpose. If this header is missing, or Greenhouse doesn’t recognize the address, the API will issue a 401 Unauthorized response. The application must also supply the API key. Via basic auth, you will include the API key as the basic auth username and nothing as the password. Since only a username needs to be provided in our case, you’ll need to append a : (colon) to the API token and then Base64 encode the resulting string. This may be included via URL:

https://<base64_encoded_api_key>:@api.greenhouse.io/v1/partners/candidates

or as an authorized header:

Authorization: Basic base64_encoded_api_key:

In all cases, the customer will have supplied the partner with a Partner API Key and a service user. Both items are required to submit candidates.

Note: Capabilities with the Ingestion API will be limited to the permissions of the On-Behalf-Of user

There are four user types, Site Admin, Job Admin, Interviewer, and Basic.

Site Admins have access to all jobs by default, whereas Job Admins/Interviewers are assigned to specific jobs. Job Admins/Interviewers will only be able to retrieve jobs via the API that they are assigned access to, or that are live on the company’s job board. However they can add Candidates to jobs they have access to, as well as jobless Prospects to Greenhouse.

Because all user permissions are job-based, in order to retrieve jobless Prospects from the API, Site Admins, Job Admins, and Interviewers need the additional Greenhouse permission to manage jobless Prospects. Otherwise, they can only add Prospects, and not retrieve them. This is true of the UI as well.

Basic users have the most restrictions, since their abilities in the UI are also very limited:

Basic users can: * Retreive jobs Retreive information about the current user * Create prospects on no jobs Create candidates on jobs

They can’t: * Retreive prospects Retreive candidates * Create a tracking link

OAuth Scopes

If you use OAuth for authentication, there are 3 permission scopes to be aware of. Some endpoints will require a specific permission scope while others require none.

General considerations

Unless otherwise specified, API methods generally conform to the following:

Ingestion API Change Log

The timestamps below are Eastern Time.

DateDescription
Apr 15, 2021 03:00:00PMAdded full_name and id to the [GET current_user] response
Aug 22, 2019 11:00:00AMAdded Change Log and General Consideration sections to the Ingestion API documentation

Candidates

Retrieve Candidates

curl 'https://api.greenhouse.io/v1/partner/candidates'
-H "Authorization: Basic MGQwMzFkODIyN2VhZmE2MWRjMzc1YTZjMmUwNjdlMjQ6"
{
    "candidate_ids": 17681532
}

API Response

{
    "id": 17681532,
    "name": "Harry Potter",
    "external_id": "24680",
    "applications": [
        {
            "id": 59724,
            "job": "Auror",
            "status": "Active",
            "stage": "Application Review",
            "profile_url": "https://app.greenhouse.io/people/17681532?application_id=26234709"
        }
    ]
}

Retrieve a candidate’s data. Note that this call will only return candidates that the current user has permission to view.

GET https://api.greenhouse.io/v1/partner/candidates

scope: candidates.view

Request Parameters

The request should contain a single query parameter that specifies a comma-delimited list of candidate IDs or a single candidate ID. If you provide any candidate ids that don’t exist or to which you do not have access, this endpoint will ignore them and only return the candidates that exist to this API key or Bearer token, or will return an empty response if you have only supplied one candidate ID.

An empty array will be returned for “Retrieve Candidates” requests with a single candidate ID for the following use-cases:

  1. Permissions changes made on a Greenhouse user account associated to the email address used to authenticate the request (e.g. User has been disabled or deprovisioned).
  2. The candidate is on a job that the user account/email address doesn’t have access to. Note that the user account must be at least a job admin on the job associated to the candidate ID. If added as a prospect, the user must have the permission to manage unattached prospects.
  3. The candidate profile was manually deleted by the organization.
  4. The source on the candidate profile was manually changed to a new source different from the original partner source.
  5. The candidate has been merged with another profile generating a new candidate ID.

If you would like more information about why you are not able to access a specific candidate ID, please contact the customer for more details, as Greenhouse Support will not share candidate details without the permission of the organization that owns the candidate record.

Query Parameter NameRequiredDescription
candidate_idsYesComma-delimited list of Candidate IDs (e.g. 123, 456)

Response Parameters

The response will always be an array of objects, even if only one candidate_id is provided.

Property NameTypeDescription
idIntegerThe ID of the candidate
external_idStringThe external ID that was provided in your initial candidate creation request. Can be null if you request the status of a candidate not associated with an external entity.
applications[]ArrayAn array containing 0 or more applications representing the jobs to which this candidate has applied. Each of the sub-elements are required for each of the applications.
applications.idIntegerThe ID of the application.
applications.jobStringName of the job this application is for (e.g. “Software developer).
applications.statusStringThe candidate’s current status. Must be one of "rejected,” “active,” or “hired.”
applications.stageStringThe applicant’s current stage in the interview pipeline (e.g. “Recruiter Phone Screen”).
applications.profile_urlStringA URL to the candidate’s profile in Greenhouse. You must be signed in to Greenhouse to view the profile.

Post Candidates

curl -X POST 'https://api.greenhouse.io/v1/partner/candidates'
-H "Authorization: Basic MGQwMzFkODIyN2VhZmE2MWRjMzc1YTZjMmUwNjdlMjQ6"
-H "Content-Type: application/json"
{
    "prospect": "true",
    "first_name": "Harry",
    "last_name": "Potter",
    "company": "Hogwarts",
    "title": "Student",
    "resume": "https://hogwarts.com/resume",
    "phone_numbers": [
        {
            "phone_number": "123-456-7890",
            "type": "home"
        }
    ],
    "emails": [
        {
            "email": "hpotter@hogwarts.edu",
            "type": "other"
        }
    ],
    "social_media": [
        {
            "url": "https://twitter.com/hp"
        }
    ],
    "websites": [
        {
            "url": "https://harrypotter.com",
            "type": "blog"
        }
    ],
    "addresses": [
        {
            "address": "4 Privet Dr",
            "type": "home"
        }
    ],
    "job_id": 12345,
    "external_id": "24680",
    "notes": "Good at Quiddich",
    "prospect_pool_id": 123,
    "prospect_pool_stage_id": 456,
    "prospect_owner_email": "prospect_owners_email@example.com"
}

API Response

{
"id": 12345,
"application_id": 17681532,
"external_id": "24680",
"profile_url": "https://app.greenhouse.io/people/17681532?application_id=26234709"
}

Create one or more candidates or prospects

POST https://api.greenhouse.io/v1/partner/candidates

scope: candidates.create

Request Parameters

Property NameTypeRequiredDescription
prospectBooleanNoTrue if this candidate should be a prospect. The organization must be able to create prospects to set this field. (Default: true)
job_idIntegerMixedRequired only if prospect is false. The ID of the job to which this candidate or prospect should be added.
first_nameStringYes
last_nameStringYes
external_idStringYesThe unique id of this candidate in your application’s system.
companyStringNoCandidate’s current company
titleStringNoCandidate’s current title
resumeStringNoURL to the candidate’s resume. Greenhouse will attempt to ingest the document at this URL and add it to the candidate record.
phone_numbers[]ArrayNo
phone_numbers.phone_numberStringMixedOnly required if phone_number is included.
phone_numbers.typeStringMixedMust be “mobile”, “home”, “work”, or “other.” Only required if phone_number is included.
emails[]ArrayNo
emails.emailStringMixedNote: Only required if email is included.
emails.typeStringMixedMust be “personal”, “work”, or “other”. Only required if email is included.
addresses[]ArrayNo
addresses.addressStringMixedA free form block of text, which may include newlines (“\n”). Only required if addresses are included.
addresses.typeStringMixedMust be “home”, “work”, or “other”. Only required if addresses are included.
social_media[]ArrayNo
social_media.urlStringMixedNote: Only required if social media urls are included.
websites[]ArrayNo
websites.urlStringMixedNote: Only required if websites are included.
websites.typeStringMixedMust be either “personal”, “company”, “portfolio”, “blog”, or “other”. Only required if websites are included.
referrerObjectNoIf present, this value will be used to populate the “Who Gets Credit” field for the candidate’s application. If omitted, the “Who Gets Credit” field will be populated with the current user’s information.
referrer.emailStringMixedUsed to match this referrer with an existing Greenhouse user, if possible. Only required if referrer is included.
referrer.first_nameStringMixedUsed to create a new ‘Referrer’ in Greenhouse if referrer.email does not match an existing user. Only required if referrer is included.
referrer.last_nameStringMixedUsed to create a new ‘Referrer’ in Greenhouse if referrer.email does not match an existing user. Only required if referrer is included.
notesStringNoFree-form plain-text notes about this candidate. One way for this to be used is to send secondary information that our API can’t capture as structured data. For example: “Skills: Java, C++, Python”
prospect_pool_idIntegerMixedUsed to put a prospect in the Prospect Pool with this id. Only required if prospect_pool_stage_id is included. “prospect” property must be set to true.
prospect_pool_stage_idIntegerNoUsed to put a prospect in the Prospect Pool Stage with this id. The stage must belong to the prospect pool provided in prospect_pool_id. “prospect” property must be set to true.
prospect_owner_emailStringNoUsed to set the prospect owner for a prospect by providing a valid user’s email that exists in Greenhouse. “prospect” property must be set to true.

Response Parameters

The API will respond with a single object if a single object was provided or an array of objects if an array was provided.

Property NameTypeDescription
idIntegerThe ID of the newly created candidate in Greenhouse.
application_idIntegerThe ID of the application implicitly created in Greenhouse.
external_idStringThe external ID that was provided in your request.
profile_urlStringA URL to the candidate’s profile within Greenhouse. The user must be signed into Greenhouse to view the profile.

Current User

Retrieve Current User

curl 'https://api.greenhouse.io/v1/partner/current_user'
-H "Authorization: Basic MGQwMzFkODIyN2VhZmE2MWRjMzc1YTZjMmUwNjdlMjQ6"

API Response

{
  "full_name": "Ron Weasley",
  "first_name": "Ron",
  "last_name": "Weasley",
  "email": "rweasley@hogwarts.edu",
  "id": 1234
}

Retrieve details about the current user

GET https://api.greenhouse.io/v1/partner/current_user

Request Parameters

This request is simply the URL. It takes no parameters.

Response Parameters

Property NameTypeDescription
full_nameStringThe current user’s full name
first_nameStringThe current user’s first name
last_nameStringThe current user’s last name
emailStringThe email address associated with the current user
idIntegerThe ID of the current user

Jobs

Retrieve Jobs

curl 'https://api.greenhouse.io/v1/partner/jobs'
-H "Authorization: Basic MGQwMzFkODIyN2VhZmE2MWRjMzc1YTZjMmUwNjdlMjQ6"

API Response

[
  {
    "id": 146859,
    "name": "Auror",
    "status": "open",
    "public": true
  },
  {
    "id": 150050,
    "name": "Professor",
    "status": "open",
    "public": true
  },
  {
    "id": 147886,
    "name": "Caretaker",
    "status": "open",
    "public": false
  },
]

Retrieve jobs that are visible for the current user, including all jobs listed on their organization’s public careers page and unpublished jobs the user can access.

GET https://api.greenhouse.io/v1/partner/jobs

scope: jobs.view

Request Parameters

This request is simply the URL. It takes no parameters.

Response Parameters

Property NameTypeDescription
idIntegerThe ID of the job.
nameStringThe name as it appears in Greenhouse, NOT necessarily how it appears on the public job board.
statusStringAlways ‘open’.
publicBooleanTrue if this job has any job posts that are currently live on any job board.

Tracking Link

Post Tracking Link

curl -X POST 'https://api.greenhouse.io/v1/partner/tracking_link'
-H "Authorization: Basic MGQwMzFkODIyN2VhZmE2MWRjMzc1YTZjMmUwNjdlMjQ6"
-H "Content-Type: application/json"
{
    "job_id": 12345
}

API Response

{ 
    "tracking_link": "http://grnh.se/yvj0bj",
    "job": "Auror", 
    "source": "Campus Recruiting",
    "referrer": "Hermione Granger"
}

Create a new tracking link for a specific job. Candidates that apply using this tracking link will automatically have their source set to your application and their referrer set to the current user.

POST https://api.greenhouse.io/v1/partner/tracking_link

Request Parameters

Property NameTypeRequired
job_idIntegerYes

Response Parameters

Property NameTypeDescription
tracking_linkStringURL for newly created tracking link.
jobStringThe name of the job tied to this tracking link.
sourceStringThe name of the source tied to this tracking link (e.g. the name of your application).
referrerStringThe name of the user tied to this tracking link.

Prospect Pools

Retrieve Prospect Pools

curl 'https://api.greenhouse.io/v1/partner/prospect_pools'
-H "Authorization: Basic MGQwMzFkODIyN2VhZmE2MWRjMzc1YTZjMmUwNjdlMjQ6"

API Response

[
  {
    "id": 123,
    "name": "Cold Outreach: Referred",
    "stages": [
      {
        "id": 1957,
        "name": "Not Contacted"
      },
      {
        "id": 1958,
        "name": "Contacted"
      },
      {
        "id": 1959,
        "name": "1st. Follow Up Sent"
      },
      {
        "id": 1960,
        "name": "2nd Follow Up Sent"
      },
      {
        "id": 1961,
        "name": "In Discussion"
      }
    ]
  },
  {
    "id": 456,
    "name": "Cold Outreach: Sourced",
    "stages": [
      {
        "id": 1962,
        "name": "Not Contacted"
      },
      {
        "id": 1963,
        "name": "Contacted"
      },
      {
        "id": 1964,
        "name": "1st. Follow Up Sent"
      },
      {
        "id": 1965,
        "name": "2nd Follow Up Sent"
      },
      {
        "id": 1966,
        "name": "In Discussion"
      }
    ]
  }
]

Retrieve prospect pools along with their stages for the current user’s organization.

GET https://api.greenhouse.io/v1/partner/prospect_pools

scope: prospectpools.view_

Request Parameters

This request is simply the URL. It takes no parameters.

Response Parameters

Property NameTypeDescription
idIntegerThe ID of the prospect pool.
nameStringThe name of the prospect pool.
stagesObjectThe stages that belong to a prospect pool with the id and name of the stage. The list of stages will be ordered the same way that it is configured to be ordered in Greenhouse.

Errors

{
    "errors": [
        {
            "message": "Your request included invalid JSON.",
            "field": "email"
        }
    ]
}

Successful API responses will have a 200-level HTTP status code. If there is a problem processing your request, you will receive a response with a 4xx- or 5xx-level status code as follows:

Status CodeDescription
400Your request included invalid JSON.
401You have not been authenticated.
403You have been authenticated, but your Greenhouse user does not have permission to the resource.
404The resource you requested could not be found.
5xxThere was an error on our end. You may retry at a later time or contact support if the problem persists.

Error Properties

Property NameTypeRequiredDescription
errors[]ArrayYes
errors.messageStringYesA message describing the error. This is for debugging purposes and is not intended to be displayed to the end-user. The exact text should not be relied on programmatically.
errors.fieldStringNoThe offending field in the request that caused the error, if applicable.