@guayaba/workflow-piece-google-calendar 0.9.1
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.
- package/.babelrc +3 -0
- package/.eslintrc.json +18 -0
- package/README.md +5 -0
- package/assets/logo.png +0 -0
- package/package.json +23 -0
- package/src/i18n/ca.json +71 -0
- package/src/i18n/de.json +151 -0
- package/src/i18n/es.json +151 -0
- package/src/i18n/fr.json +151 -0
- package/src/i18n/hi.json +71 -0
- package/src/i18n/id.json +71 -0
- package/src/i18n/ja.json +151 -0
- package/src/i18n/nl.json +151 -0
- package/src/i18n/pt.json +151 -0
- package/src/i18n/ru.json +71 -0
- package/src/i18n/translation.json +151 -0
- package/src/i18n/vi.json +71 -0
- package/src/i18n/zh.json +151 -0
- package/src/index.ts +78 -0
- package/src/lib/actions/add-attendees.action.ts +52 -0
- package/src/lib/actions/add-calendar-to-calendarlist.ts +33 -0
- package/src/lib/actions/create-event.ts +163 -0
- package/src/lib/actions/create-quick-event.ts +66 -0
- package/src/lib/actions/delete-event.action.ts +32 -0
- package/src/lib/actions/find-busy-free-periods.ts +97 -0
- package/src/lib/actions/get-event-by-id.ts +123 -0
- package/src/lib/actions/get-events.ts +111 -0
- package/src/lib/actions/update-event.action.ts +126 -0
- package/src/lib/auth.ts +81 -0
- package/src/lib/common/helper.ts +228 -0
- package/src/lib/common/index.ts +95 -0
- package/src/lib/common/types.ts +246 -0
- package/src/lib/google-calendar.mdx +25 -0
- package/src/lib/triggers/calendar-event.ts +139 -0
- package/src/lib/triggers/event-cancelled.ts +200 -0
- package/src/lib/triggers/event-ends.ts +201 -0
- package/src/lib/triggers/event-start-time-before.ts +201 -0
- package/src/lib/triggers/new-calendar.ts +203 -0
- package/src/lib/triggers/new-event-matching-search.ts +225 -0
- package/src/lib/triggers/new-event.ts +184 -0
- package/tsconfig.json +16 -0
- package/tsconfig.lib.json +15 -0
|
@@ -0,0 +1,126 @@
|
|
|
1
|
+
import { Property, createAction } from '@guayaba/workflows-framework';
|
|
2
|
+
import { google, calendar_v3 } from 'googleapis';
|
|
3
|
+
import { googleCalendarCommon, googleCalendarAuth, createGoogleClient } from '../common';
|
|
4
|
+
import dayjs from 'dayjs';
|
|
5
|
+
|
|
6
|
+
export const updateEventAction = createAction({
|
|
7
|
+
displayName: 'Update Event',
|
|
8
|
+
auth: googleCalendarAuth,
|
|
9
|
+
name: 'update_event',
|
|
10
|
+
description: 'Updates an event in Google Calendar.',
|
|
11
|
+
props: {
|
|
12
|
+
calendar_id: googleCalendarCommon.calendarDropdown('writer'),
|
|
13
|
+
eventId: Property.ShortText({
|
|
14
|
+
displayName: 'Event ID',
|
|
15
|
+
required: true,
|
|
16
|
+
}),
|
|
17
|
+
title: Property.ShortText({
|
|
18
|
+
displayName: 'Title of the event',
|
|
19
|
+
required: false,
|
|
20
|
+
}),
|
|
21
|
+
start_date_time: Property.DateTime({
|
|
22
|
+
displayName: 'Start date time of the event',
|
|
23
|
+
required: false,
|
|
24
|
+
}),
|
|
25
|
+
end_date_time: Property.DateTime({
|
|
26
|
+
displayName: 'End date time of the event',
|
|
27
|
+
required: false,
|
|
28
|
+
}),
|
|
29
|
+
location: Property.ShortText({
|
|
30
|
+
displayName: 'Location',
|
|
31
|
+
required: false,
|
|
32
|
+
}),
|
|
33
|
+
description: Property.LongText({
|
|
34
|
+
displayName: 'Description',
|
|
35
|
+
description: 'Description of the event. You can use HTML tags here.',
|
|
36
|
+
required: false,
|
|
37
|
+
}),
|
|
38
|
+
colorId: googleCalendarCommon.colorId,
|
|
39
|
+
attendees: Property.Array({
|
|
40
|
+
displayName: 'Attendees',
|
|
41
|
+
description: 'Emails of the attendees (guests)',
|
|
42
|
+
required: false,
|
|
43
|
+
}),
|
|
44
|
+
guests_can_modify: Property.Checkbox({
|
|
45
|
+
displayName: 'Guests can modify',
|
|
46
|
+
defaultValue: false,
|
|
47
|
+
required: false,
|
|
48
|
+
}),
|
|
49
|
+
guests_can_invite_others: Property.Checkbox({
|
|
50
|
+
displayName: 'Guests can invite others',
|
|
51
|
+
defaultValue: false,
|
|
52
|
+
required: false,
|
|
53
|
+
}),
|
|
54
|
+
guests_can_see_other_guests: Property.Checkbox({
|
|
55
|
+
displayName: 'Guests can see other guests',
|
|
56
|
+
defaultValue: false,
|
|
57
|
+
required: false,
|
|
58
|
+
}),
|
|
59
|
+
},
|
|
60
|
+
async run(context) {
|
|
61
|
+
const {
|
|
62
|
+
calendar_id,
|
|
63
|
+
eventId,
|
|
64
|
+
title,
|
|
65
|
+
start_date_time,
|
|
66
|
+
end_date_time,
|
|
67
|
+
location,
|
|
68
|
+
description,
|
|
69
|
+
colorId,
|
|
70
|
+
guests_can_invite_others,
|
|
71
|
+
guests_can_modify,
|
|
72
|
+
guests_can_see_other_guests,
|
|
73
|
+
} = context.propsValue;
|
|
74
|
+
|
|
75
|
+
const attendees = context.propsValue.attendees as string[];
|
|
76
|
+
|
|
77
|
+
const authClient = await createGoogleClient(context.auth);
|
|
78
|
+
const calendar = google.calendar({ version: 'v3', auth: authClient });
|
|
79
|
+
|
|
80
|
+
// Note that each patch request consumes three quota units;
|
|
81
|
+
// prefer using a get followed by an update
|
|
82
|
+
const currentEvent = await calendar.events.get({
|
|
83
|
+
calendarId: calendar_id,
|
|
84
|
+
eventId: eventId,
|
|
85
|
+
});
|
|
86
|
+
|
|
87
|
+
let attendeeFormattedList: calendar_v3.Schema$EventAttendee[] = [];
|
|
88
|
+
if (Array.isArray(attendees) && attendees.length > 0) {
|
|
89
|
+
attendeeFormattedList = attendees.map((email) => ({ email }));
|
|
90
|
+
} else if (
|
|
91
|
+
currentEvent.data.attendees &&
|
|
92
|
+
Array.isArray(currentEvent.data.attendees)
|
|
93
|
+
) {
|
|
94
|
+
attendeeFormattedList = currentEvent.data.attendees;
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
const response = await calendar.events.update({
|
|
98
|
+
calendarId: calendar_id,
|
|
99
|
+
eventId: eventId,
|
|
100
|
+
requestBody: {
|
|
101
|
+
summary: title ?? currentEvent.data.summary,
|
|
102
|
+
attendees: attendeeFormattedList,
|
|
103
|
+
description: description ?? currentEvent.data.description,
|
|
104
|
+
colorId: colorId,
|
|
105
|
+
location: location ?? currentEvent.data.location,
|
|
106
|
+
start: start_date_time
|
|
107
|
+
? {
|
|
108
|
+
dateTime: dayjs(start_date_time).format(
|
|
109
|
+
'YYYY-MM-DDTHH:mm:ss.sssZ'
|
|
110
|
+
),
|
|
111
|
+
}
|
|
112
|
+
: currentEvent.data.start,
|
|
113
|
+
end: end_date_time
|
|
114
|
+
? {
|
|
115
|
+
dateTime: dayjs(end_date_time).format('YYYY-MM-DDTHH:mm:ss.sssZ'),
|
|
116
|
+
}
|
|
117
|
+
: currentEvent.data.end,
|
|
118
|
+
guestsCanInviteOthers: guests_can_invite_others,
|
|
119
|
+
guestsCanModify: guests_can_modify,
|
|
120
|
+
guestsCanSeeOtherGuests: guests_can_see_other_guests,
|
|
121
|
+
},
|
|
122
|
+
});
|
|
123
|
+
|
|
124
|
+
return response.data;
|
|
125
|
+
},
|
|
126
|
+
});
|
package/src/lib/auth.ts
ADDED
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
import { AppConnectionValueForAuthProperty, PieceAuth, Property } from '@guayaba/workflows-framework';
|
|
2
|
+
import { AppConnectionType } from '@guayaba/workflows-shared';
|
|
3
|
+
import { google } from 'googleapis';
|
|
4
|
+
import { OAuth2Client } from 'googleapis-common';
|
|
5
|
+
|
|
6
|
+
export const googleCalendarScopes = [
|
|
7
|
+
'https://www.googleapis.com/auth/calendar.events',
|
|
8
|
+
'https://www.googleapis.com/auth/calendar.readonly',
|
|
9
|
+
// TODO: Add the scope after Google App Verification
|
|
10
|
+
// 'https://www.googleapis.com/auth/calendar.calendarlist'
|
|
11
|
+
];
|
|
12
|
+
|
|
13
|
+
export const googleCalendarAuth = [PieceAuth.OAuth2({
|
|
14
|
+
description: '',
|
|
15
|
+
authUrl: 'https://accounts.google.com/o/oauth2/auth',
|
|
16
|
+
tokenUrl: 'https://oauth2.googleapis.com/token',
|
|
17
|
+
required: true,
|
|
18
|
+
pkce: true,
|
|
19
|
+
scope: googleCalendarScopes,
|
|
20
|
+
}), PieceAuth.CustomAuth({
|
|
21
|
+
displayName: 'Service Account (Advanced)',
|
|
22
|
+
description: 'Authenticate via service account from https://console.cloud.google.com/ > IAM & Admin > Service Accounts > Create Service Account > Keys > Add key. <br> <br> You can optionally use domain-wide delegation (https://support.google.com/a/answer/162106?hl=en#zippy=%2Cset-up-domain-wide-delegation-for-a-client) to access calendars without adding the service account to each one. <br> <br> **Note:** Without a user email, the service account only has access to calendars you explicitly share with it.',
|
|
23
|
+
required: true,
|
|
24
|
+
props: {
|
|
25
|
+
serviceAccount: Property.ShortText({
|
|
26
|
+
displayName: 'Service Account JSON Key',
|
|
27
|
+
required: true,
|
|
28
|
+
}),
|
|
29
|
+
userEmail: Property.ShortText({
|
|
30
|
+
displayName: 'User Email',
|
|
31
|
+
required: false,
|
|
32
|
+
description: 'Email address of the user to impersonate for domain-wide delegation.',
|
|
33
|
+
}),
|
|
34
|
+
},
|
|
35
|
+
validate: async ({ auth }) => {
|
|
36
|
+
try {
|
|
37
|
+
await getAccessToken({
|
|
38
|
+
type: AppConnectionType.CUSTOM_AUTH,
|
|
39
|
+
props: { ...auth },
|
|
40
|
+
});
|
|
41
|
+
} catch (e) {
|
|
42
|
+
return {
|
|
43
|
+
valid: false,
|
|
44
|
+
error: (e as Error).message,
|
|
45
|
+
};
|
|
46
|
+
}
|
|
47
|
+
return {
|
|
48
|
+
valid: true,
|
|
49
|
+
};
|
|
50
|
+
},
|
|
51
|
+
})];
|
|
52
|
+
|
|
53
|
+
export type GoogleCalendarAuthValue = AppConnectionValueForAuthProperty<typeof googleCalendarAuth>;
|
|
54
|
+
|
|
55
|
+
export async function createGoogleClient(auth: GoogleCalendarAuthValue): Promise<OAuth2Client> {
|
|
56
|
+
if (auth.type === AppConnectionType.CUSTOM_AUTH) {
|
|
57
|
+
const serviceAccount = JSON.parse(auth.props.serviceAccount);
|
|
58
|
+
return new google.auth.JWT({
|
|
59
|
+
email: serviceAccount.client_email,
|
|
60
|
+
key: serviceAccount.private_key,
|
|
61
|
+
scopes: googleCalendarScopes,
|
|
62
|
+
subject: auth.props.userEmail,
|
|
63
|
+
});
|
|
64
|
+
}
|
|
65
|
+
const authClient = new OAuth2Client();
|
|
66
|
+
authClient.setCredentials(auth);
|
|
67
|
+
return authClient;
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
export const getAccessToken = async (auth: GoogleCalendarAuthValue): Promise<string> => {
|
|
71
|
+
if (auth.type === AppConnectionType.CUSTOM_AUTH) {
|
|
72
|
+
const googleClient = await createGoogleClient(auth);
|
|
73
|
+
const response = await googleClient.getAccessToken();
|
|
74
|
+
if (response.token) {
|
|
75
|
+
return response.token;
|
|
76
|
+
} else {
|
|
77
|
+
throw new Error('Could not retrieve access token from service account json');
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
return auth.access_token;
|
|
81
|
+
};
|
|
@@ -0,0 +1,228 @@
|
|
|
1
|
+
import {
|
|
2
|
+
AuthenticationType,
|
|
3
|
+
httpClient,
|
|
4
|
+
HttpMethod,
|
|
5
|
+
HttpRequest,
|
|
6
|
+
} from '@guayaba/workflows-common';
|
|
7
|
+
import { randomUUID } from 'crypto';
|
|
8
|
+
import { googleCalendarCommon, GoogleCalendarAuthValue, getAccessToken } from '.';
|
|
9
|
+
import {
|
|
10
|
+
GoogleWatchResponse,
|
|
11
|
+
GoogleWatchType,
|
|
12
|
+
CalendarObject,
|
|
13
|
+
CalendarList,
|
|
14
|
+
GoogleCalendarEvent,
|
|
15
|
+
GoogleCalendarEventList,
|
|
16
|
+
GetColorsResponse,
|
|
17
|
+
} from './types';
|
|
18
|
+
|
|
19
|
+
export async function stopWatchEvent(
|
|
20
|
+
body: GoogleWatchResponse,
|
|
21
|
+
authProp: GoogleCalendarAuthValue
|
|
22
|
+
) {
|
|
23
|
+
const request: HttpRequest = {
|
|
24
|
+
method: HttpMethod.POST,
|
|
25
|
+
url: `${googleCalendarCommon.baseUrl}/channels/stop`,
|
|
26
|
+
body: {
|
|
27
|
+
id: body?.id,
|
|
28
|
+
resourceId: body?.resourceId,
|
|
29
|
+
},
|
|
30
|
+
authentication: {
|
|
31
|
+
type: AuthenticationType.BEARER_TOKEN,
|
|
32
|
+
token: await getAccessToken(authProp),
|
|
33
|
+
},
|
|
34
|
+
};
|
|
35
|
+
await httpClient.sendRequest<any>(request);
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
export async function watchEvent(
|
|
39
|
+
calendarId: string,
|
|
40
|
+
webhookUrl: string,
|
|
41
|
+
authProp: GoogleCalendarAuthValue
|
|
42
|
+
): Promise<GoogleWatchResponse> {
|
|
43
|
+
const request: HttpRequest = {
|
|
44
|
+
method: HttpMethod.POST,
|
|
45
|
+
url: `${googleCalendarCommon.baseUrl}/calendars/${calendarId}/events/watch`,
|
|
46
|
+
body: {
|
|
47
|
+
id: randomUUID(),
|
|
48
|
+
type: GoogleWatchType.WEBHOOK,
|
|
49
|
+
address: webhookUrl,
|
|
50
|
+
},
|
|
51
|
+
authentication: {
|
|
52
|
+
type: AuthenticationType.BEARER_TOKEN,
|
|
53
|
+
token: await getAccessToken(authProp),
|
|
54
|
+
},
|
|
55
|
+
};
|
|
56
|
+
const { body: webhook } = await httpClient.sendRequest<GoogleWatchResponse>(
|
|
57
|
+
request
|
|
58
|
+
);
|
|
59
|
+
return webhook;
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
export async function getCalendars(
|
|
63
|
+
authProp: GoogleCalendarAuthValue,
|
|
64
|
+
minAccessRole?: 'writer'
|
|
65
|
+
): Promise<CalendarObject[]> {
|
|
66
|
+
// docs: https://developers.google.com/calendar/api/v3/reference/calendarList/list
|
|
67
|
+
const queryParams: Record<string, string> = {
|
|
68
|
+
showDeleted: 'false',
|
|
69
|
+
};
|
|
70
|
+
if (minAccessRole) {
|
|
71
|
+
queryParams['minAccessRole'] = minAccessRole;
|
|
72
|
+
}
|
|
73
|
+
const request: HttpRequest = {
|
|
74
|
+
method: HttpMethod.GET,
|
|
75
|
+
url: `${googleCalendarCommon.baseUrl}/users/me/calendarList`,
|
|
76
|
+
queryParams: queryParams,
|
|
77
|
+
authentication: {
|
|
78
|
+
type: AuthenticationType.BEARER_TOKEN,
|
|
79
|
+
token: await getAccessToken(authProp),
|
|
80
|
+
},
|
|
81
|
+
};
|
|
82
|
+
const response = await httpClient.sendRequest<CalendarList>(request);
|
|
83
|
+
return response.body.items;
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
export async function getColors(
|
|
87
|
+
authProp: GoogleCalendarAuthValue
|
|
88
|
+
): Promise<GetColorsResponse> {
|
|
89
|
+
const request: HttpRequest = {
|
|
90
|
+
method: HttpMethod.GET,
|
|
91
|
+
url: `${googleCalendarCommon.baseUrl}/colors`,
|
|
92
|
+
authentication: {
|
|
93
|
+
type: AuthenticationType.BEARER_TOKEN,
|
|
94
|
+
token: await getAccessToken(authProp),
|
|
95
|
+
},
|
|
96
|
+
};
|
|
97
|
+
const response = await httpClient.sendRequest<GetColorsResponse>(request);
|
|
98
|
+
return response.body;
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
export async function getEvents(
|
|
102
|
+
calendarId: string,
|
|
103
|
+
expandRecurringEvent: boolean,
|
|
104
|
+
authProp: GoogleCalendarAuthValue,
|
|
105
|
+
minUpdated?: Date
|
|
106
|
+
): Promise<GoogleCalendarEvent[]> {
|
|
107
|
+
// docs: https://developers.google.com/calendar/api/v3/reference/events/list
|
|
108
|
+
const now = new Date();
|
|
109
|
+
const yesterday = new Date();
|
|
110
|
+
yesterday.setDate(now.getDate() - 1);
|
|
111
|
+
|
|
112
|
+
const qParams: Record<string, string> = {
|
|
113
|
+
updatedMin: minUpdated?.toISOString() ?? yesterday.toISOString(),
|
|
114
|
+
maxResults: '2500', // Modified
|
|
115
|
+
orderBy: 'updated',
|
|
116
|
+
singleEvents: expandRecurringEvent ? 'true' : 'false',
|
|
117
|
+
showDeleted: 'true',
|
|
118
|
+
};
|
|
119
|
+
|
|
120
|
+
const accessToken = await getAccessToken(authProp);
|
|
121
|
+
const request: HttpRequest = {
|
|
122
|
+
method: HttpMethod.GET,
|
|
123
|
+
url: `${googleCalendarCommon.baseUrl}/calendars/${calendarId}/events`,
|
|
124
|
+
queryParams: qParams,
|
|
125
|
+
authentication: {
|
|
126
|
+
type: AuthenticationType.BEARER_TOKEN,
|
|
127
|
+
token: accessToken,
|
|
128
|
+
},
|
|
129
|
+
};
|
|
130
|
+
|
|
131
|
+
let eventList: GoogleCalendarEvent[] = [];
|
|
132
|
+
let pageToken = '';
|
|
133
|
+
do {
|
|
134
|
+
qParams['pageToken'] = pageToken;
|
|
135
|
+
const { body: res } = await httpClient.sendRequest<GoogleCalendarEventList>(
|
|
136
|
+
request
|
|
137
|
+
);
|
|
138
|
+
if (res.items.length > 0) {
|
|
139
|
+
eventList = [...eventList, ...res.items];
|
|
140
|
+
}
|
|
141
|
+
pageToken = res.nextPageToken;
|
|
142
|
+
} while (pageToken);
|
|
143
|
+
|
|
144
|
+
return eventList;
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
export async function getLatestEvent(
|
|
148
|
+
calendarId: string,
|
|
149
|
+
authProp: GoogleCalendarAuthValue
|
|
150
|
+
): Promise<GoogleCalendarEvent> {
|
|
151
|
+
const eventList = await getEvents(calendarId, false, authProp);
|
|
152
|
+
const lastUpdatedEvent = eventList.pop()!; // You can retrieve the last updated event.
|
|
153
|
+
return lastUpdatedEvent;
|
|
154
|
+
}
|
|
155
|
+
|
|
156
|
+
export async function getEventsForDropdown(
|
|
157
|
+
authProp: GoogleCalendarAuthValue,
|
|
158
|
+
calendarId?: string,
|
|
159
|
+
maxResults = 50
|
|
160
|
+
): Promise<{ label: string; value: string }[]> {
|
|
161
|
+
if (!calendarId) {
|
|
162
|
+
return [];
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
try {
|
|
166
|
+
const now = new Date();
|
|
167
|
+
const futureDate = new Date();
|
|
168
|
+
futureDate.setDate(now.getDate() + 30);
|
|
169
|
+
|
|
170
|
+
const queryParams: Record<string, string> = {
|
|
171
|
+
singleEvents: 'true',
|
|
172
|
+
orderBy: 'startTime',
|
|
173
|
+
timeMin: now.toISOString(),
|
|
174
|
+
timeMax: futureDate.toISOString(),
|
|
175
|
+
maxResults: maxResults.toString(),
|
|
176
|
+
showDeleted: 'false',
|
|
177
|
+
};
|
|
178
|
+
|
|
179
|
+
const request: HttpRequest = {
|
|
180
|
+
method: HttpMethod.GET,
|
|
181
|
+
url: `${googleCalendarCommon.baseUrl}/calendars/${encodeURIComponent(
|
|
182
|
+
calendarId
|
|
183
|
+
)}/events`,
|
|
184
|
+
queryParams: queryParams,
|
|
185
|
+
authentication: {
|
|
186
|
+
type: AuthenticationType.BEARER_TOKEN,
|
|
187
|
+
token: await getAccessToken(authProp),
|
|
188
|
+
},
|
|
189
|
+
};
|
|
190
|
+
|
|
191
|
+
const response = await httpClient.sendRequest<GoogleCalendarEventList>(
|
|
192
|
+
request
|
|
193
|
+
);
|
|
194
|
+
|
|
195
|
+
if (!response.body.items || response.body.items.length === 0) {
|
|
196
|
+
return [];
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
return response.body.items
|
|
200
|
+
.map((event) => {
|
|
201
|
+
const startTime = event.start?.dateTime || event.start?.date || '';
|
|
202
|
+
const startDate = startTime
|
|
203
|
+
? new Date(startTime).toLocaleDateString()
|
|
204
|
+
: '';
|
|
205
|
+
const startTimeFormatted = startTime
|
|
206
|
+
? new Date(startTime).toLocaleTimeString()
|
|
207
|
+
: '';
|
|
208
|
+
|
|
209
|
+
let label = event.summary || 'Untitled Event';
|
|
210
|
+
if (startDate) {
|
|
211
|
+
label += ` (${startDate}`;
|
|
212
|
+
if (event.start?.dateTime) {
|
|
213
|
+
label += ` at ${startTimeFormatted}`;
|
|
214
|
+
}
|
|
215
|
+
label += ')';
|
|
216
|
+
}
|
|
217
|
+
|
|
218
|
+
return {
|
|
219
|
+
label: label,
|
|
220
|
+
value: event.id || '',
|
|
221
|
+
};
|
|
222
|
+
})
|
|
223
|
+
.filter((item) => item.value !== '');
|
|
224
|
+
} catch (error) {
|
|
225
|
+
console.error('Error fetching events for dropdown:', error);
|
|
226
|
+
return [];
|
|
227
|
+
}
|
|
228
|
+
}
|
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
import { Property } from '@guayaba/workflows-framework';
|
|
2
|
+
import { getCalendars, getColors, getEventsForDropdown } from './helper';
|
|
3
|
+
import { googleCalendarAuth, GoogleCalendarAuthValue, getAccessToken } from '../auth';
|
|
4
|
+
|
|
5
|
+
export { googleCalendarAuth, GoogleCalendarAuthValue, getAccessToken, createGoogleClient, googleCalendarScopes } from '../auth';
|
|
6
|
+
|
|
7
|
+
export const googleCalendarCommon = {
|
|
8
|
+
baseUrl: 'https://www.googleapis.com/calendar/v3',
|
|
9
|
+
calendarDropdown: (minAccessRole?: 'writer') => {
|
|
10
|
+
return Property.Dropdown<string,true,typeof googleCalendarAuth>({
|
|
11
|
+
auth: googleCalendarAuth,
|
|
12
|
+
displayName: 'Calendar',
|
|
13
|
+
refreshers: [],
|
|
14
|
+
required: true,
|
|
15
|
+
options: async ({ auth }) => {
|
|
16
|
+
if (!auth) {
|
|
17
|
+
return {
|
|
18
|
+
disabled: true,
|
|
19
|
+
placeholder: 'Please connect your account first',
|
|
20
|
+
options: [],
|
|
21
|
+
};
|
|
22
|
+
}
|
|
23
|
+
const authValue = auth as GoogleCalendarAuthValue;
|
|
24
|
+
const calendars = await getCalendars(authValue, minAccessRole);
|
|
25
|
+
return {
|
|
26
|
+
disabled: false,
|
|
27
|
+
options: calendars.map((calendar) => {
|
|
28
|
+
return {
|
|
29
|
+
label: calendar.summary,
|
|
30
|
+
value: calendar.id,
|
|
31
|
+
};
|
|
32
|
+
}),
|
|
33
|
+
};
|
|
34
|
+
},
|
|
35
|
+
});
|
|
36
|
+
},
|
|
37
|
+
eventDropdown: (required = false) => {
|
|
38
|
+
return Property.Dropdown<string,boolean,typeof googleCalendarAuth>({
|
|
39
|
+
displayName: 'Event',
|
|
40
|
+
refreshers: ['calendar_id'],
|
|
41
|
+
required: required,
|
|
42
|
+
auth: googleCalendarAuth,
|
|
43
|
+
options: async ({ auth, calendar_id }) => {
|
|
44
|
+
if (!auth) {
|
|
45
|
+
return {
|
|
46
|
+
disabled: true,
|
|
47
|
+
placeholder: 'Please connect your account first',
|
|
48
|
+
options: [],
|
|
49
|
+
};
|
|
50
|
+
}
|
|
51
|
+
if (!calendar_id) {
|
|
52
|
+
return {
|
|
53
|
+
disabled: true,
|
|
54
|
+
placeholder: 'Please select a calendar first',
|
|
55
|
+
options: [],
|
|
56
|
+
};
|
|
57
|
+
}
|
|
58
|
+
const authValue = auth as GoogleCalendarAuthValue;
|
|
59
|
+
const events = await getEventsForDropdown(
|
|
60
|
+
authValue,
|
|
61
|
+
calendar_id as string
|
|
62
|
+
);
|
|
63
|
+
return {
|
|
64
|
+
disabled: false,
|
|
65
|
+
options: events,
|
|
66
|
+
};
|
|
67
|
+
},
|
|
68
|
+
});
|
|
69
|
+
},
|
|
70
|
+
colorId: Property.Dropdown({
|
|
71
|
+
auth: googleCalendarAuth,
|
|
72
|
+
displayName: 'Color',
|
|
73
|
+
refreshers: [],
|
|
74
|
+
required: false,
|
|
75
|
+
options: async ({ auth }) => {
|
|
76
|
+
if (!auth) {
|
|
77
|
+
return {
|
|
78
|
+
disabled: true,
|
|
79
|
+
placeholder: 'Please connect your account first',
|
|
80
|
+
options: [],
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
const response = await getColors(auth as GoogleCalendarAuthValue);
|
|
84
|
+
return {
|
|
85
|
+
disabled: false,
|
|
86
|
+
options: Object.entries(response.event).map(([key, value]) => {
|
|
87
|
+
return {
|
|
88
|
+
label: value.background,
|
|
89
|
+
value: key,
|
|
90
|
+
};
|
|
91
|
+
}),
|
|
92
|
+
};
|
|
93
|
+
},
|
|
94
|
+
}),
|
|
95
|
+
};
|