mcdev 4.3.3 → 5.0.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.
- package/.coverage-comment-template.md +20 -0
- package/.coverage-comment-template.svelte +178 -0
- package/.eslintrc.json +2 -0
- package/.fork/.prettierrc +6 -0
- package/.fork/custom-commands.json +13 -1
- package/.github/ISSUE_TEMPLATE/bug.yml +2 -0
- package/.github/workflows/code-test.yml +36 -0
- package/.github/workflows/coverage-base-update.yml +57 -0
- package/.github/workflows/coverage-develop-branch.yml +41 -0
- package/.github/workflows/coverage-main-branch.yml +41 -0
- package/.github/workflows/coverage.yml +77 -0
- package/.husky/post-checkout +1 -1
- package/.prettierrc +1 -1
- package/.vscode/extensions.json +0 -4
- package/boilerplate/config.json +1 -1
- package/boilerplate/files/.prettierrc +1 -1
- package/boilerplate/files/.vscode/extensions.json +1 -1
- package/boilerplate/files/.vscode/settings.json +1 -0
- package/boilerplate/forcedUpdates.json +8 -0
- package/docs/dist/documentation.md +1261 -433
- package/lib/Builder.js +6 -1
- package/lib/Deployer.js +34 -10
- package/lib/MetadataTypeDefinitions.js +8 -6
- package/lib/MetadataTypeInfo.js +8 -6
- package/lib/Retriever.js +4 -1
- package/lib/cli.js +54 -42
- package/lib/index.js +82 -8
- package/lib/metadataTypes/Asset.js +185 -31
- package/lib/metadataTypes/AttributeGroup.js +0 -1
- package/lib/metadataTypes/Automation.js +48 -5
- package/lib/metadataTypes/Campaign.js +20 -7
- package/lib/metadataTypes/ContentArea.js +1 -1
- package/lib/metadataTypes/DataExtension.js +221 -184
- package/lib/metadataTypes/DataExtensionField.js +12 -19
- package/lib/metadataTypes/DataExtensionTemplate.js +1 -1
- package/lib/metadataTypes/DataExtract.js +1 -1
- package/lib/metadataTypes/DataExtractType.js +1 -1
- package/lib/metadataTypes/Email.js +1 -1
- package/lib/metadataTypes/{EmailSendDefinition.js → EmailSend.js} +5 -5
- package/lib/metadataTypes/{EventDefinition.js → Event.js} +17 -35
- package/lib/metadataTypes/{FtpLocation.js → FileLocation.js} +2 -2
- package/lib/metadataTypes/FileTransfer.js +8 -7
- package/lib/metadataTypes/Filter.js +1 -1
- package/lib/metadataTypes/Folder.js +8 -3
- package/lib/metadataTypes/ImportFile.js +6 -6
- package/lib/metadataTypes/{Interaction.js → Journey.js} +311 -147
- package/lib/metadataTypes/List.js +2 -2
- package/lib/metadataTypes/MetadataType.js +318 -90
- package/lib/metadataTypes/MobileCode.js +0 -1
- package/lib/metadataTypes/MobileKeyword.js +336 -40
- package/lib/metadataTypes/MobileMessage.js +473 -0
- package/lib/metadataTypes/Query.js +114 -32
- package/lib/metadataTypes/Role.js +60 -21
- package/lib/metadataTypes/Script.js +5 -7
- package/lib/metadataTypes/SendClassification.js +40 -0
- package/lib/metadataTypes/SetDefinition.js +1 -7
- package/lib/metadataTypes/TransactionalEmail.js +2 -3
- package/lib/metadataTypes/TransactionalMessage.js +1 -2
- package/lib/metadataTypes/TransactionalSMS.js +8 -15
- package/lib/metadataTypes/{TriggeredSendDefinition.js → TriggeredSend.js} +35 -27
- package/lib/metadataTypes/User.js +1177 -0
- package/lib/metadataTypes/definitions/Asset.definition.js +2 -4
- package/lib/metadataTypes/definitions/AttributeGroup.definition.js +1 -0
- package/lib/metadataTypes/definitions/Automation.definition.js +3 -2
- package/lib/metadataTypes/definitions/Campaign.definition.js +79 -4
- package/lib/metadataTypes/definitions/ContentArea.definition.js +1 -0
- package/lib/metadataTypes/definitions/DataExtension.definition.js +2 -1
- package/lib/metadataTypes/definitions/DataExtensionField.definition.js +1 -0
- package/lib/metadataTypes/definitions/DataExtensionTemplate.definition.js +1 -0
- package/lib/metadataTypes/definitions/DataExtract.definition.js +1 -0
- package/lib/metadataTypes/definitions/DataExtractType.definition.js +1 -0
- package/lib/metadataTypes/definitions/Discovery.definition.js +1 -0
- package/lib/metadataTypes/definitions/Email.definition.js +1 -0
- package/lib/metadataTypes/definitions/{EmailSendDefinition.definition.js → EmailSend.definition.js} +4 -2
- package/lib/metadataTypes/definitions/{EventDefinition.definition.js → Event.definition.js} +2 -1
- package/lib/metadataTypes/definitions/{FtpLocation.definition.js → FileLocation.definition.js} +4 -3
- package/lib/metadataTypes/definitions/FileTransfer.definition.js +3 -2
- package/lib/metadataTypes/definitions/Filter.definition.js +1 -0
- package/lib/metadataTypes/definitions/Folder.definition.js +2 -0
- package/lib/metadataTypes/definitions/ImportFile.definition.js +4 -3
- package/lib/metadataTypes/definitions/{Interaction.definition.js → Journey.definition.js} +11 -2
- package/lib/metadataTypes/definitions/List.definition.js +1 -0
- package/lib/metadataTypes/definitions/MobileCode.definition.js +3 -1
- package/lib/metadataTypes/definitions/MobileKeyword.definition.js +27 -17
- package/lib/metadataTypes/definitions/MobileMessage.definition.js +743 -0
- package/lib/metadataTypes/definitions/Query.definition.js +3 -2
- package/lib/metadataTypes/definitions/Role.definition.js +5 -0
- package/lib/metadataTypes/definitions/Script.definition.js +1 -0
- package/lib/metadataTypes/definitions/SendClassification.definition.js +114 -0
- package/lib/metadataTypes/definitions/SetDefinition.definition.js +1 -0
- package/lib/metadataTypes/definitions/TransactionalEmail.definition.js +2 -1
- package/lib/metadataTypes/definitions/TransactionalPush.definition.js +1 -0
- package/lib/metadataTypes/definitions/TransactionalSMS.definition.js +1 -0
- package/lib/metadataTypes/definitions/{TriggeredSendDefinition.definition.js → TriggeredSend.definition.js} +5 -3
- package/lib/metadataTypes/definitions/User.definition.js +365 -0
- package/lib/retrieveChangelog.js +1 -2
- package/lib/util/auth.js +29 -9
- package/lib/util/businessUnit.js +3 -3
- package/lib/util/cli.js +55 -7
- package/lib/util/devops.js +93 -8
- package/lib/util/file.js +55 -13
- package/lib/util/init.config.js +1 -2
- package/lib/util/init.npm.js +3 -3
- package/lib/util/util.js +68 -14
- package/package.json +16 -15
- package/test/general.test.js +62 -0
- package/test/mockRoot/.mcdevrc.json +7 -5
- package/test/mockRoot/deploy/testInstance/_ParentBU_/user/testBlocked_user.user-meta.json +23 -0
- package/test/mockRoot/deploy/testInstance/_ParentBU_/user/testExisting_user.user-meta.json +31 -0
- package/test/mockRoot/deploy/testInstance/_ParentBU_/user/testNew_user.user-meta.json +27 -0
- package/test/mockRoot/deploy/testInstance/testBU/dataExtension/{childBU_dataextension_test.dataExtension-meta.json → testExisting_dataExtension.dataExtension-meta.json} +2 -2
- package/test/mockRoot/deploy/testInstance/testBU/dataExtension/{testDataExtension.dataExtension-meta.json → testNew_dataExtension.dataExtension-meta.json} +2 -2
- package/test/mockRoot/deploy/testInstance/testBU/journey/testExisting_interaction.interaction-meta.json +576 -0
- package/test/mockRoot/deploy/testInstance/testBU/mobileKeyword/testNew_keyword.mobileKeyword-meta.amp +2 -0
- package/test/mockRoot/deploy/testInstance/testBU/mobileKeyword/testNew_keyword.mobileKeyword-meta.json +10 -0
- package/test/mockRoot/deploy/testInstance/testBU/mobileKeyword/testNew_keyword_blocked.mobileKeyword-meta.amp +2 -0
- package/test/mockRoot/deploy/testInstance/testBU/mobileKeyword/testNew_keyword_blocked.mobileKeyword-meta.json +10 -0
- package/test/mockRoot/deploy/testInstance/testBU/mobileMessage/NTIzOjc4OjA.mobileMessage-meta.amp +1 -0
- package/test/mockRoot/deploy/testInstance/testBU/mobileMessage/NTIzOjc4OjA.mobileMessage-meta.json +61 -0
- package/test/mockRoot/deploy/testInstance/testBU/mobileMessage/new.mobileMessage-meta.amp +1 -0
- package/test/mockRoot/deploy/testInstance/testBU/mobileMessage/new.mobileMessage-meta.json +60 -0
- package/test/mockRoot/deploy/testInstance/testBU/query/testExistingQuery.query-meta.json +1 -1
- package/test/mockRoot/deploy/testInstance/testBU/query/testNewQuery.query-meta.json +1 -1
- package/test/mockRoot/deploy/testInstance/testBU/query/testNewQuery.query-meta.sql +1 -1
- package/test/mockRoot/deploy/testInstance/testBU/transactionalEmail/testExisting_temail.transactionalEmail-meta.json +1 -1
- package/test/mockRoot/deploy/testInstance/testBU/transactionalEmail/testNew_temail.transactionalEmail-meta.json +1 -1
- package/test/resourceFactory.js +13 -0
- package/test/resources/1111111/accountUser/configure-response.xml +70 -0
- package/test/resources/1111111/accountUser/create-response.xml +97 -0
- package/test/resources/1111111/accountUser/retrieve-response.xml +156 -0
- package/test/resources/1111111/accountUser/update-response.xml +111 -0
- package/test/resources/1111111/accountUserAccount/retrieve-response.xml +77 -0
- package/test/resources/1111111/platform/v1/setup/quickflow/data/get-response.json +455 -0
- package/test/resources/1111111/role/retrieve-response.xml +76 -0
- package/test/resources/1111111/user/build-expected.json +16 -0
- package/test/resources/1111111/user/create-expected.json +21 -0
- package/test/resources/1111111/user/retrieve-expected.json +24 -0
- package/test/resources/1111111/user/template-expected.json +16 -0
- package/test/resources/1111111/user/update-expected.json +21 -0
- package/test/resources/9999999/automation/v1/queries/549f0568-607c-4940-afef-437965094dat/delete-response.json +1 -0
- package/test/resources/9999999/automation/v1/queries/549f0568-607c-4940-afef-437965094dat/get-response.json +17 -0
- package/test/resources/9999999/automation/v1/queries/549f0568-607c-4940-afef-437965094dat/patch-response.json +3 -3
- package/test/resources/9999999/automation/v1/queries/get-response.json +21 -4
- package/test/resources/9999999/automation/v1/queries/post-response.json +4 -4
- package/test/resources/9999999/data/v1/customobjectdata/key/{childBU_dataextension_test → testExisting_dataExtension}/rowset/get-response.json +1 -1
- package/test/resources/9999999/dataExtension/build-expected.json +3 -3
- package/test/resources/9999999/dataExtension/create-expected.json +2 -2
- package/test/resources/9999999/dataExtension/create-response.xml +8 -3
- package/test/resources/9999999/dataExtension/retrieve-expected.json +3 -3
- package/test/resources/9999999/dataExtension/retrieve-response.xml +9 -4
- package/test/resources/9999999/dataExtension/template-expected.json +3 -3
- package/test/resources/9999999/dataExtension/update-expected.json +3 -3
- package/test/resources/9999999/dataExtension/update-response.xml +9 -4
- package/test/resources/9999999/dataExtensionField/retrieve-response.xml +14 -9
- package/test/resources/9999999/interaction/v1/interactions/get-response.json +312 -0
- package/test/resources/9999999/interaction/v1/interactions/key_testExisting_interaction/get-response.json +312 -0
- package/test/resources/9999999/interaction/v1/interactions/key_testExisting_interaction/put-response.json +592 -0
- package/test/resources/9999999/journey/build-expected.json +572 -0
- package/test/resources/9999999/journey/get-expected.json +576 -0
- package/test/resources/9999999/journey/put-expected.json +576 -0
- package/test/resources/9999999/journey/template-expected.json +572 -0
- package/test/resources/9999999/legacy/v1/beta/mobile/keyword/NXV4ZFMwTEFwRVczd3RaLUF5X3p5dzo4Njow/get-response.json +42 -0
- package/test/resources/9999999/legacy/v1/beta/mobile/keyword/cTVJaG5oSDJPVUNHcUh6Z3pQT2tVdzo4Njow/delete-response.json +0 -0
- package/test/resources/9999999/legacy/v1/beta/mobile/keyword/get-response.json +1 -0
- package/test/resources/9999999/legacy/v1/beta/mobile/keyword/post-response.json +3 -0
- package/test/resources/9999999/legacy/v1/beta/mobile/message/NTIzOjc4OjA/delete-response.json +0 -0
- package/test/resources/9999999/legacy/v1/beta/mobile/message/NTIzOjc4OjA/get-response.json +106 -0
- package/test/resources/9999999/legacy/v1/beta/mobile/message/NTIzOjc4OjA/post-response.json +0 -0
- package/test/resources/9999999/legacy/v1/beta/mobile/message/NTQ3Ojc4OjA/get-response.json +127 -0
- package/test/resources/9999999/legacy/v1/beta/mobile/message/get-response.json +129 -0
- package/test/resources/9999999/legacy/v1/beta/mobile/message/post-response.json +3 -0
- package/test/resources/9999999/legacy/v1/beta2/data/campaign/get-response.json +29 -0
- package/test/resources/9999999/messaging/v1/email/definitions/post-response.json +1 -1
- package/test/resources/9999999/messaging/v1/email/definitions/testExisting_temail/get-response.json +1 -1
- package/test/resources/9999999/messaging/v1/email/definitions/testExisting_temail/patch-response.json +1 -1
- package/test/resources/9999999/mobileKeyword/build-expected.amp +2 -0
- package/test/resources/9999999/mobileKeyword/build-expected.json +9 -0
- package/test/resources/9999999/mobileKeyword/get-expected.amp +2 -0
- package/test/resources/9999999/mobileKeyword/get-expected.json +15 -0
- package/test/resources/9999999/mobileKeyword/post-create-expected.amp +2 -0
- package/test/resources/9999999/mobileKeyword/post-create-expected.json +17 -0
- package/test/resources/9999999/mobileKeyword/template-expected.amp +2 -0
- package/test/resources/9999999/mobileKeyword/template-expected.json +9 -0
- package/test/resources/9999999/mobileMessage/build-expected.amp +1 -0
- package/test/resources/9999999/mobileMessage/build-expected.json +60 -0
- package/test/resources/9999999/mobileMessage/get-expected.amp +1 -0
- package/test/resources/9999999/mobileMessage/get-expected.json +61 -0
- package/test/resources/9999999/mobileMessage/post-create-expected.amp +1 -0
- package/test/resources/9999999/mobileMessage/post-create-expected.json +63 -0
- package/test/resources/9999999/mobileMessage/post-update-expected.amp +1 -0
- package/test/resources/9999999/mobileMessage/post-update-expected.json +61 -0
- package/test/resources/9999999/mobileMessage/template-expected.amp +1 -0
- package/test/resources/9999999/mobileMessage/template-expected.json +60 -0
- package/test/resources/9999999/query/build-expected.json +1 -1
- package/test/resources/9999999/query/get-expected.json +1 -1
- package/test/resources/9999999/query/get2-expected.json +11 -0
- package/test/resources/9999999/query/patch-expected.json +1 -1
- package/test/resources/9999999/query/post-expected.json +1 -1
- package/test/resources/9999999/query/template-expected.json +1 -1
- package/test/resources/9999999/queryDefinition/retrieve-response.xml +30 -0
- package/test/resources/9999999/transactionalEmail/build-expected.json +5 -5
- package/test/resources/9999999/transactionalEmail/get-expected.json +1 -1
- package/test/resources/9999999/transactionalEmail/patch-expected.json +1 -1
- package/test/resources/9999999/transactionalEmail/post-expected.json +1 -1
- package/test/resources/9999999/transactionalEmail/template-expected.json +5 -5
- package/test/resources/9999999/transactionalPush/build-expected.json +2 -2
- package/test/resources/9999999/transactionalPush/template-expected.json +2 -2
- package/test/resources/9999999/transactionalSMS/build-expected.json +3 -3
- package/test/resources/9999999/transactionalSMS/template-expected.json +3 -3
- package/test/{dataExtension.test.js → type.dataExtension.test.js} +78 -21
- package/test/{interaction.test.js → type.journey.test.js} +64 -30
- package/test/type.mobileKeyword.test.js +250 -0
- package/test/type.mobileMessage.test.js +205 -0
- package/test/{query.test.js → type.query.test.js} +102 -5
- package/test/{transactionalEmail.test.js → type.transactionalEmail.test.js} +40 -2
- package/test/{transactionalPush.test.js → type.transactionalPush.test.js} +41 -2
- package/test/{transactionalSMS.test.js → type.transactionalSMS.test.js} +73 -3
- package/test/type.user.test.js +160 -0
- package/test/utils.js +17 -5
- package/types/mcdev.d.js +48 -15
- package/.github/workflows/code-analysis.yml +0 -57
- package/lib/metadataTypes/AccountUser.js +0 -426
- package/lib/metadataTypes/definitions/AccountUser.definition.js +0 -227
- package/test/mockRoot/deploy/testInstance/testBU/interaction/testExisting_interaction.interaction-meta.json +0 -266
- package/test/resources/9999999/interaction/build-expected.json +0 -260
- package/test/resources/9999999/interaction/get-expected.json +0 -264
- package/test/resources/9999999/interaction/put-expected.json +0 -264
- package/test/resources/9999999/interaction/template-expected.json +0 -260
- package/test/resources/9999999/interaction/v1/interactions/put-response.json +0 -280
- /package/test/mockRoot/deploy/testInstance/testBU/{interaction → journey}/testNew_interaction.interaction-meta.json +0 -0
- /package/test/resources/9999999/{interaction → journey}/post-expected.json +0 -0
package/lib/util/cli.js
CHANGED
|
@@ -8,6 +8,7 @@ const inquirer = require('inquirer');
|
|
|
8
8
|
const MetadataDefinitions = require('./../MetadataTypeDefinitions');
|
|
9
9
|
const Util = require('./util');
|
|
10
10
|
const auth = require('./auth');
|
|
11
|
+
require('console.table');
|
|
11
12
|
|
|
12
13
|
/**
|
|
13
14
|
* CLI helper class
|
|
@@ -315,7 +316,7 @@ const Cli = {
|
|
|
315
316
|
if (properties && properties.credentials[value]) {
|
|
316
317
|
return `There already is an account with the name '${value}' in your config.`;
|
|
317
318
|
}
|
|
318
|
-
const converted = encodeURIComponent(value).
|
|
319
|
+
const converted = encodeURIComponent(value).replaceAll(/[*]/g, '_STAR_');
|
|
319
320
|
if (value != converted) {
|
|
320
321
|
return 'Please do not use any special chars';
|
|
321
322
|
}
|
|
@@ -526,15 +527,57 @@ const Cli = {
|
|
|
526
527
|
/**
|
|
527
528
|
* shows metadata type descriptions
|
|
528
529
|
*
|
|
529
|
-
* @returns {
|
|
530
|
+
* @returns {object[]} list of supported types with their apiNames
|
|
530
531
|
*/
|
|
531
532
|
explainTypes() {
|
|
532
|
-
|
|
533
|
-
require('
|
|
533
|
+
const MetadataTypeInfo = require('./../MetadataTypeInfo');
|
|
534
|
+
const TransactionalMessage = require('./../metadataTypes/TransactionalMessage');
|
|
535
|
+
const json = [];
|
|
536
|
+
const apiNameArr = Object.keys(MetadataDefinitions);
|
|
537
|
+
|
|
538
|
+
for (const apiName of apiNameArr) {
|
|
539
|
+
const details = MetadataDefinitions[apiName];
|
|
540
|
+
const supportCheckClass = apiName.startsWith('transactional')
|
|
541
|
+
? TransactionalMessage
|
|
542
|
+
: MetadataTypeInfo[apiName];
|
|
543
|
+
json.push({
|
|
544
|
+
name: details.typeName,
|
|
545
|
+
apiName: details.type,
|
|
546
|
+
retrieveByDefault: details.typeRetrieveByDefault,
|
|
547
|
+
supports: {
|
|
548
|
+
retrieve: Object.prototype.hasOwnProperty.call(supportCheckClass, 'retrieve'),
|
|
549
|
+
create: Object.prototype.hasOwnProperty.call(supportCheckClass, 'create'),
|
|
550
|
+
update: Object.prototype.hasOwnProperty.call(supportCheckClass, 'update'),
|
|
551
|
+
delete: Object.prototype.hasOwnProperty.call(supportCheckClass, 'deleteByKey'),
|
|
552
|
+
changeKey:
|
|
553
|
+
supportCheckClass.definition.keyIsFixed === false &&
|
|
554
|
+
supportCheckClass.definition.keyField !==
|
|
555
|
+
supportCheckClass.definition.idField &&
|
|
556
|
+
supportCheckClass.definition.fields[supportCheckClass.definition.keyField]
|
|
557
|
+
.isUpdateable &&
|
|
558
|
+
Object.prototype.hasOwnProperty.call(supportCheckClass, 'update'),
|
|
559
|
+
buildTemplate: Object.prototype.hasOwnProperty.call(
|
|
560
|
+
supportCheckClass,
|
|
561
|
+
'create'
|
|
562
|
+
), // supported for all types that can be created
|
|
563
|
+
retrieveAsTemplate: Object.prototype.hasOwnProperty.call(
|
|
564
|
+
supportCheckClass,
|
|
565
|
+
'retrieveAsTemplate'
|
|
566
|
+
),
|
|
567
|
+
},
|
|
568
|
+
description: details.typeDescription,
|
|
569
|
+
});
|
|
570
|
+
}
|
|
571
|
+
if (Util.OPTIONS.json) {
|
|
572
|
+
if (Util.OPTIONS.loggerLevel !== 'error') {
|
|
573
|
+
console.log(json); // eslint-disable-line no-console
|
|
574
|
+
}
|
|
575
|
+
return json;
|
|
576
|
+
}
|
|
534
577
|
|
|
535
578
|
const typeChoices = [];
|
|
536
579
|
for (const el in MetadataDefinitions) {
|
|
537
|
-
if (MetadataDefinitions[el].subTypes) {
|
|
580
|
+
if (MetadataDefinitions[el].subTypes && MetadataDefinitions[el].extendedSubTypes) {
|
|
538
581
|
// used for assets to show whats available by default
|
|
539
582
|
typeChoices.push({
|
|
540
583
|
Name: MetadataDefinitions[el].typeName,
|
|
@@ -545,9 +588,11 @@ const Cli = {
|
|
|
545
588
|
for (const subtype of MetadataDefinitions[el].subTypes) {
|
|
546
589
|
lastCountdown--;
|
|
547
590
|
const subTypeRetrieveByDefault =
|
|
591
|
+
Array.isArray(MetadataDefinitions[el].typeRetrieveByDefault) &&
|
|
548
592
|
MetadataDefinitions[el].typeRetrieveByDefault.includes(subtype);
|
|
593
|
+
|
|
549
594
|
const definition =
|
|
550
|
-
' ' + MetadataDefinitions[el].extendedSubTypes[subtype]
|
|
595
|
+
' ' + MetadataDefinitions[el].extendedSubTypes?.[subtype]?.join(', ');
|
|
551
596
|
typeChoices.push({
|
|
552
597
|
Name:
|
|
553
598
|
MetadataDefinitions[el].typeName.replace('-[Subtype]', ': ') + subtype,
|
|
@@ -577,7 +622,10 @@ const Cli = {
|
|
|
577
622
|
}
|
|
578
623
|
return 0;
|
|
579
624
|
});
|
|
580
|
-
|
|
625
|
+
if (Util.OPTIONS.loggerLevel !== 'error') {
|
|
626
|
+
console.table(typeChoices); // eslint-disable-line no-console
|
|
627
|
+
}
|
|
628
|
+
return json;
|
|
581
629
|
},
|
|
582
630
|
};
|
|
583
631
|
|
package/lib/util/devops.js
CHANGED
|
@@ -3,6 +3,7 @@ const File = require('./file');
|
|
|
3
3
|
const path = require('node:path');
|
|
4
4
|
const inquirer = require('inquirer');
|
|
5
5
|
const Util = require('./util');
|
|
6
|
+
const Cli = require('./cli');
|
|
6
7
|
const git = require('simple-git')();
|
|
7
8
|
const Builder = require('../Builder');
|
|
8
9
|
const MetadataType = require('../MetadataTypeInfo');
|
|
@@ -20,9 +21,10 @@ const DevOps = {
|
|
|
20
21
|
* @param {string} [range] git commit range
|
|
21
22
|
* @param {boolean} [saveToDeployDir] if true, copy metadata changes into deploy directory
|
|
22
23
|
* @param {string} [filterPaths] filter file paths that start with any specified path (comma separated)
|
|
24
|
+
* @param {number} [commitHistory] cli option to override default commit history value in config
|
|
23
25
|
* @returns {Promise.<TYPE.DeltaPkgItem[]>} -
|
|
24
26
|
*/
|
|
25
|
-
async getDeltaList(properties, range, saveToDeployDir, filterPaths) {
|
|
27
|
+
async getDeltaList(properties, range, saveToDeployDir, filterPaths, commitHistory) {
|
|
26
28
|
const rangeUserInput = range;
|
|
27
29
|
filterPaths = filterPaths
|
|
28
30
|
? filterPaths.split(',').map((filePath) =>
|
|
@@ -46,7 +48,7 @@ const DevOps = {
|
|
|
46
48
|
// Current commit is skipped due to no changes
|
|
47
49
|
const commits = await git.log([
|
|
48
50
|
'--skip=1',
|
|
49
|
-
`-${properties.options.deployment.commitHistory || 10}`,
|
|
51
|
+
`-${commitHistory || properties.options.deployment.commitHistory || 10}`,
|
|
50
52
|
]);
|
|
51
53
|
const display = commits.all.map((commit) => ({
|
|
52
54
|
name: commit.date + ' / ' + commit.message + ' / ' + commit.author_name,
|
|
@@ -104,7 +106,7 @@ const DevOps = {
|
|
|
104
106
|
}
|
|
105
107
|
|
|
106
108
|
// get metadata type from file name
|
|
107
|
-
file.type =
|
|
109
|
+
file.type = file.file.split('/')[3];
|
|
108
110
|
|
|
109
111
|
return file;
|
|
110
112
|
})
|
|
@@ -130,7 +132,14 @@ const DevOps = {
|
|
|
130
132
|
file.externalKey = null;
|
|
131
133
|
file.name = path.basename(file.file).split('.').shift();
|
|
132
134
|
} else {
|
|
133
|
-
|
|
135
|
+
// find the key in paths like:
|
|
136
|
+
// - retrieve/cred/bu/asset/block/016aecc7-7063-4b78-93f4-aa119ea933c7.asset-block-meta.html
|
|
137
|
+
// - retrieve/cred/bu/asset/message/003c1ef5-f538-473a-91da-26942024a64a/blocks/views.html.slots.[bottom-8frq7iw2k99].asset-message-meta.html
|
|
138
|
+
// - retrieve/cred/bu/query/03efd5f1-ba1f-487a-9c9a-36aeb2ae5192.query-meta.sql
|
|
139
|
+
file.externalKey =
|
|
140
|
+
file.type === 'asset'
|
|
141
|
+
? file.file.split('/')[5].split('.')[0] // assets have an additional folder level for their subtype
|
|
142
|
+
: file.file.split('/')[4].split('.')[0];
|
|
134
143
|
file.name = null;
|
|
135
144
|
}
|
|
136
145
|
|
|
@@ -207,8 +216,83 @@ const DevOps = {
|
|
|
207
216
|
Util.logger.info(`Saved report in ${path.join(directoryDeltaPkg, 'delta_package.md')}`);
|
|
208
217
|
|
|
209
218
|
// Copy filtered list of files into deploy directory
|
|
219
|
+
// only do that if we do not use templating
|
|
210
220
|
if (saveToDeployDir) {
|
|
211
|
-
|
|
221
|
+
// if templating is not used, we need to add related files to the delta package
|
|
222
|
+
const typeKeysMap = {};
|
|
223
|
+
/** @type {Object.<string, TYPE.BuObject>} */
|
|
224
|
+
const buObjects = {};
|
|
225
|
+
for (const file of delta) {
|
|
226
|
+
if (file.gitAction === 'delete' || file.type === 'folder') {
|
|
227
|
+
continue;
|
|
228
|
+
}
|
|
229
|
+
if (typeKeysMap[file.type]) {
|
|
230
|
+
typeKeysMap[file.type].push(file.externalKey);
|
|
231
|
+
} else {
|
|
232
|
+
typeKeysMap[file.type] = [file.externalKey];
|
|
233
|
+
}
|
|
234
|
+
if (!buObjects[`${file._credential}/${file._businessUnit}`]) {
|
|
235
|
+
buObjects[`${file._credential}/${file._businessUnit}`] =
|
|
236
|
+
await Cli.getCredentialObject(
|
|
237
|
+
properties,
|
|
238
|
+
`${file._credential}/${file._businessUnit}`
|
|
239
|
+
);
|
|
240
|
+
}
|
|
241
|
+
}
|
|
242
|
+
// a bit crude but works for now
|
|
243
|
+
for (const buObject of Object.values(buObjects)) {
|
|
244
|
+
for (const type in typeKeysMap) {
|
|
245
|
+
MetadataType[type].buObject = buObject;
|
|
246
|
+
MetadataType[type].properties = properties;
|
|
247
|
+
const additionalFiles = await MetadataType[type].getFilesToCommit(
|
|
248
|
+
typeKeysMap[type]
|
|
249
|
+
);
|
|
250
|
+
if (additionalFiles?.length) {
|
|
251
|
+
delta.push(
|
|
252
|
+
...additionalFiles
|
|
253
|
+
.map((filePath) => ({
|
|
254
|
+
file: path.normalize(filePath).split('\\').join('/'),
|
|
255
|
+
type,
|
|
256
|
+
gitAction: 'add/update',
|
|
257
|
+
}))
|
|
258
|
+
.filter(
|
|
259
|
+
// avoid adding files that we already have in the list
|
|
260
|
+
(addFile) =>
|
|
261
|
+
!delta.find((existFile) => existFile.file === addFile.file)
|
|
262
|
+
)
|
|
263
|
+
);
|
|
264
|
+
}
|
|
265
|
+
}
|
|
266
|
+
}
|
|
267
|
+
|
|
268
|
+
let responses;
|
|
269
|
+
if (!Util.skipInteraction) {
|
|
270
|
+
// deploy folder is in targets for definition creation
|
|
271
|
+
// recommend to purge their content first
|
|
272
|
+
responses = await inquirer.prompt([
|
|
273
|
+
{
|
|
274
|
+
type: 'confirm',
|
|
275
|
+
name: 'isPurgeDeployFolder',
|
|
276
|
+
message:
|
|
277
|
+
'Do you want to empty the deploy folder (ensures no files from previous deployments remain)?',
|
|
278
|
+
default: true,
|
|
279
|
+
},
|
|
280
|
+
]);
|
|
281
|
+
}
|
|
282
|
+
if (Util.skipInteraction || responses.isPurgeDeployFolder) {
|
|
283
|
+
// Clear output folder structure for selected sub-type
|
|
284
|
+
for (const buObject of Object.values(buObjects)) {
|
|
285
|
+
await File.remove(
|
|
286
|
+
File.normalizePath([
|
|
287
|
+
properties.directories.deploy,
|
|
288
|
+
buObject.credential,
|
|
289
|
+
buObject.businessUnit,
|
|
290
|
+
])
|
|
291
|
+
);
|
|
292
|
+
}
|
|
293
|
+
}
|
|
294
|
+
|
|
295
|
+
/** @type {TYPE.DeltaPkgItem[]} */
|
|
212
296
|
const copied = delta.map((file) =>
|
|
213
297
|
File.copyFile(
|
|
214
298
|
file.file,
|
|
@@ -253,9 +337,10 @@ const DevOps = {
|
|
|
253
337
|
* @param {TYPE.Mcdevrc} properties project config file
|
|
254
338
|
* @param {string} range git commit range
|
|
255
339
|
* @param {TYPE.DeltaPkgItem[]} [diffArr] instead of running git diff the method can also get a list of files to process
|
|
340
|
+
* @param {number} [commitHistory] cli option to override default commit history value in config
|
|
256
341
|
* @returns {Promise.<TYPE.DeltaPkgItem[]>} -
|
|
257
342
|
*/
|
|
258
|
-
async buildDeltaDefinitions(properties, range, diffArr) {
|
|
343
|
+
async buildDeltaDefinitions(properties, range, diffArr, commitHistory) {
|
|
259
344
|
const skipInteraction = Util.skipInteraction;
|
|
260
345
|
// check if sourceTargetMapping is valid
|
|
261
346
|
if (
|
|
@@ -311,7 +396,7 @@ const DevOps = {
|
|
|
311
396
|
|
|
312
397
|
const delta = Array.isArray(diffArr)
|
|
313
398
|
? diffArr
|
|
314
|
-
: await DevOps.getDeltaList(properties, range, false, sourceBU);
|
|
399
|
+
: await DevOps.getDeltaList(properties, range, false, sourceBU, commitHistory);
|
|
315
400
|
// If only chaing templating and buildDefinition if required
|
|
316
401
|
if (!delta || delta.length === 0) {
|
|
317
402
|
// info/error messages was printed by DevOps.createDeltaPkg() already
|
|
@@ -395,7 +480,7 @@ const DevOps = {
|
|
|
395
480
|
},
|
|
396
481
|
]);
|
|
397
482
|
}
|
|
398
|
-
if (skipInteraction || responses.
|
|
483
|
+
if (skipInteraction || responses.isPurgeDeployFolder) {
|
|
399
484
|
// Clear output folder structure for selected sub-type
|
|
400
485
|
await File.remove(File.normalizePath([properties.directories.deploy]));
|
|
401
486
|
}
|
package/lib/util/file.js
CHANGED
|
@@ -6,6 +6,7 @@ const fs = require('fs-extra');
|
|
|
6
6
|
const packageJson = require('../../package.json');
|
|
7
7
|
const path = require('node:path');
|
|
8
8
|
const prettier = require('prettier');
|
|
9
|
+
const beautyAmp = require('beauty-amp-core');
|
|
9
10
|
const Util = require('./util');
|
|
10
11
|
const updateNotifier = require('update-notifier');
|
|
11
12
|
|
|
@@ -52,7 +53,7 @@ const File = {
|
|
|
52
53
|
filterIllegalPathChars(path) {
|
|
53
54
|
return (
|
|
54
55
|
encodeURIComponent(path)
|
|
55
|
-
.
|
|
56
|
+
.replaceAll(/[*]/g, '_STAR_')
|
|
56
57
|
// convert space back
|
|
57
58
|
.split('%20')
|
|
58
59
|
.join(' ')
|
|
@@ -74,6 +75,9 @@ const File = {
|
|
|
74
75
|
// convert brackets back for asset blocks
|
|
75
76
|
.split('%5D')
|
|
76
77
|
.join(']')
|
|
78
|
+
// convert @ back for users
|
|
79
|
+
.split('%40')
|
|
80
|
+
.join('@')
|
|
77
81
|
);
|
|
78
82
|
},
|
|
79
83
|
|
|
@@ -86,7 +90,7 @@ const File = {
|
|
|
86
90
|
filterIllegalFilenames(filename) {
|
|
87
91
|
return (
|
|
88
92
|
encodeURIComponent(filename)
|
|
89
|
-
.
|
|
93
|
+
.replaceAll(/[*]/g, '_STAR_')
|
|
90
94
|
// convert space back
|
|
91
95
|
.split('%20')
|
|
92
96
|
.join(' ')
|
|
@@ -102,6 +106,9 @@ const File = {
|
|
|
102
106
|
// convert brackets back for asset blocks
|
|
103
107
|
.split('%5D')
|
|
104
108
|
.join(']')
|
|
109
|
+
// convert @ back for users
|
|
110
|
+
.split('%40')
|
|
111
|
+
.join('@')
|
|
105
112
|
);
|
|
106
113
|
},
|
|
107
114
|
|
|
@@ -162,12 +169,47 @@ const File = {
|
|
|
162
169
|
* @returns {Promise.<boolean>} Promise
|
|
163
170
|
*/
|
|
164
171
|
writePrettyToFile: async function (directory, filename, filetype, content, templateVariables) {
|
|
165
|
-
let formatted =
|
|
172
|
+
let formatted =
|
|
173
|
+
filetype === 'amp'
|
|
174
|
+
? this._beautify_beautyAmp(content)
|
|
175
|
+
: await this._beautify_prettier(directory, filename, filetype, content);
|
|
166
176
|
if (templateVariables) {
|
|
167
177
|
formatted = Util.replaceByObject(formatted, templateVariables);
|
|
168
178
|
}
|
|
169
179
|
return this.writeToFile(directory, filename, filetype, formatted);
|
|
170
180
|
},
|
|
181
|
+
/**
|
|
182
|
+
* helper for {@link File.writePrettyToFile}, applying beautyAmp onto given stringified content
|
|
183
|
+
*
|
|
184
|
+
* @param {string} content filecontent
|
|
185
|
+
* @returns {string} original string on error; formatted string on success
|
|
186
|
+
*/
|
|
187
|
+
_beautify_beautyAmp: function (content) {
|
|
188
|
+
// immutable at the moment:
|
|
189
|
+
const ampscript = {
|
|
190
|
+
capitalizeAndOrNot: true,
|
|
191
|
+
capitalizeIfFor: true,
|
|
192
|
+
capitalizeSet: true,
|
|
193
|
+
capitalizeVar: true,
|
|
194
|
+
maxParametersPerLine: 4,
|
|
195
|
+
};
|
|
196
|
+
// immutable at the moment:
|
|
197
|
+
const editor = {
|
|
198
|
+
insertSpaces: true,
|
|
199
|
+
tabSize: 4,
|
|
200
|
+
};
|
|
201
|
+
// logs trough console only for the moment.
|
|
202
|
+
const logs = {
|
|
203
|
+
loggerOn: false, // <= disable logging
|
|
204
|
+
};
|
|
205
|
+
try {
|
|
206
|
+
beautyAmp.setup(ampscript, editor, logs);
|
|
207
|
+
return beautyAmp.beautify(content);
|
|
208
|
+
} catch (ex) {
|
|
209
|
+
Util.logger.debug('File._beautify_beautyAmp:: error | ' + ex.message);
|
|
210
|
+
return content;
|
|
211
|
+
}
|
|
212
|
+
},
|
|
171
213
|
/**
|
|
172
214
|
* helper for {@link File.writePrettyToFile}, applying prettier onto given stringified content
|
|
173
215
|
* ! Important: run 'await File.initPrettier()' in your MetadataType.retrieve() once before hitting this
|
|
@@ -179,16 +221,16 @@ const File = {
|
|
|
179
221
|
* @returns {string} original string on error; formatted string on success
|
|
180
222
|
*/
|
|
181
223
|
_beautify_prettier: function (directory, filename, filetype, content) {
|
|
182
|
-
if (!FileFs.prettierConfig) {
|
|
183
|
-
// either no prettier config in project directory or initPrettier was not run before this
|
|
184
|
-
return content;
|
|
185
|
-
} else if (content.includes('%%[') || content.includes('%%=')) {
|
|
186
|
-
// in case we find AMPScript we need to abort beautifying as prettier
|
|
187
|
-
// will throw an error falsely assuming bad syntax
|
|
188
|
-
return content;
|
|
189
|
-
}
|
|
190
224
|
let formatted = '';
|
|
191
225
|
try {
|
|
226
|
+
if (!FileFs.prettierConfig) {
|
|
227
|
+
// either no prettier config in project directory or initPrettier was not run before this
|
|
228
|
+
return content;
|
|
229
|
+
} else if (content.includes('%%[') || content.includes('%%=')) {
|
|
230
|
+
// in case we find AMPScript we need to abort beautifying as prettier
|
|
231
|
+
// will throw an error falsely assuming bad syntax
|
|
232
|
+
return this._beautify_beautyAmp(content);
|
|
233
|
+
}
|
|
192
234
|
// load the right prettier config relative to our file
|
|
193
235
|
switch (filetype) {
|
|
194
236
|
case 'htm':
|
|
@@ -257,7 +299,7 @@ const File = {
|
|
|
257
299
|
directory,
|
|
258
300
|
filename + '.error',
|
|
259
301
|
'log',
|
|
260
|
-
`Error Log\nParser: ${FileFs.prettierConfig.parser}\n${ex.message.
|
|
302
|
+
`Error Log\nParser: ${FileFs.prettierConfig.parser}\n${ex.message.replaceAll(
|
|
261
303
|
/[\u001B\u009B][[()#;?]*(?:[0-9]{1,4}(?:;[0-9]{0,4})*)?[0-9A-ORZcf-nqry=><]/g,
|
|
262
304
|
|
|
263
305
|
''
|
|
@@ -477,7 +519,7 @@ const File = {
|
|
|
477
519
|
*/
|
|
478
520
|
async initPrettier(filetype) {
|
|
479
521
|
if (FileFs.prettierConfig === null) {
|
|
480
|
-
filetype
|
|
522
|
+
filetype ||= 'html';
|
|
481
523
|
try {
|
|
482
524
|
// pass in project dir with fake index.html to avoid "no parser" error
|
|
483
525
|
// by using process.cwd we are limiting ourselves to a config in the project root
|
package/lib/util/init.config.js
CHANGED
|
@@ -337,8 +337,7 @@ const Init = {
|
|
|
337
337
|
'files',
|
|
338
338
|
fileName
|
|
339
339
|
);
|
|
340
|
-
boilerplateFileContent
|
|
341
|
-
boilerplateFileContent || (await File.readFile(boilerplateFileName, 'utf8'));
|
|
340
|
+
boilerplateFileContent ||= await File.readFile(boilerplateFileName, 'utf8');
|
|
342
341
|
|
|
343
342
|
if (await File.pathExists(fileName)) {
|
|
344
343
|
const existingFileContent = await File.readFile(fileName, 'utf8');
|
package/lib/util/init.npm.js
CHANGED
|
@@ -43,8 +43,8 @@ const Init = {
|
|
|
43
43
|
repoName ||
|
|
44
44
|
currentFolderName
|
|
45
45
|
.toLowerCase()
|
|
46
|
-
.
|
|
47
|
-
.
|
|
46
|
+
.replaceAll(/[^a-z0-9 ]/gi, '')
|
|
47
|
+
.replaceAll(/ /gi, '-');
|
|
48
48
|
projectPackageJson = { name: standardNpmName };
|
|
49
49
|
this._getDefaultPackageJson(projectPackageJson);
|
|
50
50
|
await File.writeToFile('./', 'package', 'json', JSON.stringify(projectPackageJson));
|
|
@@ -128,7 +128,7 @@ const Init = {
|
|
|
128
128
|
* @returns {Promise.<{script: object, author: string, license: string}>} extended currentContent
|
|
129
129
|
*/
|
|
130
130
|
async _getDefaultPackageJson(currentContent) {
|
|
131
|
-
currentContent
|
|
131
|
+
currentContent ||= {};
|
|
132
132
|
// #1 scripts
|
|
133
133
|
const predefinedCommandList = {
|
|
134
134
|
build: 'sfmc-build all',
|
package/lib/util/util.js
CHANGED
|
@@ -20,7 +20,8 @@ const Util = {
|
|
|
20
20
|
/** @type {TYPE.skipInteraction} */
|
|
21
21
|
skipInteraction: false,
|
|
22
22
|
packageJsonMcdev: packageJsonMcdev,
|
|
23
|
-
|
|
23
|
+
OPTIONS: {},
|
|
24
|
+
changedKeysMap: {},
|
|
24
25
|
/**
|
|
25
26
|
* helper that allows filtering an object by its keys
|
|
26
27
|
*
|
|
@@ -286,7 +287,7 @@ const Util = {
|
|
|
286
287
|
|
|
287
288
|
sortable.sort((a, b) => b[1].length - a[1].length);
|
|
288
289
|
for (const pair of sortable) {
|
|
289
|
-
const escVal = pair[1].toString().
|
|
290
|
+
const escVal = pair[1].toString().replaceAll(/[-/\\^$*+?.()|[\]{}]/g, '\\$&');
|
|
290
291
|
const regString = new RegExp(escVal, 'g');
|
|
291
292
|
str = str.replace(regString, '{{{' + pair[0] + '}}}');
|
|
292
293
|
}
|
|
@@ -418,20 +419,24 @@ const Util = {
|
|
|
418
419
|
* @returns {string} output of command if hideOutput is true
|
|
419
420
|
*/
|
|
420
421
|
execSync(cmd, args, hideOutput) {
|
|
421
|
-
args
|
|
422
|
+
args ||= [];
|
|
422
423
|
Util.logger.info('⚡ ' + cmd + ' ' + args.join(' '));
|
|
423
424
|
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
425
|
+
try {
|
|
426
|
+
if (hideOutput) {
|
|
427
|
+
// no output displayed to user but instead returned to parsed elsewhere
|
|
428
|
+
return child_process
|
|
429
|
+
.execSync(cmd + ' ' + args.join(' '))
|
|
430
|
+
.toString()
|
|
431
|
+
.trim();
|
|
432
|
+
} else {
|
|
433
|
+
// the following options ensure the user sees the same output and
|
|
434
|
+
// interaction options as if the command was manually run
|
|
435
|
+
child_process.execSync(cmd + ' ' + args.join(' '), { stdio: [0, 1, 2] });
|
|
436
|
+
return null;
|
|
437
|
+
}
|
|
438
|
+
} catch {
|
|
439
|
+
// avoid errors from execSync to bubble up
|
|
435
440
|
}
|
|
436
441
|
},
|
|
437
442
|
/**
|
|
@@ -469,23 +474,27 @@ const Util = {
|
|
|
469
474
|
if (argv.silent) {
|
|
470
475
|
// only errors printed to CLI
|
|
471
476
|
Util.logger.level = 'error';
|
|
477
|
+
Util.OPTIONS.loggerLevel = 'error';
|
|
472
478
|
Util.loggerTransports.console.level = 'error';
|
|
473
479
|
Util.logger.debug('CLI logger set to: silent');
|
|
474
480
|
} else if (argv.verbose) {
|
|
475
481
|
// chatty user cli logs
|
|
476
482
|
Util.logger.level = 'verbose';
|
|
483
|
+
Util.OPTIONS.loggerLevel = 'verbose';
|
|
477
484
|
Util.loggerTransports.console.level = 'verbose';
|
|
478
485
|
Util.logger.debug('CLI logger set to: verbose');
|
|
479
486
|
} else {
|
|
480
487
|
// default user cli logs
|
|
481
488
|
// TODO to be switched to "warn" when cli-process is integrated
|
|
482
489
|
Util.logger.level = 'info';
|
|
490
|
+
Util.OPTIONS.loggerLevel = 'info';
|
|
483
491
|
Util.loggerTransports.console.level = 'info';
|
|
484
492
|
Util.logger.debug('CLI logger set to: info / default');
|
|
485
493
|
}
|
|
486
494
|
if (argv.debug) {
|
|
487
495
|
// enables developer output & features. no change to actual logs
|
|
488
496
|
Util.logger.level = 'debug';
|
|
497
|
+
Util.OPTIONS.loggerLevel = 'debug';
|
|
489
498
|
Util.loggerTransports.console.level = 'debug';
|
|
490
499
|
Util.logger.debug('CLI logger set to: debug');
|
|
491
500
|
}
|
|
@@ -587,6 +596,51 @@ const Util = {
|
|
|
587
596
|
setTimeout(resolve, ms);
|
|
588
597
|
});
|
|
589
598
|
},
|
|
599
|
+
/**
|
|
600
|
+
* helper for {@link Asset._extractCode} and {@link Script.prepExtractedCode} to determine if a code block is a valid SSJS block
|
|
601
|
+
*
|
|
602
|
+
* @example the following is invalid:
|
|
603
|
+
* <script runat="server">
|
|
604
|
+
* // 1
|
|
605
|
+
* </script>
|
|
606
|
+
* <script runat="server">
|
|
607
|
+
* // 2
|
|
608
|
+
* </script>
|
|
609
|
+
*
|
|
610
|
+
* the following is valid:
|
|
611
|
+
* <script runat="server">
|
|
612
|
+
* // 3
|
|
613
|
+
* </script>
|
|
614
|
+
* @param {string} code code block to check
|
|
615
|
+
* @returns {string} the SSJS code if code block is a valid SSJS block, otherwise null
|
|
616
|
+
*/
|
|
617
|
+
getSsjs(code) {
|
|
618
|
+
if (!code) {
|
|
619
|
+
return null;
|
|
620
|
+
}
|
|
621
|
+
// \s* whitespace characters, zero or more times
|
|
622
|
+
// [^>]*? any character that is not a >, zero or more times, un-greedily
|
|
623
|
+
// (.*) capture any character, zero or more times
|
|
624
|
+
// /ms multiline and dotall flags
|
|
625
|
+
// ideally the code looks like <script runat="server">...</script>
|
|
626
|
+
const scriptRegex = /^<\s*script [^>]*?>(.*)<\/\s*script\s*>$/ms;
|
|
627
|
+
code = code.trim();
|
|
628
|
+
const regexMatches = scriptRegex.exec(code);
|
|
629
|
+
if (regexMatches?.length > 1) {
|
|
630
|
+
// script found
|
|
631
|
+
/* eslint-disable unicorn/prefer-ternary */
|
|
632
|
+
if (regexMatches[1].includes('<script')) {
|
|
633
|
+
// nested script found
|
|
634
|
+
return null;
|
|
635
|
+
} else {
|
|
636
|
+
// no nested script found
|
|
637
|
+
return regexMatches[1];
|
|
638
|
+
}
|
|
639
|
+
/* eslint-enable unicorn/prefer-ternary */
|
|
640
|
+
}
|
|
641
|
+
// no script found
|
|
642
|
+
return null;
|
|
643
|
+
},
|
|
590
644
|
};
|
|
591
645
|
/**
|
|
592
646
|
* wrapper around our standard winston logging to console and logfile
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "mcdev",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "5.0.0",
|
|
4
4
|
"description": "Accenture Salesforce Marketing Cloud DevTools",
|
|
5
5
|
"author": "Accenture: joern.berkefeld, douglas.midgley, robert.zimmermann, maciej.barnas",
|
|
6
6
|
"license": "MIT",
|
|
@@ -35,7 +35,7 @@
|
|
|
35
35
|
"mcdev": "./lib/cli.js"
|
|
36
36
|
},
|
|
37
37
|
"engines": {
|
|
38
|
-
"node": ">=
|
|
38
|
+
"node": ">=15.0.0"
|
|
39
39
|
},
|
|
40
40
|
"scripts": {
|
|
41
41
|
"start": "node lib/cli.js",
|
|
@@ -51,8 +51,8 @@
|
|
|
51
51
|
"upgrade": "npm-check --update",
|
|
52
52
|
"manual-prepare": "husky install",
|
|
53
53
|
"lint-and-test": "run-s lint test",
|
|
54
|
-
"test": "mocha",
|
|
55
|
-
"coverage": "nyc
|
|
54
|
+
"test": "mocha --reporter-option maxDiffSize=25000",
|
|
55
|
+
"coverage": "nyc npm run test",
|
|
56
56
|
"version:major": "npm version --no-commit-hooks major",
|
|
57
57
|
"version:minor": "npm version --no-commit-hooks minor",
|
|
58
58
|
"version:patch": "npm version --no-commit-hooks patch"
|
|
@@ -65,14 +65,14 @@
|
|
|
65
65
|
"console.table": "0.10.0",
|
|
66
66
|
"deep-equal": "2.1.0",
|
|
67
67
|
"fs-extra": "11.1.0",
|
|
68
|
-
"inquirer": "8.2.
|
|
68
|
+
"inquirer": "8.2.5",
|
|
69
69
|
"json-to-table": "4.2.1",
|
|
70
70
|
"mustache": "4.2.0",
|
|
71
71
|
"p-limit": "3.1.0",
|
|
72
|
-
"prettier": "2.8.
|
|
73
|
-
"prettier-plugin-sql": "0.
|
|
74
|
-
"semver": "7.
|
|
75
|
-
"sfmc-sdk": "0.
|
|
72
|
+
"prettier": "2.8.8",
|
|
73
|
+
"prettier-plugin-sql": "0.14.0",
|
|
74
|
+
"semver": "7.5.0",
|
|
75
|
+
"sfmc-sdk": "1.0.0",
|
|
76
76
|
"simple-git": "3.16.0",
|
|
77
77
|
"toposort": "2.0.2",
|
|
78
78
|
"update-notifier": "5.1.0",
|
|
@@ -81,19 +81,20 @@
|
|
|
81
81
|
},
|
|
82
82
|
"devDependencies": {
|
|
83
83
|
"assert": "2.0.0",
|
|
84
|
-
"axios-mock-adapter": "1.21.
|
|
84
|
+
"axios-mock-adapter": "1.21.3",
|
|
85
85
|
"chai": "4.3.7",
|
|
86
86
|
"chai-files": "1.4.0",
|
|
87
|
-
"eslint": "8.
|
|
88
|
-
"eslint-config-prettier": "8.
|
|
87
|
+
"eslint": "8.39.0",
|
|
88
|
+
"eslint-config-prettier": "8.7.0",
|
|
89
89
|
"eslint-config-ssjs": "1.1.11",
|
|
90
|
-
"eslint-plugin-jsdoc": "
|
|
90
|
+
"eslint-plugin-jsdoc": "43.1.1",
|
|
91
91
|
"eslint-plugin-mocha": "10.1.0",
|
|
92
92
|
"eslint-plugin-prettier": "4.2.1",
|
|
93
|
-
"eslint-plugin-unicorn": "
|
|
93
|
+
"eslint-plugin-unicorn": "46.0.0",
|
|
94
|
+
"fast-xml-parser": "4.2.2",
|
|
94
95
|
"husky": "8.0.3",
|
|
95
96
|
"jsdoc-to-markdown": "8.0.0",
|
|
96
|
-
"lint-staged": "13.
|
|
97
|
+
"lint-staged": "13.2.0",
|
|
97
98
|
"mocha": "10.2.0",
|
|
98
99
|
"mock-fs": "5.2.0",
|
|
99
100
|
"npm-check": "6.0.1",
|