Personal noctalia plugins collection
1#!/usr/bin/env python3
2"""Create a calendar event via Evolution Data Server (EDS)."""
3
4import argparse
5import json
6import sys
7from datetime import datetime, timezone
8
9import gi
10gi.require_version("ECal", "2.0")
11gi.require_version("EDataServer", "1.2")
12gi.require_version("ICalGLib", "3.0")
13from gi.repository import ECal, EDataServer, ICalGLib
14
15
16def find_source(registry, calendar_uid):
17 source = registry.ref_source(calendar_uid)
18 if source and source.has_extension(EDataServer.SOURCE_EXTENSION_CALENDAR):
19 return source
20 # Fallback: search by display name
21 for src in registry.list_sources(EDataServer.SOURCE_EXTENSION_CALENDAR):
22 if src.get_display_name() == calendar_uid or src.get_uid() == calendar_uid:
23 return src
24 return None
25
26
27def make_ical_datetime(timestamp):
28 dt = datetime.fromtimestamp(timestamp, tz=timezone.utc).astimezone()
29 ical_time = ICalGLib.Time.new_null_time()
30 ical_time.set_date(dt.year, dt.month, dt.day)
31 ical_time.set_time(dt.hour, dt.minute, dt.second)
32 tz_id = dt.strftime("%Z")
33 builtin_tz = ICalGLib.Timezone.get_builtin_timezone(tz_id)
34 if builtin_tz:
35 ical_time.set_timezone(builtin_tz)
36 else:
37 ical_time.set_timezone(ICalGLib.Timezone.get_utc_timezone())
38 ical_time.set_date(dt.year, dt.month, dt.day)
39 ical_time.set_time(dt.hour, dt.minute, dt.second)
40 return ical_time
41
42
43def main():
44 parser = argparse.ArgumentParser(description="Create EDS calendar event")
45 parser.add_argument("--calendar", required=True, help="Calendar UID or display name")
46 parser.add_argument("--summary", required=True, help="Event summary/title")
47 parser.add_argument("--start", required=True, type=int, help="Start time (UNIX timestamp)")
48 parser.add_argument("--end", required=True, type=int, help="End time (UNIX timestamp)")
49 parser.add_argument("--location", default="", help="Event location")
50 parser.add_argument("--description", default="", help="Event description")
51 args = parser.parse_args()
52
53 try:
54 registry = EDataServer.SourceRegistry.new_sync(None)
55 source = find_source(registry, args.calendar)
56 if not source:
57 print(json.dumps({"success": False, "error": f"Calendar not found: {args.calendar}"}))
58 sys.exit(1)
59
60 client = ECal.Client.connect_sync(
61 source, ECal.ClientSourceType.EVENTS, -1, None
62 )
63
64 comp = ICalGLib.Component.new(ICalGLib.ComponentKind.VEVENT_COMPONENT)
65 comp.set_summary(args.summary)
66 comp.set_dtstart(make_ical_datetime(args.start))
67 comp.set_dtend(make_ical_datetime(args.end))
68
69 if args.location:
70 comp.set_location(args.location)
71 if args.description:
72 comp.set_description(args.description)
73
74 uid = client.create_object_sync(comp, ECal.OperationFlags.NONE, None)
75 print(json.dumps({"success": True, "uid": uid}))
76
77 except Exception as e:
78 print(json.dumps({"success": False, "error": str(e)}))
79 sys.exit(1)
80
81
82if __name__ == "__main__":
83 main()