Problem: Many attendees & Heavy schedule data → 502 Bad Gateway
Solution: Batch attendees + chunk date ranges
Microsoft Graph supports two access scenarios, delegated access and app-only access. In delegated access, the app calls Microsoft Graph on behalf of a signed-in user. In application-only access, the app calls Microsoft Graph with its own identity, without a signed-in user.
In the scenario of manipulating other users' schedules, you must use application-only access. In delegated access, you can only manipulate your schedule.
This demo script uses application-only access for creating events and cleaning up events. Delegated access is used for find_meeting_times.
- Go to Azure Portal → Entra ID (Azure Active Directory) → App registrations
- New registration:
- Name:
FindMeetingTimes POC - Supported account types: Single tenant or Multitenant
- Name:
- Copy Application (client) ID and Directory (tenant) ID
- API permissions → Add permission → Microsoft Graph → Delegated
- Add permissions (per MS documentation):
- User consent via browser: With interactive browser auth, users can consent to these permissions themselves during sign-in.
- API permissions → Add permission → Microsoft Graph → Application
- Add permissions and consent by administrator.
- Manage > Authentication > Settings > Allow public client flows > Enabled
Rename .env.template to .env, and replace placeholders:
AZURE_TENANT_ID=your-tenant-id-here
AZURE_CLIENT_ID=your-client-id-here
AZURE_CLIENT_SECRET=your-client-secret-here
TEST_ATTENDEES="user1@contoso.com, user2@contoso.com, user3@contoso.com"uv sync- Schedule data creation for testing:
create_events.py - Find meeting times API calls with mitigation strategies:
find_meetings.py - Purge test data:
cleanup_events.py
{
"status": 200,
"data": {
"meetingTimeSuggestions": [
{
"confidence": 87.25,
"organizerAvailability": "busy",
"meetingTimeSlot": {
"start": {
"dateTime": "2026-01-29T00:30:00.0000000",
"timeZone": "UTC"
},
"end": {
"dateTime": "2026-01-29T00:40:00.0000000",
"timeZone": "UTC"
}
}
}
],
"emptySuggestionsReason": ""
}
}