Step-by-step migration instructions

This guide includes updated read endpoints, pagination changes, recommendations for custom integrations, and a clear mapping of v1/v2 resources to their v3 equivalents. It’s designed to help you transition endpoints smoothly and efficiently.

Each table in this article is organized alphabetically and maps specific resources to their v1/v2 routes, the corresponding v3 equivalent, and any additional comments or considerations for those endpoints.

Pagination

In previous versions, pagination was implemented by passing page and per_page parameters. The backend would then use limit and offset to fetch the appropriate records. Additionally, links for next, prev, and last pages were included in the response headers. However, calculating the last page required a count of all matching records, which negatively impacted performance, especially with large datasets.

To address these performance issues, V3 introduces a cursor-based pagination system, eliminating the need for offset. This approach enhances efficiency and scalability.

Key changes in v3 pagination

No page Parameter: The page parameter is no longer supported. You may specify a per_page parameter in the first request only to define the number of records per page.
Cursor-Based Links: To navigate between pages, the response headers include cursor-based links:

  • next: URL for the next page (if available).
  • prev: URL for the previous page (if available).
  • Note: A last link is no longer provided.

Recommendations for custom integrations

We encourage users of custom integrations to adopt the Client Credentials Flow to familiarize themselves with the new authentication process in Harvest V3.

Note: The Client Credentials Flow is not available for Greenhouse partners. Partners must use the Authorization Code Grant Type.

Activity Feed
V1/V2 routeGET https://harvest.greenhouse.io/v1/candidates/{id}/activity_feed
V3 routeGET https://harvest.greenhouse.io/v3/notes
CommentsChange in presentation of the objects where type is used as opposed to separating into various objects, for a more consistent object schema experience across all note types
Applications
V1/V2 routeGET https://harvest.greenhouse.io/v1/applications
V3 routeGET https://harvest.greenhouse.io/v3/applications

GET https://harvest.greenhouse.io/v3/application_stages

GET https://harvest.greenhouse.io/v3/prospect_details

GET https://harvest.greenhouse.io/v3/prospect_pool_stages

GET https://harvest.greenhouse.io/v3/prospect_pools

GET https://harvest.greenhouse.io/v3/attachments

GET https://harvest.greenhouse.io/v3/sources

GET https://harvest.greenhouse.io/v3/users

GET https://harvest.greenhouse.io/v3/rejection_details

GET https://harvest.greenhouse.io/v3/rejection_reasons

GET https://harvest.greenhouse.io/v3/jobs
Commentscredited_toreferrer_id

applied_atcreated_at

current_stagestage_id

sourcesource_id

locationlocation_address

rejection_reasonrejection_reason_id

rejection_detailsquestion_custom_fields

jobsjob_id

prospective_officeprospect_details.office_id

prospective_departmentprospect_details.department_id

prospect_poolprospect_details.pool_id

prospect_stageprospect_details.pool_stage_id

prospect_ownerprospect_details.prospect_owner_id
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/applications/{id}
V3 routeGET https://harvest.greenhouse.io/v3/applications

GET https://harvest.greenhouse.io/v3/application_stages

GET https://harvest.greenhouse.io/v3/prospect_details

GET https://harvest.greenhouse.io/v3/prospect_pool_stages

GET https://harvest.greenhouse.io/v3/prospect_pools

GET https://harvest.greenhouse.io/v3/attachments

GET https://harvest.greenhouse.io/v3/sources

GET https://harvest.greenhouse.io/v3/users

GET https://harvest.greenhouse.io/v3/rejection_details

GET https://harvest.greenhouse.io/v3/rejection_reasons

GET https://harvest.greenhouse.io/v3/jobs
Commentscredited_toreferrer_id

applied_atcreated_at

current_stagestage_id

sourcesource_id

locationlocation_address

rejection_reasonrejection_reason_id

rejection_detailsquestion_custom_fields

jobsjob_id

prospective_officeprospect_details.office_id

prospective_departmentprospect_details.department_id

prospect_poolprospect_details.pool_id

prospect_stageprospect_details.pool_stage_id

prospect_ownerprospect_details.prospect_owner_id
Approval Flows
V1/V2 routeGET https://harvest.greenhouse.io/v1/jobs/{id}/approval_flows
V3 routeGET https://harvest.greenhouse.io/v3/approval_flows

GET https://harvest.greenhouse.io/v3/approver_groups

GET https://harvest.greenhouse.io/v3/approvers

GET https://harvest.greenhouse.io/v3/users
Commentsrequested_by_user_idrequest_by_id

prioritysort_order

Deprecated approver_groups.job_id, you will have to retrieve this in the parent, approval flows object

Deprecated approver_groups.offer_id, you will have to retrieve this in the parent, approval flows object

nameuser_id, all approver user related information will need to be retrieved from the users endpoint
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/approval_flows/{id}
V3 routeGET https://harvest.greenhouse.io/v3/approval_flows

GET https://harvest.greenhouse.io/v3/approver_groups

GET https://harvest.greenhouse.io/v3/approvers

GET https://harvest.greenhouse.io/v3/users
Commentsrequested_by_user_idrequest_by_id

prioritysort_order

Deprecated approver_groups.job_id, you will have to retrieve this in the parent, approval flows object

Deprecated approver_groups.offer_id, you will have to retrieve this in the parent, approval flows object

nameuser_id, all approver user related information will need to be retrieved from the users endpoint
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/users/{user_id}/pending_approvals
V3 routeGET https://harvest.greenhouse.io/v3/approval_flows

GET https://harvest.greenhouse.io/v3/approver_groups

GET https://harvest.greenhouse.io/v3/approvers

GET https://harvest.greenhouse.io/v3/users
CommentsPlease use the status attribute in the query filters in the approvers object to view all users with pending approvals.

requested_by_user_idrequest_by_id

prioritysort_order

Deprecated approver_groups.job_id, you will have to retrieve this in the parent, approval flows object

Deprecated approver_groups.offer_id, you will have to retrieve this in the parent, approval flows object

nameuser_id, all approver user related information will need to be retrieved from the users endpoint
Candidates
V1/V2 routeGET https://harvest.greenhouse.io/v1/candidates
V3 routeGET https://harvest.greenhouse.io/v3/candidates

GET https://harvest.greenhouse.io/v3/applications

GET https://harvest.greenhouse.io/v3/attachments

GET https://harvest.greenhouse.io/v3/candidate_educations

GET https://harvest.greenhouse.io/v3/candidate_employments

GET https://harvest.greenhouse.io/v3/referrers
CommentsDeprecated photo_url

Deprecated attachments, retrieve from the Attachments endpoint, by application

Deprecated application_ids and applications [], you can filter the Application endpoint by candidate_id

Recruiter and Coordinator objects have been moved to the Applications object

is_privateprivate

For brevity, the changes in v1 Application endpoints are not reflected in this entry. Please visit the Application endpoint detail if you were retrieving application-level data from the v1 Candidate endpoint

Candidate educations are retrieved via the custom field options endpoint
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/candidates/{id}
V3 routeGET https://harvest.greenhouse.io/v3/candidates

GET https://harvest.greenhouse.io/v3/applications

GET https://harvest.greenhouse.io/v3/attachments

GET https://harvest.greenhouse.io/v3/candidate_educations

GET https://harvest.greenhouse.io/v3/candidate_employments

GET https://harvest.greenhouse.io/v3/referrers
CommentsDeprecated photo_url

Deprecated attachments, retrieve from the Attachments endpoint, by application

Deprecated application_ids and applications [], you can filter the Application endpoint by candidate_id

Recruiter and Coordinator objects have been moved to the Applications object

is_privateprivate

For brevity, the changes in v1 Application endpoints are not reflected in this entry. Please visit the Application endpoint detail if you were retrieving application-level data from the v1 Candidate endpoint

Candidate educations are retrieved via the custom field options endpoint
Candidate Tags
V1/V2 routeGET https://harvest.greenhouse.io/v1/candidates/{id}/tags
V3 routeGET https://harvest.greenhouse.io/v3/candidates
CommentsAvailable in the tags array
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/tags/candidate
V3 routeGET https://harvest.greenhouse.io/v3/candidate_tags
CommentsNo notable changes
Close Reasons
V1/V2 routeGET https://harvest.greenhouse.io/v1/close_reasons
V3 routehttps://harvest.greenhouse.io/v3/close_reasons
CommentsNo notable changes
Departments
V1/V2 route GET https://harvest.greenhouse.io/v1/departments
V3 routeGET https://harvest.greenhouse.io/v3/departments
CommentsDeprecated child_ids, child_department_external_ids, parent_departmental_external_id

Removed render_as=tree
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/departments/{id}
V3 routeGET https://harvest.greenhouse.io/v3/departments
CommentsDeprecated child_ids, child_department_external_ids, parent_departmental_external_id

Removed render_as=tree
Educations (Degrees)
V1/V2 routeGET https://harvest.greenhouse.io/v1/degrees
V3 routeGET https://harvest.greenhouse.io/v3/custom_field_options?field_key=degree
CommentsDeprecated old endpoint to reflect candidate degrees as a custom field with multiple options
Educations (Disciplines)
V1/V2 routeGET https://harvest.greenhouse.io/v1/disciplines
V3 routeGET https://harvest.greenhouse.io/v3/custom_field_options?field_key=discipline
CommentsDeprecated old endpoint to reflect candidate disciplines as a custom field with multiple options
Educations (Schools)
V1/V2 routeGET https://harvest.greenhouse.io/v1/schools
V3 routeGET https://harvest.greenhouse.io/v3/custom_field_options?field_key=school_name
CommentsDeprecated old endpoint to reflect candidate schools as a custom field with multiple options
EEOC
V1/V2 routeGET https://harvest.greenhouse.io/v1/eeoc
V3 routeGET https://harvest.greenhouse.io/v3/eeoc
CommentsNo notable changes
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/applications/{id}/eeoc
V3 routeGET https://harvest.greenhouse.io/v3/eeoc
CommentsNo notable changes
Hiring Team
V1/V2 routeGET https://harvest.greenhouse.io/v1/jobs/{id}/hiring_team
V3 routeGET https://harvest.greenhouse.io/v3/job_hiring_managers

GET https://harvest.greenhouse.io/v3/job_owners
CommentsThe v3 Job Owners endpoint contains recruiters, coordinators, and sourcers.
Job Post Custom Locations
V1/V2 routeGET https://harvest.greenhouse.io/v1/job_posts/{id}/custom_locations
V3 routehttps://harvest.greenhouse.io/v3/job_board_custom_locations
CommentsJob post custom location id is now in the job board custom locations
Job Posts
V1/V2 routeGET https://harvest.greenhouse.io/v1/job_posts
V3 routehttps://harvest.greenhouse.io/v3/job_posts

https://harvest.greenhouse.io/v3/job_board_custom_locations

https://harvest.greenhouse.io/v3/job_post_locations
CommentsJob post custom location id is now in the job board custom locations

Job posts can now have multiple locations
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/job_posts/{id}
V3 routehttps://harvest.greenhouse.io/v3/job_posts

https://harvest.greenhouse.io/v3/job_board_custom_locations

https://harvest.greenhouse.io/v3/job_post_locations
CommentsJob post custom location id is now in the job board custom locations

Job posts can now have multiple locations
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/jobs/{id}/job_posts
V3 routehttps://harvest.greenhouse.io/v3/job_posts

https://harvest.greenhouse.io/v3/job_board_custom_locations

https://harvest.greenhouse.io/v3/job_post_locations
CommentsJob post custom location id is now in the job board custom locations

Job posts can now have multiple locations
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/jobs/{id}/job_post
V3 routehttps://harvest.greenhouse.io/v3/job_posts

https://harvest.greenhouse.io/v3/job_board_custom_locations

https://harvest.greenhouse.io/v3/job_post_locations
CommentsJob post custom location id is now in the job board custom locations

Job posts can now have multiple locations
Job Stages
V1/V2 routeGET https://harvest.greenhouse.io/v1/job_stages
V3 routeGET https://harvest.greenhouse.io/v3/job_interview_stages

GET https://harvest.greenhouse.io/v3/job_interviews

GET https://harvest.greenhouse.io/v3/interview_kits

GET https://harvest.greenhouse.io/v3/scorecard_questions

GET https://harvest.greenhouse.io/v3/default_interviewers
Commentsprioritysort_order

schedulable = truejob_interviews.scheduling_type = "NEEDS_SCHEDULING"

interview_kit.contentinterviewer_kit.exercises

interview_kit.questions []scorecard_questions, with interview_kit_id as parent
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/jobs/{id}/stages
V3 routeGET https://harvest.greenhouse.io/v3/job_interview_stages

GET https://harvest.greenhouse.io/v3/job_interviews

GET https://harvest.greenhouse.io/v3/interview_kits

GET https://harvest.greenhouse.io/v3/scorecard_questions

GET https://harvest.greenhouse.io/v3/default_interviewers
Commentsprioritysort_order

schedulable = truejob_interviews.scheduling_type = "NEEDS_SCHEDULING"

interview_kit.contentinterviewer_kit.exercises

interview_kit.questions []scorecard_questions, with interview_kit_id as parent
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/job_stages/{id}
V3 routeGET https://harvest.greenhouse.io/v3/job_interview_stages

GET https://harvest.greenhouse.io/v3/job_interviews

GET https://harvest.greenhouse.io/v3/interview_kits

GET https://harvest.greenhouse.io/v3/scorecard_questions

GET https://harvest.greenhouse.io/v3/default_interviewers
Commentsprioritysort_order

schedulable = truejob_interviews.scheduling_type = "NEEDS_SCHEDULING"

interview_kit.contentinterviewer_kit.exercises

interview_kit.questions []scorecard_questions, with interview_kit_id as parent
Offers
V1/V2 routeGET https://harvest.greenhouse.io/v1/offers
V3 routehttps://harvest.greenhouse.io/v3/offers

https://harvest.greenhouse.io/v3/openings
Commentssent_atsent_on

starts_atstarts_on
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/applications/{application_id}/offers
V3 routehttps://harvest.greenhouse.io/v3/offers

https://harvest.greenhouse.io/v3/openings
Commentssent_atsent_on

starts_atstarts_on
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/applications/{application_id}/offers/current_offer
V3 routehttps://harvest.greenhouse.io/v3/offers

https://harvest.greenhouse.io/v3/openings
CommentsPlease use the current_only boolean in our query filters.

sent_atsent_on

starts_atstarts_on
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/offers/{id}
V3 routehttps://harvest.greenhouse.io/v3/offers

https://harvest.greenhouse.io/v3/openings
Commentssent_atsent_on

starts_atstarts_on
Offices
V1/V2 routeGET https://harvest.greenhouse.io/v1/offices
V3 routehttps://harvest.greenhouse.io/v3/offices
CommentsWe no longer permit rendering as a tree

Deprecated child_ids

primary_contact_user_idprimary_in_house_contact_id

location is now flat, as opposed to the pattern in v1 offices endpoint
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/offices/{id}
V3 routehttps://harvest.greenhouse.io/v3/offices
CommentsWe no longer permit rendering as a tree

Deprecated child_ids

primary_contact_user_idprimary_in_house_contact_id

location is now flat, as opposed to the pattern in v1 offices endpoint
Openings
V1/V2 routeGET https://harvest.greenhouse.io/v1/jobs/{job_id}/openings
V3 routeGET https://harvest.greenhouse.io/v3/openings

GET https://harvest.greenhouse.io/v3/close_reasons
Commentsstatusopen (enum → boolean)

prioritysort_order
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/jobs/{job_id}/openings/{id}
V3 routeGET https://harvest.greenhouse.io/v3/openings

GET https://harvest.greenhouse.io/v3/close_reasons
Commentsstatusopen (enum → boolean)

prioritysort_order
Scheduled Interviews
V1/V2 routeGET https://harvest.greenhouse.io/v1/scheduled_interviews
V3 routeGET https://harvest.greenhouse.io/v3/interviews

GET https://harvest.greenhouse.io/v3/users

GET https://harvest.greenhouse.io/v3/interviewers
Commentsorganizerorganizer_id

start.date_timestarts_at or all_day_start_on

end.date_timeends_at or all_day_end_on

We have also introduced all_day_start_on and all_day_end_on for interviews that are scheduled without specified times of the day.
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/applications/{id}/scheduled_interviews
V3 routeGET https://harvest.greenhouse.io/v3/interviews

GET https://harvest.greenhouse.io/v3/users

GET https://harvest.greenhouse.io/v3/interviewers
Commentsorganizerorganizer_id

start.date_timestarts_at or all_day_start_on

end.date_timeends_at or all_day_end_on

We have also introduced all_day_start_on and all_day_end_on for interviews that are scheduled without specified times of the day.
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/scheduled_interviews/{id}
V3 routeGET https://harvest.greenhouse.io/v3/interviews

GET https://harvest.greenhouse.io/v3/users

GET https://harvest.greenhouse.io/v3/interviewers
Commentsorganizerorganizer_id

start.date_timestarts_at or all_day_start_on

end.date_timeends_at or all_day_end_on

We have also introduced all_day_start_on and all_day_end_on for interviews that are scheduled without specified times of the day.
Scorecards
V1/V2 routeGET https://harvest.greenhouse.io/v1/scorecards
V3 routehttps://harvest.greenhouse.io/v3/scorecards

https://harvest.greenhouse.io/v3/job_stages

https://harvest.greenhouse.io/v3/job_interview_steps

https://harvest.greenhouse.io/v3/interviewers

https://harvest.greenhouse.io/v3/scorecard_candidate_attributes

https://harvest.greenhouse.io/v3/scorecard_questions

https://harvest.greenhouse.io/v3/scorecard_question_answers

https://harvest.greenhouse.io/v3/scorecard_question_options

https://harvest.greenhouse.io/v3/scorecard_question_answer_options
Commentscandidate_id removed, will need to retrieve via application

submitted_bysubmtter_id

overall_recommendationcandidate_rating
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/applications/{id}/scorecards
V3 routehttps://harvest.greenhouse.io/v3/scorecards

https://harvest.greenhouse.io/v3/job_stages

https://harvest.greenhouse.io/v3/job_interview_steps

https://harvest.greenhouse.io/v3/interviewers

https://harvest.greenhouse.io/v3/scorecard_candidate_attributes

https://harvest.greenhouse.io/v3/scorecard_questions

https://harvest.greenhouse.io/v3/scorecard_question_answers

https://harvest.greenhouse.io/v3/scorecard_question_options

https://harvest.greenhouse.io/v3/scorecard_question_answer_options
Commentscandidate_id removed, will need to retrieve via application

submitted_bysubmtter_id

overall_recommendationcandidate_rating
******
V1/V2 routeGET https://harvest.greenhouse.io/v1/scorecards/{id}
V3 routehttps://harvest.greenhouse.io/v3/scorecards

https://harvest.greenhouse.io/v3/job_stages

https://harvest.greenhouse.io/v3/job_interview_steps

https://harvest.greenhouse.io/v3/interviewers

https://harvest.greenhouse.io/v3/scorecard_candidate_attributes

https://harvest.greenhouse.io/v3/scorecard_questions

https://harvest.greenhouse.io/v3/scorecard_question_answers

https://harvest.greenhouse.io/v3/scorecard_question_options

https://harvest.greenhouse.io/v3/scorecard_question_answer_options
Commentscandidate_id removed, will need to retrieve via application

submitted_bysubmtter_id

overall_recommendationcandidate_rating
Sources
V1/V2 routeGET https://harvest.greenhouse.io/v1/sources
V3 routeGET https://harvest.greenhouse.io/v3/sources
CommentsNo notable changes
Tracking Links
V1/V2 routeGET https://harvest.greenhouse.io/v1/tracking_links/{token}
V3 routeGET https://harvest.greenhouse.io/v3/tracking_links

GET https://harvest.greenhouse.io/v3/sources

GET https://harvest.greenhouse.io/v3/users

GET https://harvest.greenhouse.io/v3/referrers

GET https://boards-api.greenhouse.io/v1/boards/{board_token}
Commentsjob_boardjob_board_id

sourcesource_id

credited_toreferrer_id

Job board data is publicly available, there is no authentication required for job board endpoints.
User Roles
V1/V2 routeGET https://harvest.greenhouse.io/v1/user_roles
V3 routeGET https://harvest.greenhouse.io/v3/user_roles
Commentstyperole_type
[Resource]
V1/V2 route
V3 route
Comments