Waarom de Google Calendar API?
De Google Calendar API geeft je programmatische toegang tot Google Agenda: je kunt afspraken aanmaken, lezen, bijwerken en verwijderen vanuit je eigen applicatie. Dit is handig voor:
- CRM-systemen die automatisch agenda-items aanmaken bij een verkoop
- Booking-applicaties die beschikbaarheid controleren en afspraken vastleggen
- Geautomatiseerde herinneringen of terugkerende planning
- Rapporten over vergadertijd en agenda-gebruik
Gratis tot een quotum
De Google Calendar API is gratis tot een ruim quotum (zie de FAQ onderaan voor de actuele cijfers). Google heeft aangekondigd dat verbruik boven de limieten later in 2026 kosten kan gaan opleveren via je Google Cloud-factuur. Controleer de actuele limieten en eventuele tarieven altijd in de Google Cloud Console.
Stap 1: API inschakelen en authenticatie opzetten
API activeren in de Cloud Console
- Ga naar
console.cloud.google.com. - Maak een nieuw project aan of selecteer een bestaand project.
- Ga naar API's en services > Bibliotheek en zoek naar Google Calendar API.
- Klik op Inschakelen.
- Ga naar Inloggegevens en maak de juiste credentials aan: een OAuth 2.0 Client-ID voor applicaties die namens een gebruiker werken, of een Serviceaccount voor server-to-server authenticatie zonder gebruikersinteractie.
OAuth 2.0 of serviceaccount?
Onderstaande tabel helpt je kiezen tussen de twee authenticatiemethodes.
| Situatie | Kies dit |
|---|---|
| Je voert acties uit namens een specifieke gebruiker | OAuth 2.0 |
| De gebruiker moet zelf toestemming geven | OAuth 2.0 |
| Je benadert agenda's van verschillende externe gebruikers | OAuth 2.0 |
| Je draait een server-side proces zonder gebruikersinteractie | Serviceaccount |
| Je beheert agenda's binnen je eigen Workspace-domein | Serviceaccount met domeinbrede delegatie |
| Je bouwt een achtergrondproces dat automatisch agenda's beheert | Serviceaccount |
Stap 2: Authenticatie implementeren (Python)
Onderstaand voorbeeld gebruikt de officiele Google-clientbibliotheken (google-auth-oauthlib en google-api-python-client). Het slaat het token lokaal op zodat de gebruiker niet bij elke run opnieuw hoeft in te loggen.
from google.oauth2.credentials import Credentials
from google_auth_oauthlib.flow import InstalledAppFlow
from googleapiclient.discovery import build
import os
SCOPES = ['https://www.googleapis.com/auth/calendar']
def get_calendar_service():
creds = None
if os.path.exists('token.json'):
creds = Credentials.from_authorized_user_file('token.json', SCOPES)
if not creds or not creds.valid:
flow = InstalledAppFlow.from_client_secrets_file(
'credentials.json', SCOPES
)
creds = flow.run_local_server(port=0)
with open('token.json', 'w') as token:
token.write(creds.to_json())
return build('calendar', 'v3', credentials=creds)
Houd je credentials uit je repository
Zet credentials.json en token.json nooit in versiebeheer. Voeg ze toe aan je .gitignore en bewaar geheimen in productie in een secrets manager. Een gelekte refresh token geeft directe toegang tot de agenda.
Stap 3: Afspraken aanmaken
def create_event(service, calendar_id, titel, start_dt, end_dt, deelnemers=None):
event = {
'summary': titel,
'start': {
'dateTime': start_dt.isoformat(),
'timeZone': 'Europe/Amsterdam',
},
'end': {
'dateTime': end_dt.isoformat(),
'timeZone': 'Europe/Amsterdam',
},
}
if deelnemers:
event['attendees'] = [{'email': email} for email in deelnemers]
result = service.events().insert(
calendarId=calendar_id,
body=event,
sendUpdates='all'
).execute()
return result.get('htmlLink')
Met sendUpdates='all' krijgen alle deelnemers automatisch een uitnodiging. Gebruik 'none' als je geen mails wilt versturen, bijvoorbeeld bij een bulk-import.
Stap 4: Afspraken ophalen
from datetime import datetime, timezone
def get_upcoming_events(service, calendar_id, max_results=10):
now = datetime.now(timezone.utc).isoformat()
events_result = service.events().list(
calendarId=calendar_id,
timeMin=now,
maxResults=max_results,
singleEvents=True,
orderBy='startTime'
).execute()
return events_result.get('items', [])
Zet singleEvents=True zodat terugkerende afspraken worden uitgesplitst naar losse instanties. Alleen dan werkt orderBy='startTime' correct.
Beschikbaarheid controleren met FreeBusy
De FreeBusy-query is ideaal om beschikbaarheid te controleren voordat je een afspraak plant. Je krijgt per agenda de bezette tijdsblokken terug, zonder de details van de afspraken zelf.
def check_availability(service, email_addresses, start_dt, end_dt):
body = {
'timeMin': start_dt.isoformat(),
'timeMax': end_dt.isoformat(),
'timeZone': 'Europe/Amsterdam',
'items': [{'id': email} for email in email_addresses]
}
result = service.freebusy().query(body=body).execute()
return result.get('calendars', {})
Voorkom dubbele boekingen
Roep FreeBusy aan vlak voordat je een afspraak vastlegt en controleer de teruggegeven busy-blokken. Combineer dit met een korte lock of database-controle in je eigen app, zodat twee gelijktijdige boekingen niet allebei in hetzelfde gat vallen.
Webhooks voor real-time updates
In plaats van periodiek de API te pollen, kun je een notificatiekanaal instellen dat je applicatie een POST-verzoek stuurt zodra er iets in de agenda wijzigt.
def setup_calendar_watch(service, calendar_id, webhook_url):
channel = {
'id': 'mijn-unieke-channel-id',
'type': 'web_hook',
'address': webhook_url,
}
result = service.events().watch(
calendarId=calendar_id,
body=channel
).execute()
return result
Het kanaal verloopt na verloop van tijd (de vervaldatum staat in het antwoord). Plan een proces dat het kanaal op tijd vernieuwt en de oude weer afsluit met service.channels().stop(). Je webhook_url moet publiek bereikbaar zijn via HTTPS met een geldig certificaat.
Hoe lang zijn OAuth-tokens geldig?
Access tokens zijn standaard 1 uur geldig. Refresh tokens blijven in productie geldig totdat ze worden ingetrokken, maar vervallen automatisch na zes maanden zonder gebruik. Let op: zolang je OAuth-toestemmingsscherm op de status Testing staat met gebruikerstype Extern, vervalt de refresh token al na 7 dagen. Zet de publicatiestatus op In productie om dat te voorkomen.
Kan ik de API gebruiken voor agenda's van andere gebruikers in mijn organisatie?
Met een serviceaccount en domeinbrede delegatie kun je namens alle gebruikers in je Workspace-domein acties uitvoeren. Dit moet een beheerder eerst goedkeuren in de Admin-console.
Is er een limiet aan het aantal API-aanroepen?
Ja. De Calendar API kent een drempel van ongeveer 1.000.000 verzoeken per dag per project en 600 verzoeken per minuut per gebruiker. Projecten die op of na 1 mei 2026 zijn aangemaakt vallen onder een herziene quotumstructuur, dus controleer de actuele cijfers altijd in de Cloud Console.
Kan ik terugkerende evenementen aanmaken?
Ja, gebruik het veld recurrence in de event-body met RRULE-syntax. Bijvoorbeeld RRULE:FREQ=WEEKLY;BYDAY=MO,WE,FR voor een wekelijkse afspraak op maandag, woensdag en vrijdag.
Hoe verwijder ik een afspraak via de API?
Gebruik service.events().delete(calendarId=calendar_id, eventId=event_id).execute(). Verwijderen is permanent. Wil je een afspraak alleen annuleren zonder hem te verwijderen, zet dan het veld status op cancelled.
Waarom krijg ik foutmelding 403 "usage limits exceeded"?
Je raakt dan een snelheidslimiet, meestal de limiet per gebruiker per minuut. Bouw exponentiele back-off met retries in en spreid bulk-bewerkingen over de tijd. Per gebruiker een eigen quota-identifier meesturen helpt om verzoeken eerlijk te verdelen.