add proxy for the first part and try to develop the second part

This commit is contained in:
Pierre Geeraert
2025-12-03 12:08:56 +00:00
parent 6c34d510e5
commit 460f18d85a
1095 changed files with 358799 additions and 5 deletions
@@ -0,0 +1,72 @@
from datetime import timedelta
from ics.grammar.parse import ContentLine
from ics.serializers.serializer import Serializer
from ics.utils import arrow_to_iso, escape_string, timedelta_to_duration
class BaseAlarmSerializer(Serializer):
def serialize_trigger(alarm, container):
if alarm.trigger is None:
raise ValueError("Alarm must have a trigger")
if isinstance(alarm.trigger, timedelta):
representation = timedelta_to_duration(alarm.trigger)
container.append(ContentLine("TRIGGER", value=representation))
else:
container.append(
ContentLine(
"TRIGGER",
params={"VALUE": ["DATE-TIME"]},
value=arrow_to_iso(alarm.trigger),
)
)
def serialize_duration(alarm, container):
if alarm.duration:
representation = timedelta_to_duration(alarm.duration)
container.append(ContentLine("DURATION", value=representation))
def serialize_repeat(alarm, container):
if alarm.repeat:
container.append(ContentLine("REPEAT", value=alarm.repeat))
def serialize_action(alarm, container):
container.append(ContentLine("ACTION", value=alarm.action))
class CustomAlarmSerializer(BaseAlarmSerializer):
pass
class AudioAlarmSerializer(BaseAlarmSerializer):
def serialize_attach(alarm, container):
if alarm._sound:
container.append(str(alarm._sound))
class DisplayAlarmSerializer(BaseAlarmSerializer):
def serialize_description(alarm, container):
container.append(
ContentLine("DESCRIPTION", value=escape_string(alarm.display_text or ""))
)
class EmailAlarmSerializer(BaseAlarmSerializer):
def serialize_body(alarm, container):
container.append(
ContentLine("DESCRIPTION", value=escape_string(alarm.body or ""))
)
def serialize_subject(alarm, container):
container.append(
ContentLine("SUMMARY", value=escape_string(alarm.subject or ""))
)
def serialize_recipients(alarm, container):
for attendee in alarm.recipients:
container.append(attendee.serialize())
class NoneAlarmSerializer(BaseAlarmSerializer):
pass
@@ -0,0 +1,35 @@
from ics.grammar.parse import ContentLine
from ics.serializers.serializer import Serializer
from ics.utils import escape_string
class PersonSerializer(Serializer):
def serialize_cn(person: "Person", line: ContentLine):
if person.common_name:
line.params["CN"] = [escape_string(person.common_name)]
def serialize_dir(person: "Person", line: ContentLine):
if person.dir:
line.params["DIR"] = [escape_string(person.dir)]
def serialize_sent_by(person: "Person", line: ContentLine):
if person.sent_by:
line.params["SENT-BY"] = [escape_string(person.sent_by)]
class AttendeeSerializer(PersonSerializer):
def serialize_rsvp(attendee: "Attendee", line: ContentLine):
if attendee.rsvp is not None:
line.params["RSVP"] = [attendee.rsvp]
def serialize_role(attendee: "Attendee", line: ContentLine):
if attendee.role:
line.params["ROLE"] = [escape_string(attendee.role)]
def serialize_partstat(attendee: "Attendee", line: ContentLine):
if attendee.partstat:
line.params["PARTSTAT"] = [escape_string(attendee.partstat)]
def serialize_cutype(attendee: "Attendee", line: ContentLine):
if attendee.cutype:
line.params["CUTYPE"] = [escape_string(attendee.cutype)]
@@ -0,0 +1,121 @@
from ics.attendee import Attendee, Organizer
from ics.grammar.parse import ContentLine
from ics.serializers.serializer import Serializer
from ics.utils import (arrow_date_to_iso, arrow_to_iso, escape_string,
timedelta_to_duration, uid_gen)
class EventSerializer(Serializer):
def serialize_created(event, container):
if event.created:
container.append(ContentLine("DTSTAMP", value=arrow_to_iso(event.created)))
def serialize_last_modified(event, container):
if event.last_modified:
instant = event.last_modified
container.append(ContentLine("LAST-MODIFIED", value=arrow_to_iso(instant)))
def serialize_start(event, container):
if event.begin and not event.all_day:
container.append(ContentLine("DTSTART", value=arrow_to_iso(event.begin)))
def serialize_all_day(event, container):
if event.begin and event.all_day:
container.append(
ContentLine(
"DTSTART",
params={"VALUE": ["DATE"]},
value=arrow_date_to_iso(event.begin),
)
)
if event._end_time:
container.append(
ContentLine(
"DTEND",
params={"VALUE": ["DATE"]},
value=arrow_date_to_iso(event.end),
)
)
def serialize_duration(event, container):
if event._duration and event.begin:
representation = timedelta_to_duration(event._duration)
container.append(ContentLine("DURATION", value=representation))
def serialize_end(event, container):
if event.begin and event._end_time and not event.all_day:
container.append(ContentLine("DTEND", value=arrow_to_iso(event.end)))
def serialize_summary(event, container):
if event.name:
container.append(ContentLine("SUMMARY", value=escape_string(event.name)))
def serialize_organizer(event, container):
if event.organizer:
organizer = event.organizer
if isinstance(organizer, str):
organizer = Organizer(organizer)
container.append(organizer.serialize())
def serialize_attendee(event, container):
for attendee in event.attendees:
if isinstance(attendee, str):
attendee = Attendee(attendee)
container.append(attendee.serialize())
def serialize_description(event, container):
if event.description:
container.append(
ContentLine("DESCRIPTION", value=escape_string(event.description))
)
def serialize_location(event, container):
if event.location:
container.append(
ContentLine("LOCATION", value=escape_string(event.location))
)
def serialize_geo(event, container):
if event.geo:
container.append(ContentLine("GEO", value="%f;%f" % event.geo))
def serialize_url(event, container):
if event.url:
container.append(ContentLine("URL", value=escape_string(event.url)))
def serialize_transparent(event, container):
if event.transparent is None:
return
if event.transparent:
container.append(ContentLine("TRANSP", value=escape_string("TRANSPARENT")))
else:
container.append(ContentLine("TRANSP", value=escape_string("OPAQUE")))
def serialize_uid(event, container):
if event.uid:
uid = event.uid
else:
uid = uid_gen()
container.append(ContentLine("UID", value=uid))
def serialize_alarm(event, container):
for alarm in event.alarms:
container.append(str(alarm))
def serialize_status(event, container):
if event.status:
container.append(ContentLine("STATUS", value=event.status))
def serialize_class(event, container):
if event.classification:
container.append(ContentLine("CLASS", value=event.classification))
def serialize_categories(event, container):
if event.categories:
container.append(
ContentLine(
"CATEGORIES",
value=",".join([escape_string(s) for s in event.categories]),
)
)
@@ -0,0 +1,31 @@
from ics.grammar.parse import ContentLine
from ics.serializers.serializer import Serializer
class CalendarSerializer(Serializer):
def serialize_0version(calendar, container): # 0version will be sorted first
container.append(ContentLine("VERSION", value="2.0"))
def serialize_1prodid(calendar, container): # 1prodid will be sorted second
if calendar.creator:
creator = calendar.creator
else:
creator = "ics.py - http://git.io/lLljaA"
container.append(ContentLine("PRODID", value=creator))
def serialize_calscale(calendar, container):
if calendar.scale:
container.append(ContentLine("CALSCALE", value=calendar.scale.upper()))
def serialize_method(calendar, container):
if calendar.method:
container.append(ContentLine("METHOD", value=calendar.method.upper()))
def serialize_event(calendar, container):
for event in calendar.events:
container.append(event.serialize())
def serialize_todo(calendar, container):
for todo in calendar.todos:
container.append(todo.serialize())
@@ -0,0 +1,16 @@
from typing import Callable
class Serializer:
@classmethod
def get_serializers(cls) -> Callable:
methods = [
(method_name, getattr(cls, method_name))
for method_name in dir(cls)
if callable(getattr(cls, method_name))
]
return sorted([
method_callable
for (method_name, method_callable) in methods
if method_name.startswith("serialize_")
], key=lambda x: x.__name__)
@@ -0,0 +1,88 @@
from typing import TYPE_CHECKING
import arrow
from ics.grammar.parse import Container, ContentLine
from ics.serializers.serializer import Serializer
from ics.utils import (arrow_to_iso, escape_string, timedelta_to_duration,
uid_gen)
if TYPE_CHECKING:
from ics.todo import Todo
class TodoSerializer(Serializer):
def serialize_dtstamp(todo: "Todo", container: Container):
if todo.dtstamp:
instant = todo.dtstamp
else:
instant = arrow.now()
container.append(ContentLine("DTSTAMP", value=arrow_to_iso(instant)))
def serialize_uid(todo: "Todo", container: Container):
if todo.uid:
uid = todo.uid
else:
uid = uid_gen()
container.append(ContentLine("UID", value=uid))
def serialize_completed(todo: "Todo", container: Container):
if todo.completed:
container.append(
ContentLine("COMPLETED", value=arrow_to_iso(todo.completed))
)
def serialize_created(todo: "Todo", container: Container):
if todo.created:
container.append(ContentLine("CREATED", value=arrow_to_iso(todo.created)))
def serialize_description(todo: "Todo", container: Container):
if todo.description:
container.append(
ContentLine("DESCRIPTION", value=escape_string(todo.description))
)
def serialize_start(todo: "Todo", container: Container):
if todo.begin:
container.append(ContentLine("DTSTART", value=arrow_to_iso(todo.begin)))
def serialize_location(todo: "Todo", container: Container):
if todo.location:
container.append(
ContentLine("LOCATION", value=escape_string(todo.location))
)
def serialize_percent(todo: "Todo", container: Container):
if todo.percent is not None:
container.append(ContentLine("PERCENT-COMPLETE", value=str(todo.percent)))
def serialize_priority(todo: "Todo", container: Container):
if todo.priority is not None:
container.append(ContentLine("PRIORITY", value=str(todo.priority)))
def serialize_summary(todo: "Todo", container: Container):
if todo.name:
container.append(ContentLine("SUMMARY", value=escape_string(todo.name)))
def serialize_url(todo: "Todo", container: Container):
if todo.url:
container.append(ContentLine("URL", value=escape_string(todo.url)))
def serialize_due(todo: "Todo", container: Container):
if todo._due_time:
container.append(ContentLine("DUE", value=arrow_to_iso(todo._due_time)))
def serialize_duration(todo: "Todo", container: Container):
if todo._duration:
representation = timedelta_to_duration(todo._duration)
container.append(ContentLine("DURATION", value=representation))
def serialize_alarm(todo: "Todo", container: Container):
for alarm in todo.alarms:
container.append(alarm.serialize())
def serialize_status(todo: "Todo", container: Container):
if todo.status:
container.append(ContentLine("STATUS", value=todo.status))