Reference
Invites
12 routes, generated from Morse’s own OpenAPI document. Every path below hangs off the base URL, and every one needs the bearer header.
The examples are built from each route’s schema, so the shapes and types are exactly what the API declares. The values are illustrative, and no one has run them.
A guest's answer so far, by the token in their invitation.
/m/{code}/replyGET/m/{code}/reply
curl "$MORSE/m/4KJ9P2/reply?i=%E2%80%A6" \
-H "Authorization: Bearer $MORSE_TOKEN"{
"duration_minutes": 30,
"host_name": "Priya Shah",
"note": "Annual plans are billed up front.",
"proposed_start": "2026-10-02T10:30:00+05:30",
"response": "…",
"scheduled_at": "2026-10-02T10:30:00+05:30",
"status": "…"
}A guest answers, as POST /meetings/{id}/reply does for a colleague.
/m/{code}/replyPOST/m/{code}/reply
curl -X POST "$MORSE/m/4KJ9P2/reply" \
-H "Authorization: Bearer $MORSE_TOKEN" \
-H "Content-Type: application/json" \
-d '{ "invite_token": "mp_YOUR_MORSE_TOKEN" }'{
"duration_minutes": 30,
"host_name": "Priya Shah",
"note": "Annual plans are billed up front.",
"proposed_start": "2026-10-02T10:30:00+05:30",
"response": "…",
"scheduled_at": "2026-10-02T10:30:00+05:30",
"status": "…"
}Times the host is free for instead, for a guest, by their token.
/m/{code}/reply/slotsGET/m/{code}/reply/slots
curl "$MORSE/m/4KJ9P2/reply/slots?i=%E2%80%A6" \
-H "Authorization: Bearer $MORSE_TOKEN"{
"slots": [
"2026-10-02T10:30:00+05:30"
],
"zone": "…"
}Who the host has asked — the same people the calendar event and the move and cancel emails go to — each with how far they have got.
/meetings/{meeting_id}/invitesSomeone who walked in through the link belongs in the room's people list, not here.
GET/meetings/{meeting_id}/invites
curl "$MORSE/meetings/3f9c1a24-5e6f-4b31-9a77-1b2c3d4e5f60/invites" \
-H "Authorization: Bearer $MORSE_TOKEN"[
{
"display_name": "Priya Shah",
"email": "priya@neuralarc.ai",
"key": true,
"kind": "…",
"note": "Annual plans are billed up front.",
"proposed_start": "2026-10-02T10:30:00+05:30",
"response": "…",
"status": "…"
}
]Email up to 25 people an invitation to a meeting.
/meetings/{meeting_id}/invitesAnyone in the room may invite. Send
X-Timezone so the email shows your times.
POST/meetings/{meeting_id}/invites
curl -X POST "$MORSE/meetings/3f9c1a24-5e6f-4b31-9a77-1b2c3d4e5f60/invites" \
-H "Authorization: Bearer $MORSE_TOKEN" \
-H "x-timezone: Asia/Kolkata" \
-H "Content-Type: application/json" \
-d '{ "emails": [ "priya@neuralarc.ai" ] }'[
{
"delivery": "…",
"detail": "…",
"email": "priya@neuralarc.ai",
"kind": "…"
}
]Each colleague's answer on the Google event, by address — 'accepted', 'declined', 'tentative' or 'needsAction'. Guests are never Google attendees, so they are never in it.
/meetings/{meeting_id}/invites/responsesIts own request, so the invite list never waits on Google: the list is Morse's and answers at once, and the replies fill in when Google answers — within a few seconds, or not at all. Read through each time, never kept (ADR-012): the answer is Google's, and a stored copy would only be stale.
GET/meetings/{meeting_id}/invites/responses
curl "$MORSE/meetings/3f9c1a24-5e6f-4b31-9a77-1b2c3d4e5f60/invites/responses" \
-H "Authorization: Bearer $MORSE_TOKEN"Withdraw an invitation to someone who has not arrived.
/meetings/{meeting_id}/invites/{email}Host-only, like remove. Without it, a mistyped address, or a colleague who
has no account and so no participant row to remove, stays on the calendar
event and on every email for good.
Someone who has already knocked or joined is removed from the people list
instead. That is a different act, with a re-entry guard, and this must not
become a quiet way around it.
DELETE/meetings/{meeting_id}/invites/{email}
curl -X DELETE "$MORSE/meetings/3f9c1a24-5e6f-4b31-9a77-1b2c3d4e5f60/invites/priya@neuralarc.ai" \
-H "Authorization: Bearer $MORSE_TOKEN" \
-H "x-timezone: Asia/Kolkata"Star someone invited as key to the meeting, or unstar them.
/meetings/{meeting_id}/invites/{email}/keyHost only. If a key person says no or suggests another time, the meeting shows as at risk.
PUT/meetings/{meeting_id}/invites/{email}/key
curl -X PUT "$MORSE/meetings/3f9c1a24-5e6f-4b31-9a77-1b2c3d4e5f60/invites/priya@neuralarc.ai/key" \
-H "Authorization: Bearer $MORSE_TOKEN" \
-H "Content-Type: application/json" \
-d '{ "key": true }'Keep the booked time over the one this invitee suggested.
/meetings/{meeting_id}/invites/{email}/suggestionHost only. They are emailed that it stands, with a way to answer again, and are back to no answer until they do: they said no to the old suggestion, not to this time. To use their time instead, move the meeting to it.
DELETE/meetings/{meeting_id}/invites/{email}/suggestion
curl -X DELETE "$MORSE/meetings/3f9c1a24-5e6f-4b31-9a77-1b2c3d4e5f60/invites/priya@neuralarc.ai/suggestion" \
-H "Authorization: Bearer $MORSE_TOKEN" \
-H "x-timezone: Asia/Kolkata"Undoing a removal — the only thing that can. removed is the one status
the re-entry guards refuse, so without this a misclicked Remove is permanent
and the host has to build a new meeting around one mistake.
/meetings/{meeting_id}/participants/{participant_id}/reinvite**Host-only**, matching remove rather than invite: undoing a removal is
closer to removing than to inviting. And a named act on one person, never a
side effect of re-sending a list — a host re-pasting eight addresses must
not silently readmit someone they deliberately ejected. Google Meet resolves
this the same way: a removed participant is readmitted only by being
manually re-invited from inside the meeting.
This goes *through* the guard rather than around it. The row returns to
invited, so they still have to knock and still have to be admitted —
three human decisions, where the removal took one.
POST/meetings/{meeting_id}/participants/{participant_id}/reinvite
curl -X POST "$MORSE/meetings/3f9c1a24-5e6f-4b31-9a77-1b2c3d4e5f60/participants/3f9c1a24-5e6f-4b31-9a77-1b2c3d4e5f60/reinvite" \
-H "Authorization: Bearer $MORSE_TOKEN" \
-H "x-timezone: Asia/Kolkata"{
"delivery": "…",
"detail": "…",
"email": "priya@neuralarc.ai",
"kind": "…"
}Answer an invitation: accepted, declined, or a proposed_start from
/reply/slots.
/meetings/{meeting_id}/replyThe host is emailed a no, a suggested time, or a change of mind.
POST/meetings/{meeting_id}/reply
curl -X POST "$MORSE/meetings/3f9c1a24-5e6f-4b31-9a77-1b2c3d4e5f60/reply" \
-H "Authorization: Bearer $MORSE_TOKEN" \
-H "Content-Type: application/json" \
-d '{ "note": "Annual plans are billed up front.", "proposed_start": "2026-10-02T10:30:00+05:30", "response": "accepted" }'{
"duration_minutes": 30,
"host_name": "Priya Shah",
"note": "Annual plans are billed up front.",
"proposed_start": "2026-10-02T10:30:00+05:30",
"response": "…",
"scheduled_at": "2026-10-02T10:30:00+05:30",
"status": "…"
}Times the host is free for instead, over the next two weeks.
/meetings/{meeting_id}/reply/slotsGET/meetings/{meeting_id}/reply/slots
curl "$MORSE/meetings/3f9c1a24-5e6f-4b31-9a77-1b2c3d4e5f60/reply/slots" \
-H "Authorization: Bearer $MORSE_TOKEN"{
"slots": [
"2026-10-02T10:30:00+05:30"
],
"zone": "…"
}