Sync courses and editions to your LMS
Goal: every course edition that participants can enroll in exists as a course in your LMS, named consistently, with the right dates, and is closed when the edition is canceled or completed.
Which object becomes an LMS course
Create one LMS course per planned course (course edition). Use the parent course (template) for the name, code and description; use the planned course for dates, status and participants. See the data model if the distinction is new to you.
Only planned courses whose template is in scope get an LMS course. How you mark a template as in scope is described in Which courses get an LMS course. Check the marker in your middleware on every planned_course.* and enrollment.* event and ignore records that are out of scope.
If your LMS groups courses in a hierarchy, place the course in the node you chose in Where courses live in the LMS hierarchy.
Recommended LMS course name: <course name> - <start date or edition label>, for example Project management basics - 2026-10-05. Store the planned course id in the LMS course's external identifier field.
Fields to map
From GET /api/v1/courses/{id}:
| Field | Use it for |
|---|---|
id | Look up the template; store it if you group LMS courses by template. |
name | LMS course name. |
code | LMS course short name or code prefix. |
From GET /api/v1/planned_courses/{id}:
| Field | Use it for |
|---|---|
id | External identifier of the LMS course. |
course_id | Link to the template above. |
type | FixedPlannedCourse has dates; FlexiblePlannedCourse is self-paced and gets access windows per enrollment. |
status | planned, active, completed or canceled. Create for planned and active; close or hide for completed; deactivate for canceled. |
start_date, end_date | LMS course start and end date. Empty for flexible planned courses. |
external_content_url | The LMS course URL you write back later, see Show the LMS course link. |
Trimmed example:
{
"id": 4211,
"course_id": 87,
"type": "FixedPlannedCourse",
"status": "planned",
"start_date": "2026-10-05",
"end_date": "2026-10-07",
"external_content_url": null,
"updated_at": "2026-09-12T09:41:03.120Z"
}
Webhook events to subscribe to
| Event | What to do |
|---|---|
planned_course.created | Fetch the planned course and its course, create the LMS course. |
planned_course.updated | Fetch and update name, dates and status. |
planned_course.canceled | Deactivate or hide the LMS course; unenroll or deactivate its participants. |
planned_course.deleted | Same as canceled. Keep the LMS course for history unless it was never used. |
course.updated | The template was renamed or recoded; update every LMS course created from its planned courses. |
course.deleted | Its planned courses are gone too; treat like canceled. |
Optional, if you also mirror meetings into an LMS calendar: meeting.created, meeting.updated, meeting.deleted, and GET /api/v1/planned_courses/{id}/meetings.