Skip to content

Commit 738cf1d

Browse files
author
barticus
authored
Merge pull request #73 from mailchimp/feature/node-18-support
Node 18 runtime testing and configuration.
2 parents 9b920c0 + 4f74eb2 commit 738cf1d

File tree

5 files changed

+2318
-1717
lines changed

5 files changed

+2318
-1717
lines changed

CHANGELOG.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,10 @@
1+
## Version 0.5.4
2+
3+
- Switch from mailchimp-api-v3 package to @mailchimp/mailchimp_marketing (PR #66)
4+
- Add a configurable retry to allow a higher chance of requests causing transient failures to succeed (PR #69)
5+
- Added linter config and updated packages. (PR #70)
6+
- Node.JS 18 runtime for functions (PR #73)
7+
18
## Version 0.5.3
29

310
- Addressed [breaking change in Google Cloud Functions](https://cloud.google.com/functions/docs/release-notes#April_11_2023) where the build command would run on function deployment (PR #65).

extension.yaml

Lines changed: 16 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -13,12 +13,11 @@
1313
# limitations under the License.
1414

1515
name: mailchimp-firebase-sync
16-
version: 0.5.3
16+
version: 0.5.4
1717
specVersion: v1beta
1818

1919
displayName: Manage Marketing with Mailchimp
20-
description:
21-
Syncs user data with a Mailchimp audience for sending personalized email marketing campaigns.
20+
description: Syncs user data with a Mailchimp audience for sending personalized email marketing campaigns.
2221

2322
license: Apache-2.0
2423

@@ -59,7 +58,7 @@ resources:
5958
then automatically adds the new user to your specified MailChimp audience.
6059
properties:
6160
location: ${LOCATION}
62-
runtime: nodejs16
61+
runtime: nodejs18
6362
eventTrigger:
6463
eventType: providers/firebase.auth/eventTypes/user.create
6564
resource: projects/${PROJECT_ID}
@@ -72,7 +71,7 @@ resources:
7271
MailChimp audience.
7372
properties:
7473
location: ${LOCATION}
75-
runtime: nodejs16
74+
runtime: nodejs18
7675
eventTrigger:
7776
eventType: providers/firebase.auth/eventTypes/user.delete
7877
resource: projects/${PROJECT_ID}
@@ -81,11 +80,11 @@ resources:
8180
type: firebaseextensions.v1beta.function
8281
description:
8382
Member Tags provide the ability to associate "metadata" or "labels" with a Mailchimp subscriber.
84-
The memberTagsHandler function listens for Firestore write events based on specified config path,
83+
The memberTagsHandler function listens for Firestore write events based on specified config path,
8584
then automatically classifies the document data as Mailchimp subscriber tags.
8685
properties:
8786
location: ${LOCATION}
88-
runtime: nodejs16
87+
runtime: nodejs18
8988
eventTrigger:
9089
eventType: providers/cloud.firestore/eventTypes/document.write
9190
resource: projects/${param:PROJECT_ID}/databases/(default)/documents/${param:MAILCHIMP_MEMBER_TAGS_WATCH_PATH}/{documentId}
@@ -94,11 +93,11 @@ resources:
9493
type: firebaseextensions.v1beta.function
9594
description:
9695
Merge fields provide the ability to create new properties that can be associated with Mailchimp subscriber.
97-
The mergeFieldsHandler function listens for Firestore write events based on specified config path,
96+
The mergeFieldsHandler function listens for Firestore write events based on specified config path,
9897
then automatically populates the Mailchimp subscriber's respective merge fields.
9998
properties:
10099
location: ${LOCATION}
101-
runtime: nodejs16
100+
runtime: nodejs18
102101
eventTrigger:
103102
eventType: providers/cloud.firestore/eventTypes/document.write
104103
resource: projects/${param:PROJECT_ID}/databases/(default)/documents/${param:MAILCHIMP_MERGE_FIELDS_WATCH_PATH}/{documentId}
@@ -107,12 +106,12 @@ resources:
107106
type: firebaseextensions.v1beta.function
108107
description:
109108
Member events are Mailchimp specific activity events that can be created and associated with a predefined action.
110-
The memberEventsHandler function Listens for Firestore write events based on specified config path,
111-
then automatically uses the document data to create a Mailchimp event on the subscriber's profile
109+
The memberEventsHandler function Listens for Firestore write events based on specified config path,
110+
then automatically uses the document data to create a Mailchimp event on the subscriber's profile
112111
which can subsequently trigger automation workflows.
113112
properties:
114113
location: ${LOCATION}
115-
runtime: nodejs16
114+
runtime: nodejs18
116115
eventTrigger:
117116
eventType: providers/cloud.firestore/eventTypes/document.write
118117
resource: projects/${param:PROJECT_ID}/databases/(default)/documents/${param:MAILCHIMP_MEMBER_EVENTS_WATCH_PATH}/{documentId}
@@ -305,17 +304,16 @@ params:
305304
306305
NOTE: To disable this cloud function listener, provide an empty JSON config `{}`.
307306
308-
309307
required: true
310-
default: '{}'
308+
default: "{}"
311309

312310
- param: MAILCHIMP_MERGE_FIELDS_WATCH_PATH
313311
label: Firebase Merge Fields Watch Path
314312
description: The Firestore collection to watch for merge field changes
315313
type: string
316314
example: registrations
317315
default: _unused_
318-
required: true
316+
required: true
319317

320318
- param: MAILCHIMP_MERGE_FIELDS_CONFIG
321319
type: string
@@ -335,7 +333,7 @@ params:
335333
2) `statusField` - An optional configuration setting for syncing the users mailchimp status. Properties are:
336334
337335
- `documentPath` - (required) The path to the field in the document containing the users status, as a string. The format can be any valid [JMES Path query](https://jmespath.org/). e.g. "status", "meta.status".
338-
336+
339337
- `statusFormat` - (optional) Indicates the format that the status field is. The options are:
340338
- `"string"` - The default, this will sync the value from the status field as is, with no modification.
341339
- `"boolean"` - This will check if the value is truthy (e.g. true, 1, "subscribed"), and if so will resolve the status to "subscribed", otherwise it will resolve to "unsubscribed".
@@ -418,9 +416,8 @@ params:
418416
419417
NOTE: To disable this cloud function listener, provide an empty JSON config `{}`.
420418
421-
422419
required: true
423-
default: '{}'
420+
default: "{}"
424421

425422
- param: MAILCHIMP_MEMBER_EVENTS_WATCH_PATH
426423
label: Firebase Member Events Watch Path
@@ -513,6 +510,5 @@ params:
513510
514511
NOTE: To disable this cloud function listener, provide an empty JSON config `{}`.
515512
516-
517513
required: true
518-
default: '{}'
514+
default: "{}"

functions/index.js

Lines changed: 16 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
const crypto = require("crypto");
22
const _ = require("lodash");
3-
const functions = require("firebase-functions");
3+
const { auth, firestore, logger } = require("firebase-functions");
44
const admin = require("firebase-admin");
55
const mailchimp = require("@mailchimp/mailchimp_marketing");
66
const jmespath = require("jmespath");
@@ -25,7 +25,7 @@ function processConfig(configInput) {
2525
// (tags, merge fields, custom events) at the root.
2626
config = Object.entries(configInput).reduce((acc, [key, value]) => {
2727
const logError = (message) => {
28-
functions.logger.log(message, key, value);
28+
logger.log(message, key, value);
2929
return acc;
3030
};
3131
if (configInput[key] && Object.keys(CONFIG_PARAMS).includes(key)) {
@@ -180,7 +180,7 @@ function errorFilterFor404(err) {
180180
return err?.status === 404;
181181
}
182182

183-
exports.addUserToList = functions.handler.auth.user.onCreate(
183+
exports.addUserToList = auth.user().onCreate(
184184
async (user) => {
185185
logs.start();
186186

@@ -221,7 +221,7 @@ exports.addUserToList = functions.handler.auth.user.onCreate(
221221
},
222222
);
223223

224-
exports.removeUserFromList = functions.handler.auth.user.onDelete(
224+
exports.removeUserFromList = auth.user().onDelete(
225225
async (user) => {
226226
logs.start();
227227

@@ -256,7 +256,7 @@ exports.removeUserFromList = functions.handler.auth.user.onDelete(
256256
},
257257
);
258258

259-
exports.memberTagsHandler = functions.handler.firestore.document
259+
exports.memberTagsHandler = firestore.document(config.mailchimpMemberTagsWatchPath)
260260
.onWrite(async (event) => {
261261
// If an empty JSON configuration was provided then consider function as NO-OP
262262
if (_.isEmpty(config.mailchimpMemberTags)) return;
@@ -271,11 +271,11 @@ exports.memberTagsHandler = functions.handler.firestore.document
271271
return;
272272
}
273273
if (!tagsConfig.memberTags) {
274-
functions.logger.log(`A property named 'memberTags' is required`);
274+
logger.log(`A property named 'memberTags' is required`);
275275
return;
276276
}
277277
if (!Array.isArray(tagsConfig.memberTags)) {
278-
functions.logger.log("\"memberTags\" must be an array");
278+
logger.log("\"memberTags\" must be an array");
279279
return;
280280
}
281281

@@ -320,11 +320,11 @@ exports.memberTagsHandler = functions.handler.firestore.document
320320
), errorFilterFor404);
321321
}
322322
} catch (e) {
323-
functions.logger.log(e);
323+
logger.log(e);
324324
}
325325
});
326326

327-
exports.mergeFieldsHandler = functions.handler.firestore.document
327+
exports.mergeFieldsHandler = firestore.document(config.mailchimpMergeFieldWatchPath)
328328
.onWrite(async (event) => {
329329
// If an empty JSON configuration was provided then consider function as NO-OP
330330
if (_.isEmpty(config.mailchimpMergeField)) return;
@@ -339,11 +339,11 @@ exports.mergeFieldsHandler = functions.handler.firestore.document
339339
return;
340340
}
341341
if (!mergeFieldsConfig.mergeFields || _.isEmpty(mergeFieldsConfig.mergeFields)) {
342-
functions.logger.log(`A property named 'mergeFields' is required`);
342+
logger.log(`A property named 'mergeFields' is required`);
343343
return;
344344
}
345345
if (!_.isObject(mergeFieldsConfig.mergeFields)) {
346-
functions.logger.log("Merge Fields config must be an object");
346+
logger.log("Merge Fields config must be an object");
347347
return;
348348
}
349349

@@ -410,11 +410,11 @@ exports.mergeFieldsHandler = functions.handler.firestore.document
410410
), errorFilterFor404);
411411
}
412412
} catch (e) {
413-
functions.logger.log(e);
413+
logger.log(e);
414414
}
415415
});
416416

417-
exports.memberEventsHandler = functions.handler.firestore.document
417+
exports.memberEventsHandler = firestore.document(config.mailchimpMemberEventsWatchPath)
418418
.onWrite(async (event) => {
419419
// If an empty JSON configuration was provided then consider function as NO-OP
420420
if (_.isEmpty(config.mailchimpMemberEvents)) return;
@@ -429,11 +429,11 @@ exports.memberEventsHandler = functions.handler.firestore.document
429429
return;
430430
}
431431
if (!eventsConfig.memberEvents) {
432-
functions.logger.log(`A property named 'memberEvents' is required`);
432+
logger.log(`A property named 'memberEvents' is required`);
433433
return;
434434
}
435435
if (!Array.isArray(eventsConfig.memberEvents)) {
436-
functions.logger.log(`'memberEvents' property must be an array`);
436+
logger.log(`'memberEvents' property must be an array`);
437437
return;
438438
}
439439

@@ -482,7 +482,7 @@ exports.memberEventsHandler = functions.handler.firestore.document
482482
await Promise.all(requests);
483483
}
484484
} catch (e) {
485-
functions.logger.log(e);
485+
logger.log(e);
486486
}
487487
});
488488

0 commit comments

Comments
 (0)