@todu/engine 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (57) hide show
  1. package/dist/change-observer.d.ts +15 -0
  2. package/dist/change-observer.d.ts.map +1 -0
  3. package/dist/change-observer.js +64 -0
  4. package/dist/change-observer.js.map +1 -0
  5. package/dist/habits.d.ts +6 -0
  6. package/dist/habits.d.ts.map +1 -0
  7. package/dist/habits.js +397 -0
  8. package/dist/habits.js.map +1 -0
  9. package/dist/index.d.ts +25 -0
  10. package/dist/index.d.ts.map +1 -0
  11. package/dist/index.js +104 -0
  12. package/dist/index.js.map +1 -0
  13. package/dist/labels.d.ts +5 -0
  14. package/dist/labels.d.ts.map +1 -0
  15. package/dist/labels.js +113 -0
  16. package/dist/labels.js.map +1 -0
  17. package/dist/notes.d.ts +5 -0
  18. package/dist/notes.d.ts.map +1 -0
  19. package/dist/notes.js +163 -0
  20. package/dist/notes.js.map +1 -0
  21. package/dist/projects.d.ts +5 -0
  22. package/dist/projects.d.ts.map +1 -0
  23. package/dist/projects.js +117 -0
  24. package/dist/projects.js.map +1 -0
  25. package/dist/recurring.d.ts +23 -0
  26. package/dist/recurring.d.ts.map +1 -0
  27. package/dist/recurring.js +372 -0
  28. package/dist/recurring.js.map +1 -0
  29. package/dist/schedule.d.ts +38 -0
  30. package/dist/schedule.d.ts.map +1 -0
  31. package/dist/schedule.js +330 -0
  32. package/dist/schedule.js.map +1 -0
  33. package/dist/scheduling.d.ts +62 -0
  34. package/dist/scheduling.d.ts.map +1 -0
  35. package/dist/scheduling.js +58 -0
  36. package/dist/scheduling.js.map +1 -0
  37. package/dist/storage.d.ts +34 -0
  38. package/dist/storage.d.ts.map +1 -0
  39. package/dist/storage.js +204 -0
  40. package/dist/storage.js.map +1 -0
  41. package/dist/sync-client.d.ts +16 -0
  42. package/dist/sync-client.d.ts.map +1 -0
  43. package/dist/sync-client.js +54 -0
  44. package/dist/sync-client.js.map +1 -0
  45. package/dist/sync-server.d.ts +12 -0
  46. package/dist/sync-server.d.ts.map +1 -0
  47. package/dist/sync-server.js +21 -0
  48. package/dist/sync-server.js.map +1 -0
  49. package/dist/tasks.d.ts +18 -0
  50. package/dist/tasks.d.ts.map +1 -0
  51. package/dist/tasks.js +396 -0
  52. package/dist/tasks.js.map +1 -0
  53. package/dist/todu.d.ts +115 -0
  54. package/dist/todu.d.ts.map +1 -0
  55. package/dist/todu.js +76 -0
  56. package/dist/todu.js.map +1 -0
  57. package/package.json +52 -0
@@ -0,0 +1,330 @@
1
+ import { validateRRule as coreValidateRRule, validationError, } from "@todu/core";
2
+ // rrule is CJS. Node wraps it in { default: ... }, Bun resolves ESM named exports.
3
+ // Use namespace import and unwrap at runtime to support both.
4
+ import * as rruleNs from "rrule";
5
+ // biome-ignore lint/suspicious/noExplicitAny: CJS/ESM interop requires runtime detection
6
+ const rruleMod = rruleNs.default ?? rruleNs;
7
+ const RRule = rruleMod.RRule;
8
+ /** Internal: create an RRule from parsed options */
9
+ function createRRule(options) {
10
+ return new RRule(options);
11
+ }
12
+ /** Internal: parse an RRULE string into options */
13
+ function parseRRuleString(rule) {
14
+ return RRule.parseString(rule);
15
+ }
16
+ // ============================================================================
17
+ // RRULE parsing and occurrence calculation
18
+ // ============================================================================
19
+ /**
20
+ * Parse an RRULE string into an internal RRule instance with a start date.
21
+ * Returns the instance for use by nextOccurrence/nextOccurrences.
22
+ * The RRule type is not exposed — consumers use the higher-level functions.
23
+ */
24
+ function parseRule(rule, startDate, timezone) {
25
+ // Validate format first
26
+ const formatError = coreValidateRRule(rule);
27
+ if (formatError)
28
+ return { error: formatError };
29
+ try {
30
+ // Parse start date as a Date in UTC (rrule library works in UTC internally)
31
+ const dtstart = dateStringToUTC(startDate, timezone);
32
+ // Parse the RRULE string and create instance
33
+ const parsed = parseRRuleString(rule);
34
+ const rrule = createRRule({
35
+ ...parsed,
36
+ dtstart,
37
+ });
38
+ return { rrule };
39
+ }
40
+ catch (e) {
41
+ return {
42
+ error: validationError("schedule", `Failed to parse RRULE: ${e instanceof Error ? e.message : String(e)}`),
43
+ };
44
+ }
45
+ }
46
+ /**
47
+ * Calculate the next occurrence after a given date.
48
+ *
49
+ * @param rule - RRULE string
50
+ * @param startDate - Schedule start date (YYYY-MM-DD)
51
+ * @param timezone - IANA timezone
52
+ * @param afterDate - Find next occurrence after this date (YYYY-MM-DD)
53
+ * @param endDate - Optional end date (YYYY-MM-DD) — no occurrences after this
54
+ * @returns Next occurrence as YYYY-MM-DD string, or null if no more occurrences
55
+ */
56
+ export function nextOccurrence(rule, startDate, timezone, afterDate, endDate) {
57
+ const parsed = parseRule(rule, startDate, timezone);
58
+ if (parsed.error)
59
+ return null;
60
+ const after = dateStringToUTC(afterDate, timezone);
61
+ const next = parsed.rrule.after(after);
62
+ if (!next)
63
+ return null;
64
+ // Convert back to date string in the template's timezone
65
+ const dateStr = utcToDateString(next, timezone);
66
+ // Check against end date
67
+ if (endDate && dateStr > endDate)
68
+ return null;
69
+ return dateStr;
70
+ }
71
+ /**
72
+ * Calculate the next N occurrences starting from a given date (inclusive).
73
+ * Used for the "upcoming" view.
74
+ *
75
+ * @param rule - RRULE string
76
+ * @param startDate - Schedule start date (YYYY-MM-DD)
77
+ * @param timezone - IANA timezone
78
+ * @param fromDate - Start listing from this date (YYYY-MM-DD), inclusive
79
+ * @param count - Number of occurrences to return
80
+ * @param endDate - Optional end date (YYYY-MM-DD)
81
+ * @returns Array of YYYY-MM-DD date strings
82
+ */
83
+ export function nextOccurrences(rule, startDate, timezone, fromDate, count, endDate) {
84
+ const parsed = parseRule(rule, startDate, timezone);
85
+ if (parsed.error)
86
+ return [];
87
+ const results = [];
88
+ // Get occurrences starting from the day before fromDate
89
+ // (so fromDate itself is included if it matches)
90
+ const dayBefore = shiftDate(fromDate, -1);
91
+ const after = dateStringToUTC(dayBefore, timezone);
92
+ // Use between() for bounded queries when we have an end date
93
+ const effectiveEnd = endDate ? dateStringToUTC(endDate, timezone) : null;
94
+ let current = parsed.rrule.after(after);
95
+ while (current && results.length < count) {
96
+ const dateStr = utcToDateString(current, timezone);
97
+ // Check end date
98
+ if (effectiveEnd && current > effectiveEnd)
99
+ break;
100
+ results.push(dateStr);
101
+ current = parsed.rrule.after(current);
102
+ }
103
+ return results;
104
+ }
105
+ /**
106
+ * Check if a specific date is a valid occurrence of the schedule.
107
+ * Used to validate early materialization requests.
108
+ */
109
+ export function isScheduledDate(rule, startDate, timezone, date, endDate) {
110
+ const parsed = parseRule(rule, startDate, timezone);
111
+ if (parsed.error)
112
+ return false;
113
+ // Check if date is within bounds
114
+ if (date < startDate)
115
+ return false;
116
+ if (endDate && date > endDate)
117
+ return false;
118
+ // Check the day before to see if this date is the next occurrence
119
+ const dayBefore = shiftDate(date, -1);
120
+ const after = dateStringToUTC(dayBefore, timezone);
121
+ const next = parsed.rrule.after(after);
122
+ if (!next)
123
+ return false;
124
+ const nextStr = utcToDateString(next, timezone);
125
+ return nextStr === date;
126
+ }
127
+ // ============================================================================
128
+ // Human-readable schedule descriptions
129
+ // ============================================================================
130
+ const DAY_NAMES = {
131
+ MO: "Monday",
132
+ TU: "Tuesday",
133
+ WE: "Wednesday",
134
+ TH: "Thursday",
135
+ FR: "Friday",
136
+ SA: "Saturday",
137
+ SU: "Sunday",
138
+ };
139
+ const SHORT_DAY_NAMES = {
140
+ MO: "Mon",
141
+ TU: "Tue",
142
+ WE: "Wed",
143
+ TH: "Thu",
144
+ FR: "Fri",
145
+ SA: "Sat",
146
+ SU: "Sun",
147
+ };
148
+ /**
149
+ * Convert an RRULE string to a human-readable description.
150
+ */
151
+ export function describeSchedule(rule) {
152
+ const parts = parseRRuleParts(rule);
153
+ const freq = (parts.FREQ || "").toUpperCase();
154
+ const interval = parts.INTERVAL ? Number.parseInt(parts.INTERVAL, 10) : 1;
155
+ const byday = parts.BYDAY;
156
+ const bymonthday = parts.BYMONTHDAY;
157
+ const bymonth = parts.BYMONTH;
158
+ switch (freq) {
159
+ case "DAILY": {
160
+ if (interval === 1) {
161
+ if (byday)
162
+ return `Daily on ${formatDayList(byday)}`;
163
+ return "Daily";
164
+ }
165
+ return `Every ${interval} days`;
166
+ }
167
+ case "WEEKLY": {
168
+ const prefix = interval === 1 ? "Weekly" : `Every ${interval} weeks`;
169
+ if (byday) {
170
+ const days = byday.split(",");
171
+ // Check for common patterns
172
+ if (isWeekdays(days))
173
+ return interval === 1 ? "Every weekday" : `${prefix} on weekdays`;
174
+ return `${prefix} on ${formatDayList(byday)}`;
175
+ }
176
+ return prefix;
177
+ }
178
+ case "MONTHLY": {
179
+ const prefix = interval === 1 ? "Monthly" : `Every ${interval} months`;
180
+ if (bymonthday)
181
+ return `${prefix} on day ${bymonthday}`;
182
+ return prefix;
183
+ }
184
+ case "YEARLY": {
185
+ const prefix = interval === 1 ? "Yearly" : `Every ${interval} years`;
186
+ if (bymonth && bymonthday) {
187
+ const monthName = getMonthName(Number.parseInt(bymonth, 10));
188
+ return `${prefix} on ${monthName} ${bymonthday}`;
189
+ }
190
+ return prefix;
191
+ }
192
+ default:
193
+ return rule;
194
+ }
195
+ }
196
+ // ============================================================================
197
+ // Today helper — get current date in a timezone
198
+ // ============================================================================
199
+ /**
200
+ * Get today's date in the given timezone as YYYY-MM-DD.
201
+ */
202
+ export function todayInTimezone(timezone) {
203
+ const formatter = new Intl.DateTimeFormat("en-CA", {
204
+ timeZone: timezone,
205
+ year: "numeric",
206
+ month: "2-digit",
207
+ day: "2-digit",
208
+ });
209
+ return formatter.format(new Date());
210
+ }
211
+ // ============================================================================
212
+ // Internal helpers
213
+ // ============================================================================
214
+ /**
215
+ * Convert a YYYY-MM-DD date string to a UTC Date object,
216
+ * treating the date as midnight in the given timezone.
217
+ */
218
+ function dateStringToUTC(dateStr, timezone) {
219
+ // Parse the date parts
220
+ const [year, month, day] = dateStr.split("-").map(Number);
221
+ // Create a date at midnight UTC first
222
+ const utcDate = new Date(Date.UTC(year, month - 1, day));
223
+ // Get the timezone offset for this date
224
+ // We use a formatter to determine what time it is in the target timezone
225
+ const formatter = new Intl.DateTimeFormat("en-US", {
226
+ timeZone: timezone,
227
+ year: "numeric",
228
+ month: "numeric",
229
+ day: "numeric",
230
+ hour: "numeric",
231
+ minute: "numeric",
232
+ hourCycle: "h23",
233
+ });
234
+ // Find the offset by comparing the formatted date to the UTC date
235
+ const parts = formatter.formatToParts(utcDate);
236
+ const getPart = (type) => Number(parts.find((p) => p.type === type)?.value || 0);
237
+ const tzYear = getPart("year");
238
+ const tzMonth = getPart("month");
239
+ const tzDay = getPart("day");
240
+ const tzHour = getPart("hour");
241
+ const tzMinute = getPart("minute");
242
+ // If the timezone date differs from what we want, we need to adjust
243
+ // We want midnight in the target timezone
244
+ const tzDate = new Date(Date.UTC(tzYear, tzMonth - 1, tzDay, tzHour, tzMinute));
245
+ const offsetMs = tzDate.getTime() - utcDate.getTime();
246
+ // Midnight in the target timezone = UTC midnight minus the offset
247
+ return new Date(Date.UTC(year, month - 1, day) - offsetMs);
248
+ }
249
+ /**
250
+ * Convert a UTC Date object to a YYYY-MM-DD string in the given timezone.
251
+ */
252
+ function utcToDateString(date, timezone) {
253
+ const formatter = new Intl.DateTimeFormat("en-CA", {
254
+ timeZone: timezone,
255
+ year: "numeric",
256
+ month: "2-digit",
257
+ day: "2-digit",
258
+ });
259
+ return formatter.format(date);
260
+ }
261
+ /**
262
+ * Shift a YYYY-MM-DD date string by N days.
263
+ */
264
+ function shiftDate(dateStr, days) {
265
+ const [year, month, day] = dateStr.split("-").map(Number);
266
+ const date = new Date(Date.UTC(year, month - 1, day + days));
267
+ const y = date.getUTCFullYear();
268
+ const m = String(date.getUTCMonth() + 1).padStart(2, "0");
269
+ const d = String(date.getUTCDate()).padStart(2, "0");
270
+ return `${y}-${m}-${d}`;
271
+ }
272
+ /**
273
+ * Parse an RRULE string into key-value pairs.
274
+ */
275
+ function parseRRuleParts(rule) {
276
+ const result = {};
277
+ for (const part of rule.split(";")) {
278
+ const [key, value] = part.split("=", 2);
279
+ if (key && value) {
280
+ result[key.toUpperCase()] = value;
281
+ }
282
+ }
283
+ return result;
284
+ }
285
+ /**
286
+ * Format a comma-separated BYDAY list into human-readable form.
287
+ */
288
+ function formatDayList(byday) {
289
+ const days = byday.split(",").map((d) => d.trim().toUpperCase());
290
+ if (days.length === 1) {
291
+ return DAY_NAMES[days[0]] || days[0];
292
+ }
293
+ // Use short names for multiple days
294
+ const names = days.map((d) => SHORT_DAY_NAMES[d] || d);
295
+ if (names.length === 2) {
296
+ return `${names[0]} and ${names[1]}`;
297
+ }
298
+ return `${names.slice(0, -1).join(", ")}, and ${names[names.length - 1]}`;
299
+ }
300
+ /**
301
+ * Check if a set of days represents weekdays (Mon-Fri).
302
+ */
303
+ function isWeekdays(days) {
304
+ const weekdays = new Set(["MO", "TU", "WE", "TH", "FR"]);
305
+ if (days.length !== 5)
306
+ return false;
307
+ return days.every((d) => weekdays.has(d.toUpperCase()));
308
+ }
309
+ /**
310
+ * Get month name from number (1-12).
311
+ */
312
+ function getMonthName(month) {
313
+ const names = [
314
+ "",
315
+ "January",
316
+ "February",
317
+ "March",
318
+ "April",
319
+ "May",
320
+ "June",
321
+ "July",
322
+ "August",
323
+ "September",
324
+ "October",
325
+ "November",
326
+ "December",
327
+ ];
328
+ return names[month] || String(month);
329
+ }
330
+ //# sourceMappingURL=schedule.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"schedule.js","sourceRoot":"","sources":["../src/schedule.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,aAAa,IAAI,iBAAiB,EAElC,eAAe,GAChB,MAAM,YAAY,CAAC;AAEpB,mFAAmF;AACnF,8DAA8D;AAC9D,OAAO,KAAK,OAAO,MAAM,OAAO,CAAC;AAEjC,yFAAyF;AACzF,MAAM,QAAQ,GAAI,OAAe,CAAC,OAAO,IAAI,OAAO,CAAC;AACrD,MAAM,KAAK,GAAG,QAAQ,CAAC,KAA6B,CAAC;AAQrD,oDAAoD;AACpD,SAAS,WAAW,CAAC,OAAgC,EAAiB;IACpE,OAAO,IAAI,KAAK,CAAC,OAAO,CAA6B,CAAC;AAAA,CACvD;AAED,mDAAmD;AACnD,SAAS,gBAAgB,CAAC,IAAY,EAA2B;IAC/D,OAAO,KAAK,CAAC,WAAW,CAAC,IAAI,CAA4B,CAAC;AAAA,CAC3D;AAED,+EAA+E;AAC/E,2CAA2C;AAC3C,+EAA+E;AAE/E;;;;GAIG;AACH,SAAS,SAAS,CAChB,IAAY,EACZ,SAAiB,EACjB,QAAgB,EACqE;IACrF,wBAAwB;IACxB,MAAM,WAAW,GAAG,iBAAiB,CAAC,IAAI,CAAC,CAAC;IAC5C,IAAI,WAAW;QAAE,OAAO,EAAE,KAAK,EAAE,WAAW,EAAE,CAAC;IAE/C,IAAI,CAAC;QACH,4EAA4E;QAC5E,MAAM,OAAO,GAAG,eAAe,CAAC,SAAS,EAAE,QAAQ,CAAC,CAAC;QAErD,6CAA6C;QAC7C,MAAM,MAAM,GAAG,gBAAgB,CAAC,IAAI,CAAC,CAAC;QACtC,MAAM,KAAK,GAAG,WAAW,CAAC;YACxB,GAAG,MAAM;YACT,OAAO;SACR,CAAC,CAAC;QAEH,OAAO,EAAE,KAAK,EAAE,CAAC;IACnB,CAAC;IAAC,OAAO,CAAC,EAAE,CAAC;QACX,OAAO;YACL,KAAK,EAAE,eAAe,CACpB,UAAU,EACV,0BAA0B,CAAC,YAAY,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CACvE;SACF,CAAC;IACJ,CAAC;AAAA,CACF;AAED;;;;;;;;;GASG;AACH,MAAM,UAAU,cAAc,CAC5B,IAAY,EACZ,SAAiB,EACjB,QAAgB,EAChB,SAAiB,EACjB,OAAgB,EACD;IACf,MAAM,MAAM,GAAG,SAAS,CAAC,IAAI,EAAE,SAAS,EAAE,QAAQ,CAAC,CAAC;IACpD,IAAI,MAAM,CAAC,KAAK;QAAE,OAAO,IAAI,CAAC;IAE9B,MAAM,KAAK,GAAG,eAAe,CAAC,SAAS,EAAE,QAAQ,CAAC,CAAC;IACnD,MAAM,IAAI,GAAG,MAAM,CAAC,KAAK,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;IAEvC,IAAI,CAAC,IAAI;QAAE,OAAO,IAAI,CAAC;IAEvB,yDAAyD;IACzD,MAAM,OAAO,GAAG,eAAe,CAAC,IAAI,EAAE,QAAQ,CAAC,CAAC;IAEhD,yBAAyB;IACzB,IAAI,OAAO,IAAI,OAAO,GAAG,OAAO;QAAE,OAAO,IAAI,CAAC;IAE9C,OAAO,OAAO,CAAC;AAAA,CAChB;AAED;;;;;;;;;;;GAWG;AACH,MAAM,UAAU,eAAe,CAC7B,IAAY,EACZ,SAAiB,EACjB,QAAgB,EAChB,QAAgB,EAChB,KAAa,EACb,OAAgB,EACN;IACV,MAAM,MAAM,GAAG,SAAS,CAAC,IAAI,EAAE,SAAS,EAAE,QAAQ,CAAC,CAAC;IACpD,IAAI,MAAM,CAAC,KAAK;QAAE,OAAO,EAAE,CAAC;IAE5B,MAAM,OAAO,GAAa,EAAE,CAAC;IAE7B,wDAAwD;IACxD,iDAAiD;IACjD,MAAM,SAAS,GAAG,SAAS,CAAC,QAAQ,EAAE,CAAC,CAAC,CAAC,CAAC;IAC1C,MAAM,KAAK,GAAG,eAAe,CAAC,SAAS,EAAE,QAAQ,CAAC,CAAC;IAEnD,6DAA6D;IAC7D,MAAM,YAAY,GAAG,OAAO,CAAC,CAAC,CAAC,eAAe,CAAC,OAAO,EAAE,QAAQ,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC;IAEzE,IAAI,OAAO,GAAgB,MAAM,CAAC,KAAK,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;IAErD,OAAO,OAAO,IAAI,OAAO,CAAC,MAAM,GAAG,KAAK,EAAE,CAAC;QACzC,MAAM,OAAO,GAAG,eAAe,CAAC,OAAO,EAAE,QAAQ,CAAC,CAAC;QAEnD,iBAAiB;QACjB,IAAI,YAAY,IAAI,OAAO,GAAG,YAAY;YAAE,MAAM;QAElD,OAAO,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;QACtB,OAAO,GAAG,MAAM,CAAC,KAAK,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;IACxC,CAAC;IAED,OAAO,OAAO,CAAC;AAAA,CAChB;AAED;;;GAGG;AACH,MAAM,UAAU,eAAe,CAC7B,IAAY,EACZ,SAAiB,EACjB,QAAgB,EAChB,IAAY,EACZ,OAAgB,EACP;IACT,MAAM,MAAM,GAAG,SAAS,CAAC,IAAI,EAAE,SAAS,EAAE,QAAQ,CAAC,CAAC;IACpD,IAAI,MAAM,CAAC,KAAK;QAAE,OAAO,KAAK,CAAC;IAE/B,iCAAiC;IACjC,IAAI,IAAI,GAAG,SAAS;QAAE,OAAO,KAAK,CAAC;IACnC,IAAI,OAAO,IAAI,IAAI,GAAG,OAAO;QAAE,OAAO,KAAK,CAAC;IAE5C,kEAAkE;IAClE,MAAM,SAAS,GAAG,SAAS,CAAC,IAAI,EAAE,CAAC,CAAC,CAAC,CAAC;IACtC,MAAM,KAAK,GAAG,eAAe,CAAC,SAAS,EAAE,QAAQ,CAAC,CAAC;IACnD,MAAM,IAAI,GAAG,MAAM,CAAC,KAAK,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;IAEvC,IAAI,CAAC,IAAI;QAAE,OAAO,KAAK,CAAC;IAExB,MAAM,OAAO,GAAG,eAAe,CAAC,IAAI,EAAE,QAAQ,CAAC,CAAC;IAChD,OAAO,OAAO,KAAK,IAAI,CAAC;AAAA,CACzB;AAED,+EAA+E;AAC/E,uCAAuC;AACvC,+EAA+E;AAE/E,MAAM,SAAS,GAA2B;IACxC,EAAE,EAAE,QAAQ;IACZ,EAAE,EAAE,SAAS;IACb,EAAE,EAAE,WAAW;IACf,EAAE,EAAE,UAAU;IACd,EAAE,EAAE,QAAQ;IACZ,EAAE,EAAE,UAAU;IACd,EAAE,EAAE,QAAQ;CACb,CAAC;AAEF,MAAM,eAAe,GAA2B;IAC9C,EAAE,EAAE,KAAK;IACT,EAAE,EAAE,KAAK;IACT,EAAE,EAAE,KAAK;IACT,EAAE,EAAE,KAAK;IACT,EAAE,EAAE,KAAK;IACT,EAAE,EAAE,KAAK;IACT,EAAE,EAAE,KAAK;CACV,CAAC;AAEF;;GAEG;AACH,MAAM,UAAU,gBAAgB,CAAC,IAAY,EAAU;IACrD,MAAM,KAAK,GAAG,eAAe,CAAC,IAAI,CAAC,CAAC;IACpC,MAAM,IAAI,GAAG,CAAC,KAAK,CAAC,IAAI,IAAI,EAAE,CAAC,CAAC,WAAW,EAAE,CAAC;IAC9C,MAAM,QAAQ,GAAG,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,QAAQ,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC1E,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC;IAC1B,MAAM,UAAU,GAAG,KAAK,CAAC,UAAU,CAAC;IACpC,MAAM,OAAO,GAAG,KAAK,CAAC,OAAO,CAAC;IAE9B,QAAQ,IAAI,EAAE,CAAC;QACb,KAAK,OAAO,EAAE,CAAC;YACb,IAAI,QAAQ,KAAK,CAAC,EAAE,CAAC;gBACnB,IAAI,KAAK;oBAAE,OAAO,YAAY,aAAa,CAAC,KAAK,CAAC,EAAE,CAAC;gBACrD,OAAO,OAAO,CAAC;YACjB,CAAC;YACD,OAAO,SAAS,QAAQ,OAAO,CAAC;QAClC,CAAC;QAED,KAAK,QAAQ,EAAE,CAAC;YACd,MAAM,MAAM,GAAG,QAAQ,KAAK,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,SAAS,QAAQ,QAAQ,CAAC;YACrE,IAAI,KAAK,EAAE,CAAC;gBACV,MAAM,IAAI,GAAG,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;gBAC9B,4BAA4B;gBAC5B,IAAI,UAAU,CAAC,IAAI,CAAC;oBAAE,OAAO,QAAQ,KAAK,CAAC,CAAC,CAAC,CAAC,eAAe,CAAC,CAAC,CAAC,GAAG,MAAM,cAAc,CAAC;gBACxF,OAAO,GAAG,MAAM,OAAO,aAAa,CAAC,KAAK,CAAC,EAAE,CAAC;YAChD,CAAC;YACD,OAAO,MAAM,CAAC;QAChB,CAAC;QAED,KAAK,SAAS,EAAE,CAAC;YACf,MAAM,MAAM,GAAG,QAAQ,KAAK,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,SAAS,QAAQ,SAAS,CAAC;YACvE,IAAI,UAAU;gBAAE,OAAO,GAAG,MAAM,WAAW,UAAU,EAAE,CAAC;YACxD,OAAO,MAAM,CAAC;QAChB,CAAC;QAED,KAAK,QAAQ,EAAE,CAAC;YACd,MAAM,MAAM,GAAG,QAAQ,KAAK,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,SAAS,QAAQ,QAAQ,CAAC;YACrE,IAAI,OAAO,IAAI,UAAU,EAAE,CAAC;gBAC1B,MAAM,SAAS,GAAG,YAAY,CAAC,MAAM,CAAC,QAAQ,CAAC,OAAO,EAAE,EAAE,CAAC,CAAC,CAAC;gBAC7D,OAAO,GAAG,MAAM,OAAO,SAAS,IAAI,UAAU,EAAE,CAAC;YACnD,CAAC;YACD,OAAO,MAAM,CAAC;QAChB,CAAC;QAED;YACE,OAAO,IAAI,CAAC;IAChB,CAAC;AAAA,CACF;AAED,+EAA+E;AAC/E,kDAAgD;AAChD,+EAA+E;AAE/E;;GAEG;AACH,MAAM,UAAU,eAAe,CAAC,QAAgB,EAAU;IACxD,MAAM,SAAS,GAAG,IAAI,IAAI,CAAC,cAAc,CAAC,OAAO,EAAE;QACjD,QAAQ,EAAE,QAAQ;QAClB,IAAI,EAAE,SAAS;QACf,KAAK,EAAE,SAAS;QAChB,GAAG,EAAE,SAAS;KACf,CAAC,CAAC;IACH,OAAO,SAAS,CAAC,MAAM,CAAC,IAAI,IAAI,EAAE,CAAC,CAAC;AAAA,CACrC;AAED,+EAA+E;AAC/E,mBAAmB;AACnB,+EAA+E;AAE/E;;;GAGG;AACH,SAAS,eAAe,CAAC,OAAe,EAAE,QAAgB,EAAQ;IAChE,uBAAuB;IACvB,MAAM,CAAC,IAAI,EAAE,KAAK,EAAE,GAAG,CAAC,GAAG,OAAO,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC;IAE1D,sCAAsC;IACtC,MAAM,OAAO,GAAG,IAAI,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,EAAE,KAAK,GAAG,CAAC,EAAE,GAAG,CAAC,CAAC,CAAC;IAEzD,wCAAwC;IACxC,yEAAyE;IACzE,MAAM,SAAS,GAAG,IAAI,IAAI,CAAC,cAAc,CAAC,OAAO,EAAE;QACjD,QAAQ,EAAE,QAAQ;QAClB,IAAI,EAAE,SAAS;QACf,KAAK,EAAE,SAAS;QAChB,GAAG,EAAE,SAAS;QACd,IAAI,EAAE,SAAS;QACf,MAAM,EAAE,SAAS;QACjB,SAAS,EAAE,KAAK;KACjB,CAAC,CAAC;IAEH,kEAAkE;IAClE,MAAM,KAAK,GAAG,SAAS,CAAC,aAAa,CAAC,OAAO,CAAC,CAAC;IAC/C,MAAM,OAAO,GAAG,CAAC,IAAY,EAAE,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,KAAK,IAAI,CAAC,EAAE,KAAK,IAAI,CAAC,CAAC,CAAC;IAEzF,MAAM,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IAC/B,MAAM,OAAO,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IACjC,MAAM,KAAK,GAAG,OAAO,CAAC,KAAK,CAAC,CAAC;IAC7B,MAAM,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IAC/B,MAAM,QAAQ,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAC;IAEnC,oEAAoE;IACpE,0CAA0C;IAC1C,MAAM,MAAM,GAAG,IAAI,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE,OAAO,GAAG,CAAC,EAAE,KAAK,EAAE,MAAM,EAAE,QAAQ,CAAC,CAAC,CAAC;IAChF,MAAM,QAAQ,GAAG,MAAM,CAAC,OAAO,EAAE,GAAG,OAAO,CAAC,OAAO,EAAE,CAAC;IAEtD,kEAAkE;IAClE,OAAO,IAAI,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,EAAE,KAAK,GAAG,CAAC,EAAE,GAAG,CAAC,GAAG,QAAQ,CAAC,CAAC;AAAA,CAC5D;AAED;;GAEG;AACH,SAAS,eAAe,CAAC,IAAU,EAAE,QAAgB,EAAU;IAC7D,MAAM,SAAS,GAAG,IAAI,IAAI,CAAC,cAAc,CAAC,OAAO,EAAE;QACjD,QAAQ,EAAE,QAAQ;QAClB,IAAI,EAAE,SAAS;QACf,KAAK,EAAE,SAAS;QAChB,GAAG,EAAE,SAAS;KACf,CAAC,CAAC;IACH,OAAO,SAAS,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;AAAA,CAC/B;AAED;;GAEG;AACH,SAAS,SAAS,CAAC,OAAe,EAAE,IAAY,EAAU;IACxD,MAAM,CAAC,IAAI,EAAE,KAAK,EAAE,GAAG,CAAC,GAAG,OAAO,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC;IAC1D,MAAM,IAAI,GAAG,IAAI,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,EAAE,KAAK,GAAG,CAAC,EAAE,GAAG,GAAG,IAAI,CAAC,CAAC,CAAC;IAC7D,MAAM,CAAC,GAAG,IAAI,CAAC,cAAc,EAAE,CAAC;IAChC,MAAM,CAAC,GAAG,MAAM,CAAC,IAAI,CAAC,WAAW,EAAE,GAAG,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC;IAC1D,MAAM,CAAC,GAAG,MAAM,CAAC,IAAI,CAAC,UAAU,EAAE,CAAC,CAAC,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC;IACrD,OAAO,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC;AAAA,CACzB;AAED;;GAEG;AACH,SAAS,eAAe,CAAC,IAAY,EAA0B;IAC7D,MAAM,MAAM,GAA2B,EAAE,CAAC;IAC1C,KAAK,MAAM,IAAI,IAAI,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,EAAE,CAAC;QACnC,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC,CAAC;QACxC,IAAI,GAAG,IAAI,KAAK,EAAE,CAAC;YACjB,MAAM,CAAC,GAAG,CAAC,WAAW,EAAE,CAAC,GAAG,KAAK,CAAC;QACpC,CAAC;IACH,CAAC;IACD,OAAO,MAAM,CAAC;AAAA,CACf;AAED;;GAEG;AACH,SAAS,aAAa,CAAC,KAAa,EAAU;IAC5C,MAAM,IAAI,GAAG,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC,WAAW,EAAE,CAAC,CAAC;IAEjE,IAAI,IAAI,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACtB,OAAO,SAAS,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,IAAI,IAAI,CAAC,CAAC,CAAC,CAAC;IACvC,CAAC;IAED,oCAAoC;IACpC,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,eAAe,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC;IAEvD,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACvB,OAAO,GAAG,KAAK,CAAC,CAAC,CAAC,QAAQ,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC;IACvC,CAAC;IAED,OAAO,GAAG,KAAK,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,SAAS,KAAK,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC,EAAE,CAAC;AAAA,CAC3E;AAED;;GAEG;AACH,SAAS,UAAU,CAAC,IAAc,EAAW;IAC3C,MAAM,QAAQ,GAAG,IAAI,GAAG,CAAC,CAAC,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,CAAC,CAAC,CAAC;IACzD,IAAI,IAAI,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,KAAK,CAAC;IACpC,OAAO,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,WAAW,EAAE,CAAC,CAAC,CAAC;AAAA,CACzD;AAED;;GAEG;AACH,SAAS,YAAY,CAAC,KAAa,EAAU;IAC3C,MAAM,KAAK,GAAG;QACZ,EAAE;QACF,SAAS;QACT,UAAU;QACV,OAAO;QACP,OAAO;QACP,KAAK;QACL,MAAM;QACN,MAAM;QACN,QAAQ;QACR,WAAW;QACX,SAAS;QACT,UAAU;QACV,UAAU;KACX,CAAC;IACF,OAAO,KAAK,CAAC,KAAK,CAAC,IAAI,MAAM,CAAC,KAAK,CAAC,CAAC;AAAA,CACtC"}
@@ -0,0 +1,62 @@
1
+ import type { DocHandle } from "@automerge/automerge-repo";
2
+ import type { CatalogDocument } from "@todu/core";
3
+ /**
4
+ * A schedulable item from the catalog — either a recurring template or a habit.
5
+ * Both share these fields that the framework needs to check.
6
+ */
7
+ export interface SchedulableItem {
8
+ id: string;
9
+ nextDue: string;
10
+ timezone: string;
11
+ paused: boolean;
12
+ endDate?: string;
13
+ }
14
+ /**
15
+ * Context passed to template processors during processTemplates().
16
+ * Processors determine "today" per-item using todayInTimezone()
17
+ * with each item's configured timezone.
18
+ */
19
+ export interface ProcessingContext {
20
+ /** The catalog document handle for reading/writing */
21
+ catalog: DocHandle<CatalogDocument>;
22
+ }
23
+ /**
24
+ * A handler that processes due items of a specific type.
25
+ * Registered by recurring templates and habits modules.
26
+ *
27
+ * @param context - Processing context with catalog access
28
+ * @returns Number of items processed
29
+ */
30
+ export type TemplateProcessor = (context: ProcessingContext) => Promise<number>;
31
+ /**
32
+ * Register a template processor.
33
+ * Called by recurring.ts and habits.ts to register their processing logic.
34
+ *
35
+ * @param type - Processor type identifier (e.g., "recurring", "habit")
36
+ * @param processor - The processing function
37
+ */
38
+ export declare function registerProcessor(type: string, processor: TemplateProcessor): void;
39
+ /**
40
+ * Clear all registered processors.
41
+ * Used in tests to reset state between runs.
42
+ */
43
+ export declare function clearProcessors(): void;
44
+ /**
45
+ * Get all registered processor types.
46
+ * Used in tests to verify registration.
47
+ */
48
+ export declare function getRegisteredProcessors(): string[];
49
+ /**
50
+ * Process all due templates and habits.
51
+ *
52
+ * Called during createTodu() initialization. Runs each registered
53
+ * processor in sequence. Each processor is responsible for:
54
+ * 1. Reading its items from the catalog
55
+ * 2. Checking which are due (nextDue <= today, not paused)
56
+ * 3. Performing the appropriate action (generate tasks, advance nextDue, etc.)
57
+ *
58
+ * This function is the single entry point — no daemon, no polling,
59
+ * no on-complete triggers. Just process on access.
60
+ */
61
+ export declare function processTemplates(catalog: DocHandle<CatalogDocument>): Promise<void>;
62
+ //# sourceMappingURL=scheduling.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"scheduling.d.ts","sourceRoot":"","sources":["../src/scheduling.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,2BAA2B,CAAC;AAC3D,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAMlD;;;GAGG;AACH,MAAM,WAAW,eAAe;IAC9B,EAAE,EAAE,MAAM,CAAC;IACX,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,MAAM,CAAC;IACjB,MAAM,EAAE,OAAO,CAAC;IAChB,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED;;;;GAIG;AACH,MAAM,WAAW,iBAAiB;IAChC,sDAAsD;IACtD,OAAO,EAAE,SAAS,CAAC,eAAe,CAAC,CAAC;CACrC;AAED;;;;;;GAMG;AACH,MAAM,MAAM,iBAAiB,GAAG,CAAC,OAAO,EAAE,iBAAiB,KAAK,OAAO,CAAC,MAAM,CAAC,CAAC;AAQhF;;;;;;GAMG;AACH,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,MAAM,EAAE,SAAS,EAAE,iBAAiB,GAAG,IAAI,CAElF;AAED;;;GAGG;AACH,wBAAgB,eAAe,IAAI,IAAI,CAEtC;AAED;;;GAGG;AACH,wBAAgB,uBAAuB,IAAI,MAAM,EAAE,CAElD;AAED;;;;;;;;;;;GAWG;AACH,wBAAsB,gBAAgB,CAAC,OAAO,EAAE,SAAS,CAAC,eAAe,CAAC,GAAG,OAAO,CAAC,IAAI,CAAC,CAiBzF"}
@@ -0,0 +1,58 @@
1
+ /**
2
+ * Registry of template processors.
3
+ * Each processor handles a specific type of schedulable item.
4
+ */
5
+ const processors = new Map();
6
+ /**
7
+ * Register a template processor.
8
+ * Called by recurring.ts and habits.ts to register their processing logic.
9
+ *
10
+ * @param type - Processor type identifier (e.g., "recurring", "habit")
11
+ * @param processor - The processing function
12
+ */
13
+ export function registerProcessor(type, processor) {
14
+ processors.set(type, processor);
15
+ }
16
+ /**
17
+ * Clear all registered processors.
18
+ * Used in tests to reset state between runs.
19
+ */
20
+ export function clearProcessors() {
21
+ processors.clear();
22
+ }
23
+ /**
24
+ * Get all registered processor types.
25
+ * Used in tests to verify registration.
26
+ */
27
+ export function getRegisteredProcessors() {
28
+ return Array.from(processors.keys());
29
+ }
30
+ /**
31
+ * Process all due templates and habits.
32
+ *
33
+ * Called during createTodu() initialization. Runs each registered
34
+ * processor in sequence. Each processor is responsible for:
35
+ * 1. Reading its items from the catalog
36
+ * 2. Checking which are due (nextDue <= today, not paused)
37
+ * 3. Performing the appropriate action (generate tasks, advance nextDue, etc.)
38
+ *
39
+ * This function is the single entry point — no daemon, no polling,
40
+ * no on-complete triggers. Just process on access.
41
+ */
42
+ export async function processTemplates(catalog) {
43
+ if (processors.size === 0)
44
+ return;
45
+ for (const [type, processor] of processors) {
46
+ try {
47
+ const context = {
48
+ catalog,
49
+ };
50
+ await processor(context);
51
+ }
52
+ catch (e) {
53
+ // Log but don't fail — one processor failing shouldn't block others
54
+ console.error(`[scheduling] processor "${type}" failed:`, e instanceof Error ? e.message : String(e));
55
+ }
56
+ }
57
+ }
58
+ //# sourceMappingURL=scheduling.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"scheduling.js","sourceRoot":"","sources":["../src/scheduling.ts"],"names":[],"mappings":"AAsCA;;;GAGG;AACH,MAAM,UAAU,GAAmC,IAAI,GAAG,EAAE,CAAC;AAE7D;;;;;;GAMG;AACH,MAAM,UAAU,iBAAiB,CAAC,IAAY,EAAE,SAA4B,EAAQ;IAClF,UAAU,CAAC,GAAG,CAAC,IAAI,EAAE,SAAS,CAAC,CAAC;AAAA,CACjC;AAED;;;GAGG;AACH,MAAM,UAAU,eAAe,GAAS;IACtC,UAAU,CAAC,KAAK,EAAE,CAAC;AAAA,CACpB;AAED;;;GAGG;AACH,MAAM,UAAU,uBAAuB,GAAa;IAClD,OAAO,KAAK,CAAC,IAAI,CAAC,UAAU,CAAC,IAAI,EAAE,CAAC,CAAC;AAAA,CACtC;AAED;;;;;;;;;;;GAWG;AACH,MAAM,CAAC,KAAK,UAAU,gBAAgB,CAAC,OAAmC,EAAiB;IACzF,IAAI,UAAU,CAAC,IAAI,KAAK,CAAC;QAAE,OAAO;IAElC,KAAK,MAAM,CAAC,IAAI,EAAE,SAAS,CAAC,IAAI,UAAU,EAAE,CAAC;QAC3C,IAAI,CAAC;YACH,MAAM,OAAO,GAAsB;gBACjC,OAAO;aACR,CAAC;YACF,MAAM,SAAS,CAAC,OAAO,CAAC,CAAC;QAC3B,CAAC;QAAC,OAAO,CAAC,EAAE,CAAC;YACX,sEAAoE;YACpE,OAAO,CAAC,KAAK,CACX,2BAA2B,IAAI,WAAW,EAC1C,CAAC,YAAY,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,CAC3C,CAAC;QACJ,CAAC;IACH,CAAC;AAAA,CACF"}
@@ -0,0 +1,34 @@
1
+ import type { DocHandle } from "@automerge/automerge-repo";
2
+ import { Repo } from "@automerge/automerge-repo";
3
+ import { type CatalogDocument } from "@todu/core";
4
+ export interface Storage {
5
+ /** The Automerge repo instance */
6
+ repo: Repo;
7
+ /** The catalog document handle */
8
+ catalog: DocHandle<CatalogDocument>;
9
+ /** Whether this storage is ephemeral (in-memory, no persistence) */
10
+ ephemeral: boolean;
11
+ /** Shut down the repo */
12
+ close(): Promise<void>;
13
+ }
14
+ /**
15
+ * Initialize storage: create data directory, set up Automerge repo,
16
+ * and load or create the catalog document.
17
+ */
18
+ export declare function initStorage(storagePath: string): Promise<Storage>;
19
+ /**
20
+ * Initialize ephemeral storage with no filesystem persistence.
21
+ * Used by CLI when syncing with a running Electron instance.
22
+ *
23
+ * Creates an in-memory Automerge repo and reads the catalog document ID
24
+ * from the marker file (written by the persistent owner).
25
+ *
26
+ * IMPORTANT: The caller must connect a sync adapter to the repo BEFORE
27
+ * calling `findCatalog()`. The ephemeral repo has no local data — it
28
+ * needs a sync peer to provide the document contents.
29
+ */
30
+ export declare function initEphemeralStorage(storagePath: string): Promise<Omit<Storage, "catalog"> & {
31
+ /** Find the catalog document via sync. Call AFTER connecting a sync adapter. */
32
+ findCatalog(): Promise<Storage>;
33
+ }>;
34
+ //# sourceMappingURL=storage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"storage.d.ts","sourceRoot":"","sources":["../src/storage.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,SAAS,EAAc,MAAM,2BAA2B,CAAC;AACvE,OAAO,EAAE,IAAI,EAAE,MAAM,2BAA2B,CAAC;AAEjD,OAAO,EAEL,KAAK,eAAe,EAGrB,MAAM,YAAY,CAAC;AAwCpB,MAAM,WAAW,OAAO;IACtB,kCAAkC;IAClC,IAAI,EAAE,IAAI,CAAC;IAEX,kCAAkC;IAClC,OAAO,EAAE,SAAS,CAAC,eAAe,CAAC,CAAC;IAEpC,oEAAoE;IACpE,SAAS,EAAE,OAAO,CAAC;IAEnB,yBAAyB;IACzB,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC,CAAC;CACxB;AAED;;;GAGG;AACH,wBAAsB,WAAW,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAqBvE;AAED;;;;;;;;;;GAUG;AACH,wBAAsB,oBAAoB,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CACtE,IAAI,CAAC,OAAO,EAAE,SAAS,CAAC,GAAG;IACzB,gFAAgF;IAChF,WAAW,IAAI,OAAO,CAAC,OAAO,CAAC,CAAC;CACjC,CACF,CAwDA"}