@blazeo.com/appointment-client 1.0.6 → 1.0.8

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 (62) hide show
  1. package/Appointment-Client/.gitattributes +2 -0
  2. package/blazeo.com-appointment-client-1.0.8.tgz +0 -0
  3. package/dist/calendar/buildUnifiedCalendarView.d.ts +8 -0
  4. package/dist/calendar/buildUnifiedCalendarView.js +29 -8
  5. package/dist/calendar/fetchCalendarDetails.d.ts +8 -40
  6. package/dist/calendar/fetchCalendarDetails.js +117 -47
  7. package/dist/calendar/fetchCalendarWithOpeningHours.d.ts +1 -10
  8. package/dist/calendar/fetchCalendarWithOpeningHours.js +34 -15
  9. package/dist/calendar/getAllParticipantOpeningHours.d.ts +4 -1
  10. package/dist/calendar/getAllParticipantOpeningHours.js +6 -1
  11. package/dist/calendar/getOpeningHours.d.ts +4 -1
  12. package/dist/calendar/getOpeningHours.js +2 -2
  13. package/dist/calendar/getParticipantOpeningHours.js +9 -4
  14. package/dist/calendar/getParticipants.d.ts +4 -1
  15. package/dist/calendar/getParticipants.js +6 -1
  16. package/dist/calendar/mapToDesiredResponse.d.ts +70 -0
  17. package/dist/calendar/mapToDesiredResponse.js +99 -0
  18. package/dist/config/applyBlazeoDefaults.js +3 -2
  19. package/dist/config/blazeoClientDefaults.js +2 -2
  20. package/dist/config/ensureBlazeoHttpReady.d.ts +17 -0
  21. package/dist/config/ensureBlazeoHttpReady.js +31 -0
  22. package/dist/config/initializeAppointmentClient.d.ts +4 -0
  23. package/dist/config/initializeAppointmentClient.js +9 -3
  24. package/dist/config/syncBlazeoConnection.d.ts +6 -0
  25. package/dist/config/syncBlazeoConnection.js +18 -0
  26. package/dist/index.d.ts +4 -1
  27. package/dist/index.js +3 -1
  28. package/package.json +1 -1
  29. package/sample/.env.example +5 -0
  30. package/sample/package-lock.json +70 -1
  31. package/sample/package.json +1 -0
  32. package/sample/src/AllParticipantOpeningHoursTab.jsx +13 -4
  33. package/sample/src/App2.jsx +22 -2
  34. package/sample/src/AvailabilityTab.jsx +8 -3
  35. package/sample/src/BlazeoConnectionSettings.jsx +16 -15
  36. package/sample/src/CreateCalendarTab.jsx +23 -6
  37. package/sample/src/EventTab.jsx +31 -8
  38. package/sample/src/FetchCalendarTab.jsx +94 -70
  39. package/sample/src/OpeningHoursTab.jsx +13 -4
  40. package/sample/src/ParticipantInfoTab.jsx +8 -3
  41. package/sample/src/ParticipantOpeningHoursTab.jsx +17 -7
  42. package/sample/src/ParticipantTab.jsx +13 -4
  43. package/sample/src/blazeoBootstrap.js +30 -0
  44. package/sample/src/blazeoDemoError.js +14 -0
  45. package/sample/src/blazeoPushConnection.js +23 -0
  46. package/sample/src/main.jsx +3 -3
  47. package/sample/vite.config.js +19 -5
  48. package/src/calendar/buildUnifiedCalendarView.ts +35 -7
  49. package/src/calendar/fetchCalendarDetails.ts +318 -226
  50. package/src/calendar/fetchCalendarWithOpeningHours.ts +130 -99
  51. package/src/calendar/getAllParticipantOpeningHours.ts +9 -1
  52. package/src/calendar/getOpeningHours.ts +2 -2
  53. package/src/calendar/getParticipantOpeningHours.ts +14 -5
  54. package/src/calendar/getParticipants.ts +9 -1
  55. package/src/calendar/mapToDesiredResponse.ts +104 -0
  56. package/src/config/applyBlazeoDefaults.ts +3 -2
  57. package/src/config/blazeoClientDefaults.ts +2 -2
  58. package/src/config/ensureBlazeoHttpReady.ts +41 -0
  59. package/src/config/initializeAppointmentClient.ts +9 -3
  60. package/src/config/syncBlazeoConnection.ts +19 -0
  61. package/src/index.ts +7 -1
  62. package/blazeo.com-appointment-client-1.0.6.tgz +0 -0
@@ -0,0 +1,14 @@
1
+ /**
2
+ * Maps low-level Blazeo / calendar-client errors to actionable copy for this sample.
3
+ */
4
+ export function mapBlazeoDemoError(message) {
5
+ const m = String(message ?? "");
6
+ if (
7
+ /Model env requires baseUrl|requires baseUrl\. Call configure|baseUrl is missing|Blazeo base URL is not set/i.test(
8
+ m
9
+ )
10
+ ) {
11
+ return "Blazeo Base URL is not set for API calls. Enter **Base URL** (and optional Consumer) in the **Blazeo connection** card at the top of this page, or set `blazeoClientConfig` / `VITE_BLAZEO_BASE_URL`.";
12
+ }
13
+ return m;
14
+ }
@@ -0,0 +1,23 @@
1
+ import { ensureBlazeoHttpReady, initializeAppointmentClient } from "appointment-client";
2
+ import { configure } from "@blazeo.com/calendar-client";
3
+
4
+ function normalizeBase(u) {
5
+ const t = (u ?? "").trim();
6
+ if (!t) return "";
7
+ return t.replace(/\/+$/, "");
8
+ }
9
+
10
+ /**
11
+ * Applies Base URL from the connection card. With Vite `resolve.alias` pointing
12
+ * `@blazeo.com/calendar-client` at one file, `configure` here matches `CalendarModel`'s store.
13
+ * `initializeAppointmentClient` + `ensureBlazeoHttpReady` keep `appointment-client` helpers aligned.
14
+ */
15
+ export function pushBlazeoConnection(effective) {
16
+ const baseUrl = normalizeBase(effective?.baseUrl ?? "");
17
+ if (!baseUrl) return;
18
+ const consumer = (effective?.consumer ?? "").trim() || undefined;
19
+ const cfg = { baseUrl, ...(consumer ? { consumer } : {}) };
20
+ initializeAppointmentClient(cfg);
21
+ configure(cfg);
22
+ ensureBlazeoHttpReady(cfg);
23
+ }
@@ -1,11 +1,11 @@
1
- import { applyBlazeoClientConfig } from "appointment-client";
2
1
  import { StrictMode } from "react";
3
2
  import { createRoot } from "react-dom/client";
4
3
  import { App } from "./App2.jsx";
4
+ import { bootstrapBlazeoClient } from "./blazeoBootstrap.js";
5
5
  import "./style.css";
6
6
 
7
- /** Apply file defaults (`blazeoClientDefaults.ts`) before React mounts. */
8
- applyBlazeoClientConfig();
7
+ /** Blazeo: `blazeoClientDefaults.ts` + optional `VITE_BLAZEO_*` (.env) `configure()` for calendar-client. */
8
+ bootstrapBlazeoClient();
9
9
 
10
10
  const rootEl = document.getElementById("app");
11
11
  if (!rootEl) {
@@ -1,10 +1,23 @@
1
1
  import react from "@vitejs/plugin-react";
2
2
  import { defineConfig, loadEnv } from "vite";
3
3
  import path from "path";
4
+ import fs from "fs";
4
5
  import { fileURLToPath } from "url";
5
6
 
6
7
  const __dirname = path.dirname(fileURLToPath(import.meta.url));
7
8
 
9
+ /** Single physical entry for `@blazeo.com/calendar-client` (hoisted or nested under `file:..` parent). */
10
+ function calendarClientEntry() {
11
+ const candidates = [
12
+ path.resolve(__dirname, "node_modules/@blazeo.com/calendar-client/dist/index.mjs"),
13
+ path.resolve(__dirname, "../node_modules/@blazeo.com/calendar-client/dist/index.mjs"),
14
+ ];
15
+ for (const p of candidates) {
16
+ if (fs.existsSync(p)) return p;
17
+ }
18
+ return candidates[0];
19
+ }
20
+
8
21
  export default defineConfig(({ mode }) => {
9
22
  const env = loadEnv(mode, path.resolve(__dirname, "."), "");
10
23
  const proxyTarget = (env.VITE_DEV_PROXY_TARGET ?? "").trim().replace(/\/+$/, "");
@@ -26,13 +39,14 @@ export default defineConfig(({ mode }) => {
26
39
  plugins: [react()],
27
40
  /** Ensure one instance so `configure()` and models share the same store. */
28
41
  resolve: {
29
- preserveSymlinks: true,
42
+ // `file:..` appointment-client is symlinked; `true` can resolve the same dep twice → two `getConfig()` stores.
43
+ preserveSymlinks: false,
30
44
  dedupe: ["@blazeo.com/calendar-client", "mobx", "mobx-state-tree"],
31
45
  alias: {
32
- "@blazeo.com/calendar-client": path.resolve(
33
- __dirname,
34
- "../node_modules/@blazeo.com/calendar-client/dist/index.mjs"
35
- ),
46
+ // Ensure Vite/Rollup can always resolve the local workspace package.
47
+ // (Avoids `Failed to resolve import "appointment-client"` during dev/build.)
48
+ "appointment-client": path.resolve(__dirname, "../dist/index.js"),
49
+ "@blazeo.com/calendar-client": calendarClientEntry(),
36
50
  },
37
51
  },
38
52
  optimizeDeps: {
@@ -37,14 +37,19 @@ function coerceMemberId(v: unknown): number | string | null {
37
37
  * Canonical member id used in both `members[].id` and `openingHours[].member`.
38
38
  */
39
39
  function resolveParticipantMemberId(calPart: Record<string, any>): number | string {
40
- const n = pick<number | null>(calPart, "id", "Id");
41
- if (n != null && typeof n === "number" && !Number.isNaN(n)) return n;
40
+ // Prefer the participantId GUID when available — it is the stable cross-endpoint identifier.
42
41
  const sid = pick<string>(calPart, "participantId", "ParticipantId", "participant_id");
43
42
  if (sid != null && String(sid).trim() !== "") {
44
43
  const t = String(sid).trim();
45
44
  if (/^\d+$/.test(t)) return Number(t);
46
45
  return t;
47
46
  }
47
+ // Fall back to id — accepts both numeric and string (e.g. a GUID stored as id).
48
+ const n = pick<number | string | null>(calPart, "id", "Id");
49
+ if (n != null) {
50
+ if (typeof n === "number" && !Number.isNaN(n)) return n;
51
+ if (typeof n === "string" && n.trim() !== "") return n.trim();
52
+ }
48
53
  return "";
49
54
  }
50
55
 
@@ -56,6 +61,7 @@ export interface UnifiedCalendarMember {
56
61
  status: number | null;
57
62
  /** Full row from Participants/GetInfo (plain object). */
58
63
  participantInfo?: Record<string, unknown> | null;
64
+ __typename?: string;
59
65
  }
60
66
 
61
67
  export interface UnifiedParticipantWithHours extends UnifiedCalendarMember {
@@ -63,13 +69,20 @@ export interface UnifiedParticipantWithHours extends UnifiedCalendarMember {
63
69
  }
64
70
 
65
71
  export interface UnifiedOpeningHourRow {
72
+ id?: number | string;
73
+ createdOn?: string;
74
+ modifiedOn?: string;
66
75
  member: number | string;
76
+ openingHourId?: string;
77
+ calendarId?: string;
78
+ participantId?: string;
67
79
  days: string[];
68
80
  startHour: number;
69
81
  startMinute: number;
70
82
  endHour: number;
71
83
  endMinute: number;
72
84
  off: boolean;
85
+ __typename?: string;
73
86
  }
74
87
 
75
88
  function dayOrderIndex(d: string): number {
@@ -253,6 +266,7 @@ export function buildUnifiedCalendarView(
253
266
  email: email ?? null,
254
267
  status: deriveMemberStatus({}, inf),
255
268
  participantInfo: participantInfoPlain,
269
+ __typename: "Member",
256
270
  });
257
271
  }
258
272
  }
@@ -277,13 +291,20 @@ export function buildUnifiedCalendarView(
277
291
  const off = Boolean(pick(row, "off", "Off"));
278
292
 
279
293
  openingHours.push({
294
+ id: pick(row, "id", "Id") ?? 0,
295
+ createdOn: pick(row, "createdOn", "CreatedOn", "created_on") ?? "0001-01-01T00:00:00.000Z",
296
+ modifiedOn: pick(row, "modifiedOn", "ModifiedOn", "modified_on") ?? "0001-01-01T00:00:00.000Z",
280
297
  member: memberId,
298
+ openingHourId: pick(row, "openingHourId", "OpeningHourId", "opening_hour_id") ?? "",
299
+ calendarId: pick(row, "calendarId", "CalendarId", "calendar_id") ?? "",
300
+ participantId: pick(row, "participantId", "ParticipantId", "participant_id") ?? "",
281
301
  days,
282
302
  startHour,
283
303
  startMinute,
284
304
  endHour,
285
305
  endMinute,
286
306
  off,
307
+ __typename: "OpeningHour",
287
308
  });
288
309
  }
289
310
 
@@ -294,6 +315,7 @@ export function buildUnifiedCalendarView(
294
315
  members,
295
316
  openingHours,
296
317
  participants: buildNestedParticipants(members, openingHours),
318
+ __typename: "Calendar",
297
319
  } as UnifiedCalendarView;
298
320
 
299
321
  return view;
@@ -306,17 +328,23 @@ function buildNestedParticipants(
306
328
  members: UnifiedCalendarMember[],
307
329
  openingHours: UnifiedOpeningHourRow[]
308
330
  ): UnifiedParticipantWithHours[] {
309
- return members.map((m) => {
310
- const hours = openingHours.filter((oh) => {
331
+ const nested: UnifiedParticipantWithHours[] = [];
332
+ members.forEach((m) => {
333
+ const hoursForThisMember = openingHours.filter((oh) => {
311
334
  const mid = String(oh.member).trim().toLowerCase();
312
335
  const pid = String(m.id).trim().toLowerCase();
313
336
  return mid === pid;
314
337
  });
315
338
  // Remove the 'member' field from the nested opening hours as it's redundant.
316
- const nestedHours = hours.map(({ member, ...rest }) => rest as any);
317
- return {
339
+ const nestedHours = hoursForThisMember.map(({ member, ...rest }) => ({
340
+ ...rest,
341
+ __typename: "OpeningHour"
342
+ }));
343
+ nested.push({
318
344
  ...m,
319
345
  openingHours: nestedHours,
320
- };
346
+ __typename: "Member",
347
+ } as UnifiedParticipantWithHours);
321
348
  });
349
+ return nested;
322
350
  }