Simple API for Google Calendar management
—
GCSA provides comprehensive attendee management through the Attendee and Person classes. These classes handle event participants, organizers, RSVP status tracking, and participant permissions for collaborative calendar usage.
from gcsa.attendee import Attendee, ResponseStatus
from gcsa.person import Person
from gcsa.event import Eventclass Attendee(Person):
def __init__(
self,
email: str,
display_name = None,
comment = None,
optional = None,
is_resource = None,
additional_guests = None,
_id = None,
_is_self = None,
_response_status = None
):
"""
Create an event attendee.
:param email: Attendee's email address (required)
:param display_name: Display name for the attendee
:param comment: Comment added by attendee when responding
:param optional: Whether attendance is optional (True) or required (False)
:param is_resource: Whether this represents a resource (room, equipment) rather than person
:param additional_guests: Number of additional guests attendee can bring
:param _id: Attendee identifier (read-only)
:param _is_self: Whether this attendee is the authenticated user (read-only)
:param _response_status: Current response status (read-only, use ResponseStatus constants)
"""All Attendee objects inherit from Person and have additional attendee-specific properties for managing event participation.
class Person:
def __init__(
self,
email: str,
display_name = None,
_id = None,
_is_self = None
):
"""
Create a person object for organizers, creators, or attendees.
:param email: Person's email address (required)
:param display_name: Display name for the person
:param _id: Person identifier (read-only)
:param _is_self: Whether this person is the authenticated user (read-only)
"""class ResponseStatus:
NEEDS_ACTION = "needsAction" # No response yet (default)
DECLINED = "declined" # Declined invitation
TENTATIVE = "tentative" # Tentatively accepted
ACCEPTED = "accepted" # Accepted invitationdef add_attendee(self, attendee):
"""
Add a single attendee to the event.
:param attendee: Attendee object to add to the event
"""
def add_attendees(self, attendees):
"""
Add multiple attendees to the event.
:param attendees: List of Attendee objects to add to the event
"""from gcsa.google_calendar import GoogleCalendar
from gcsa.event import Event
from gcsa.attendee import Attendee, ResponseStatus
from datetime import datetime
gc = GoogleCalendar()
# Create attendees
organizer = Attendee(
email="organizer@example.com",
display_name="Meeting Organizer"
)
required_attendee = Attendee(
email="john.doe@example.com",
display_name="John Doe",
optional=False
)
optional_attendee = Attendee(
email="jane.smith@example.com",
display_name="Jane Smith",
optional=True,
additional_guests=2 # Can bring 2 additional guests
)
# Create event with attendees
meeting = Event(
summary="Team Planning Meeting",
start=datetime(2024, 2, 15, 10, 0),
end=datetime(2024, 2, 15, 11, 30),
description="Planning for Q2 objectives",
attendees=[organizer, required_attendee, optional_attendee]
)
gc.add_event(meeting)from gcsa.attendee import Attendee
# Get existing event
event = gc.get_event("event_id")
# Add single attendee
new_attendee = Attendee(
email="newperson@example.com",
display_name="New Person",
optional=True
)
event.add_attendee(new_attendee)
# Add multiple attendees
additional_attendees = [
Attendee("alice@example.com", display_name="Alice"),
Attendee("bob@example.com", display_name="Bob", optional=True)
]
event.add_attendees(additional_attendees)
# Update the event
gc.update_event(event, send_updates="all")from gcsa.attendee import Attendee
from gcsa.event import Event
from datetime import datetime
# Book a conference room as an attendee
conference_room = Attendee(
email="conference-room-a@example.com",
display_name="Conference Room A",
is_resource=True # Indicates this is a resource, not a person
)
# Book equipment as attendees
projector = Attendee(
email="projector-1@example.com",
display_name="Projector #1",
is_resource=True
)
meeting = Event(
summary="Board Meeting",
start=datetime(2024, 3, 1, 14, 0),
end=datetime(2024, 3, 1, 16, 0),
attendees=[
Attendee("ceo@example.com", display_name="CEO"),
Attendee("cfo@example.com", display_name="CFO"),
conference_room, # Room booking
projector # Equipment booking
]
)
gc.add_event(meeting)from gcsa.event import Event
from gcsa.attendee import Attendee
from datetime import datetime
# Create event with specific guest permissions
event = Event(
summary="Confidential Planning Session",
start=datetime(2024, 2, 20, 9, 0),
end=datetime(2024, 2, 20, 10, 0),
guests_can_invite_others=False, # Guests cannot invite others
guests_can_modify=False, # Guests cannot modify event
guests_can_see_other_guests=True, # Guests can see other attendees
attendees=[
Attendee("manager@example.com", display_name="Manager"),
Attendee("lead@example.com", display_name="Team Lead")
]
)
gc.add_event(event)from gcsa.google_calendar import GoogleCalendar
from gcsa.attendee import ResponseStatus
gc = GoogleCalendar()
# Get event with attendees
event = gc.get_event("event_id")
# Check attendee responses
print("Attendee responses:")
for attendee in event.attendees:
status = getattr(attendee, '_response_status', ResponseStatus.NEEDS_ACTION)
print(f"- {attendee.display_name or attendee.email}: {status}")
# Filter attendees by response status
accepted_attendees = [
attendee for attendee in event.attendees
if getattr(attendee, '_response_status') == ResponseStatus.ACCEPTED
]
declined_attendees = [
attendee for attendee in event.attendees
if getattr(attendee, '_response_status') == ResponseStatus.DECLINED
]
print(f"Accepted: {len(accepted_attendees)}")
print(f"Declined: {len(declined_attendees)}")from gcsa.attendee import Attendee
from gcsa.event import Event
from datetime import datetime
# Attendee with comment and additional guest allowance
attendee_with_comment = Attendee(
email="expert@example.com",
display_name="Industry Expert",
comment="Looking forward to sharing insights on market trends",
additional_guests=1 # Can bring one additional guest
)
networking_event = Event(
summary="Industry Networking Event",
start=datetime(2024, 4, 15, 18, 0),
end=datetime(2024, 4, 15, 20, 0),
location="Grand Hotel Ballroom",
attendees=[attendee_with_comment]
)
gc.add_event(networking_event)from gcsa.attendee import Attendee
from gcsa.event import Event
from datetime import datetime
# Create event with many attendees
attendee_emails = [
"employee1@example.com",
"employee2@example.com",
"employee3@example.com",
# ... many more
]
all_hands_attendees = []
for email in attendee_emails:
attendee = Attendee(
email=email,
display_name=email.split('@')[0].replace('.', ' ').title()
)
all_hands_attendees.append(attendee)
all_hands_meeting = Event(
summary="All Hands Meeting",
start=datetime(2024, 3, 15, 9, 0),
end=datetime(2024, 3, 15, 10, 0),
description="Company-wide quarterly update",
attendees=all_hands_attendees
)
gc.add_event(all_hands_meeting)from gcsa.attendee import Attendee
from gcsa.event import Event
from datetime import datetime
# Mix of internal and external attendees
internal_attendees = [
Attendee("john@mycompany.com", display_name="John (Internal)"),
Attendee("sarah@mycompany.com", display_name="Sarah (Internal)")
]
external_attendees = [
Attendee("client@othercorp.com", display_name="Client Representative"),
Attendee("vendor@supplier.com", display_name="Vendor Contact")
]
# Create client meeting with mixed attendees
client_meeting = Event(
summary="Client Review Meeting",
start=datetime(2024, 2, 28, 14, 0),
end=datetime(2024, 2, 28, 15, 30),
attendees=internal_attendees + external_attendees,
guests_can_see_other_guests=False # Hide attendee list from externals
)
# Send updates only to external attendees when updating
gc.add_event(client_meeting)
gc.update_event(client_meeting, send_updates="externalOnly")from gcsa.event import Event
from gcsa.attendee import Attendee
from datetime import datetime
# Create event that allows self-registration
workshop = Event(
summary="Python Workshop",
start=datetime(2024, 3, 20, 10, 0),
end=datetime(2024, 3, 20, 16, 0),
description="Learn Python basics in this hands-on workshop",
location="Training Room B",
anyone_can_add_self=True, # Allow people to add themselves
guests_can_invite_others=True, # Allow attendees to invite others
attendees=[
Attendee("instructor@example.com", display_name="Workshop Instructor")
]
)
gc.add_event(workshop)from gcsa.google_calendar import GoogleCalendar
from gcsa.attendee import Attendee
gc = GoogleCalendar()
# Get event and manage attendees
event = gc.get_event("event_id")
# Remove specific attendee
event.attendees = [
attendee for attendee in event.attendees
if attendee.email != "person.to.remove@example.com"
]
# Add attendees based on conditions
new_attendees = []
if len(event.attendees) < 5: # Only add if not too crowded
new_attendees.extend([
Attendee("backup1@example.com", optional=True),
Attendee("backup2@example.com", optional=True)
])
event.add_attendees(new_attendees)
gc.update_event(event)from gcsa.google_calendar import GoogleCalendar
from gcsa.person import Person
gc = GoogleCalendar()
# Get event and check organizer/creator info
event = gc.get_event("event_id")
# Check who created the event
if hasattr(event, 'creator') and event.creator:
print(f"Event created by: {event.creator.display_name or event.creator.email}")
# Check who organizes the event
if hasattr(event, 'organizer') and event.organizer:
print(f"Event organized by: {event.organizer.display_name or event.organizer.email}")
# Check if current user is the organizer
if hasattr(event.organizer, '_is_self') and event.organizer._is_self:
print("You are the organizer of this event")from gcsa.google_calendar import GoogleCalendar
from gcsa.attendee import Attendee
from gcsa.event import Event
from googleapiclient.errors import HttpError
from datetime import datetime
gc = GoogleCalendar()
try:
# Create event with potentially invalid attendee
event = Event(
summary="Test Meeting",
start=datetime(2024, 2, 15, 10, 0),
end=datetime(2024, 2, 15, 11, 0),
attendees=[
Attendee("valid@example.com", display_name="Valid User"),
Attendee("invalid-email", display_name="Invalid Email") # Invalid email
]
)
gc.add_event(event)
except HttpError as e:
print(f"Error adding attendees: {e}")
except ValueError as e:
print(f"Validation error: {e}")
# Validate email format before creating attendee
import re
def is_valid_email(email):
pattern = r'^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$'
return re.match(pattern, email) is not None
attendee_emails = ["user@example.com", "invalid-email", "user2@example.com"]
valid_attendees = []
for email in attendee_emails:
if is_valid_email(email):
valid_attendees.append(Attendee(email))
else:
print(f"Skipping invalid email: {email}")
event = Event(
summary="Validated Meeting",
start=datetime(2024, 2, 15, 10, 0),
end=datetime(2024, 2, 15, 11, 0),
attendees=valid_attendees
)
gc.add_event(event)The Attendee and Person classes provide comprehensive support for managing event participants, from simple meetings to complex events with resources, external attendees, and sophisticated permission settings. The classes handle all aspects of attendee management including RSVP tracking, guest permissions, and participant metadata.
Install with Tessl CLI
npx tessl i tessl/pypi-gcsa