From eed35d30fbd6c51bec07d38edbc7026391ab146a Mon Sep 17 00:00:00 2001 From: Sudip Paul <67197965+ItsSudip@users.noreply.github.com> Date: Fri, 18 Oct 2024 11:10:25 +0530 Subject: [PATCH 1/2] feat: add missing fields on the pinterest_tag mapping (#3798) * feat: add missing fields on the pinterest_tag mapping * chore: fix test cases * chore(deps): bump actions/checkout from 4.1.1 to 4.2.1 (#3796) Bumps [actions/checkout](https://github.com/actions/checkout) from 4.1.1 to 4.2.1. - [Release notes](https://github.com/actions/checkout/releases) - [Changelog](https://github.com/actions/checkout/blob/main/CHANGELOG.md) - [Commits](https://github.com/actions/checkout/compare/v4.1.1...v4.2.1) --- updated-dependencies: - dependency-name: actions/checkout dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> * chore(deps): bump actions/setup-node from 4.0.3 to 4.0.4 (#3749) Bumps [actions/setup-node](https://github.com/actions/setup-node) from 4.0.3 to 4.0.4. - [Release notes](https://github.com/actions/setup-node/releases) - [Commits](https://github.com/actions/setup-node/compare/v4.0.3...v4.0.4) --- updated-dependencies: - dependency-name: actions/setup-node dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Sankeerth * fix: heap userId extraction (#3801) * chore: remove redundant old implementation (#3802) * chore: remove redundant old implementation * chore: remove test cases related to pinterest_tag * chore: fix test cases * chore: fix lint issue * chore: fix lint issue again * Should filter out falsey reserved attributes from Intercom destination (#3767) * Should filter out reserved attributes from Intercom destination even if they are falsey * Fix presence check to allow null values --------- Co-authored-by: Manish Kumar <144022547+manish339k@users.noreply.github.com> * chore(deps): bump koa and @types/koa (#3709) Bumps [koa](https://github.com/koajs/koa) and [@types/koa](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/koa). These dependencies needed to be updated together. Updates `koa` from 2.15.0 to 2.15.3 - [Changelog](https://github.com/koajs/koa/blob/2.15.3/History.md) - [Commits](https://github.com/koajs/koa/compare/2.15.0...2.15.3) Updates `@types/koa` from 2.13.12 to 2.15.0 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/koa) --- updated-dependencies: - dependency-name: koa dependency-type: direct:production update-type: version-update:semver-patch - dependency-name: "@types/koa" dependency-type: direct:development update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Yashasvi Bajpai <33063622+yashasvibajpai@users.noreply.github.com> * fix: populate source destination info env set properly (#3806) --------- Signed-off-by: dependabot[bot] Co-authored-by: Sankeerth Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Dilip Kola <33080863+koladilip@users.noreply.github.com> Co-authored-by: shrouti1507 <60211312+shrouti1507@users.noreply.github.com> Co-authored-by: Will Co-authored-by: Manish Kumar <144022547+manish339k@users.noreply.github.com> Co-authored-by: Yashasvi Bajpai <33063622+yashasvibajpai@users.noreply.github.com> Co-authored-by: Akash Chetty --- .github/workflows/build-pr-artifacts.yml | 2 +- .github/workflows/build-push-docker-image.yml | 6 +- .github/workflows/commitlint.yml | 4 +- .github/workflows/component-test-report.yml | 4 +- .github/workflows/draft-new-release.yml | 4 +- .../dt-test-and-report-code-coverage.yml | 4 +- .github/workflows/housekeeping.yml | 2 +- .github/workflows/prepare-for-dev-deploy.yml | 2 +- .../workflows/prepare-for-prod-dt-deploy.yml | 4 +- .../workflows/prepare-for-prod-ut-deploy.yml | 4 +- .../workflows/prepare-for-staging-deploy.yml | 4 +- .github/workflows/publish-new-release.yml | 4 +- .github/workflows/slack-notify.yml | 2 +- .github/workflows/ut-tests.yml | 4 +- .github/workflows/verify-server-start.yml | 4 +- .github/workflows/verify.yml | 4 +- package-lock.json | 14 +- package.json | 4 +- src/cdk/v2/destinations/intercom/utils.js | 2 +- .../v2/destinations/intercom/utils.test.js | 12 + .../v2/destinations/pinterest_tag/config.js | 19 + .../pinterest_tag/procWorkflow.yaml | 24 +- .../pinterest_tag/rtWorkflow.yaml | 2 +- .../v2/destinations/pinterest_tag/utils.js | 150 +++++++ .../destinations/pinterest_tag/utils.test.js | 2 +- src/v0/destinations/pinterest_tag/config.js | 31 -- .../data/pinterestCommonConfig.json | 61 --- .../data/pinterestCustomConfig.json | 38 -- .../data/pinterestUserConfig.json | 93 ---- .../destinations/pinterest_tag/transform.js | 202 --------- src/v0/destinations/pinterest_tag/utils.js | 416 ------------------ src/warehouse/index.js | 2 +- test/__tests__/data/pinterest_tag_input.json | 15 + test/__tests__/data/pinterest_tag_output.json | 61 +++ .../pinterest_tag_router_batch_output.json | 104 ++++- .../data/pinterest_tag_router_input.json | 16 + .../data/pinterest_tag_router_output.json | 72 +++ test/__tests__/pinterestConversion.test.js | 54 --- test/apitests/service.api.test.ts | 89 ---- .../pinterest_tag/processor/data.ts | 200 +++++++-- .../destinations/pinterest_tag/router/data.ts | 148 ++++++- .../destinations/pinterest_tag/step/data.ts | 286 ++++++++++-- 42 files changed, 1034 insertions(+), 1141 deletions(-) create mode 100644 src/cdk/v2/destinations/pinterest_tag/config.js create mode 100644 src/cdk/v2/destinations/pinterest_tag/utils.js rename src/{v0 => cdk/v2}/destinations/pinterest_tag/utils.test.js (97%) delete mode 100644 src/v0/destinations/pinterest_tag/config.js delete mode 100644 src/v0/destinations/pinterest_tag/data/pinterestCommonConfig.json delete mode 100644 src/v0/destinations/pinterest_tag/data/pinterestCustomConfig.json delete mode 100644 src/v0/destinations/pinterest_tag/data/pinterestUserConfig.json delete mode 100644 src/v0/destinations/pinterest_tag/transform.js delete mode 100644 src/v0/destinations/pinterest_tag/utils.js delete mode 100644 test/__tests__/pinterestConversion.test.js diff --git a/.github/workflows/build-pr-artifacts.yml b/.github/workflows/build-pr-artifacts.yml index f6aaa189404..46670fba846 100644 --- a/.github/workflows/build-pr-artifacts.yml +++ b/.github/workflows/build-pr-artifacts.yml @@ -22,7 +22,7 @@ jobs: tag_name_ut: ${{ steps.gen_tag_names.outputs.tag_name_ut }} steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 diff --git a/.github/workflows/build-push-docker-image.yml b/.github/workflows/build-push-docker-image.yml index cffb5f91da4..acc06496c27 100644 --- a/.github/workflows/build-push-docker-image.yml +++ b/.github/workflows/build-push-docker-image.yml @@ -64,7 +64,7 @@ jobs: should_execute_tests: ${{ steps.processing.outputs.should_execute_tests }} steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 - id: files @@ -92,7 +92,7 @@ jobs: needs: [get_sha, get_changed_files] steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: ref: ${{ needs.get_sha.outputs.sha }} fetch-depth: 1 @@ -145,7 +145,7 @@ jobs: needs: [get_sha, get_changed_files] steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: ref: ${{ needs.get_sha.outputs.sha }} fetch-depth: 1 diff --git a/.github/workflows/commitlint.yml b/.github/workflows/commitlint.yml index 7f6d068e157..74e7f0e6041 100644 --- a/.github/workflows/commitlint.yml +++ b/.github/workflows/commitlint.yml @@ -11,12 +11,12 @@ jobs: runs-on: ubuntu-latest steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 0 - name: Setup Node - uses: actions/setup-node@v4.0.3 + uses: actions/setup-node@v4.0.4 with: node-version-file: '.nvmrc' cache: 'npm' diff --git a/.github/workflows/component-test-report.yml b/.github/workflows/component-test-report.yml index 02df1478d4f..8d739c5aee6 100644 --- a/.github/workflows/component-test-report.yml +++ b/.github/workflows/component-test-report.yml @@ -27,12 +27,12 @@ jobs: aws-region: us-east-1 - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 - name: Setup Node - uses: actions/setup-node@v4.0.3 + uses: actions/setup-node@v4.0.4 with: node-version-file: '.nvmrc' cache: 'npm' diff --git a/.github/workflows/draft-new-release.yml b/.github/workflows/draft-new-release.yml index 82174d1d724..602ded980fd 100644 --- a/.github/workflows/draft-new-release.yml +++ b/.github/workflows/draft-new-release.yml @@ -11,12 +11,12 @@ jobs: if: (github.ref == 'refs/heads/develop' || startsWith(github.ref, 'refs/heads/hotfix/')) && (github.actor == 'ItsSudip' || github.actor == 'krishna2020' || github.actor == 'saikumarrs' || github.actor == 'sandeepdsvs' || github.actor == 'koladilip' || github.actor == 'shrouti1507' || github.actor == 'anantjain45823' || github.actor == 'chandumlg' || github.actor == 'mihir-4116' || github.actor == 'yashasvibajpai' || github.actor == 'sanpj2292' || github.actor == 'utsabc') && (github.triggering_actor == 'ItsSudip' || github.triggering_actor == 'krishna2020' || github.triggering_actor == 'koladilip' || github.triggering_actor == 'saikumarrs' || github.triggering_actor == 'sandeepdsvs' || github.triggering_actor == 'shrouti1507' || github.triggering_actor == 'anantjain45823' || github.triggering_actor == 'chandumlg' || github.triggering_actor == 'mihir-4116' || github.triggering_actor == 'yashasvibajpai' || github.triggering_actor == 'sanpj2292' || github.triggering_actor == 'utsabc') steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 0 - name: Setup Node - uses: actions/setup-node@v4.0.3 + uses: actions/setup-node@v4.0.4 with: node-version-file: '.nvmrc' cache: 'npm' diff --git a/.github/workflows/dt-test-and-report-code-coverage.yml b/.github/workflows/dt-test-and-report-code-coverage.yml index 85625a1558e..86963b62703 100644 --- a/.github/workflows/dt-test-and-report-code-coverage.yml +++ b/.github/workflows/dt-test-and-report-code-coverage.yml @@ -31,12 +31,12 @@ jobs: tests_run_outcome: ${{steps.run_tests.outcome}} steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 - name: Setup Node - uses: actions/setup-node@v4.0.3 + uses: actions/setup-node@v4.0.4 with: node-version-file: '.nvmrc' cache: 'npm' diff --git a/.github/workflows/housekeeping.yml b/.github/workflows/housekeeping.yml index 388b80c15f5..bd66a936899 100644 --- a/.github/workflows/housekeeping.yml +++ b/.github/workflows/housekeeping.yml @@ -33,7 +33,7 @@ jobs: runs-on: ubuntu-latest steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 - name: Delete Old Branches uses: beatlabs/delete-old-branches-action@v0.0.10 diff --git a/.github/workflows/prepare-for-dev-deploy.yml b/.github/workflows/prepare-for-dev-deploy.yml index a1fdda8ccda..b5482bcddf1 100644 --- a/.github/workflows/prepare-for-dev-deploy.yml +++ b/.github/workflows/prepare-for-dev-deploy.yml @@ -32,7 +32,7 @@ jobs: tag_name_ut: ${{ steps.gen_tag_names.outputs.tag_name_ut }} steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 diff --git a/.github/workflows/prepare-for-prod-dt-deploy.yml b/.github/workflows/prepare-for-prod-dt-deploy.yml index 8e589f5b208..0a61a359bfa 100644 --- a/.github/workflows/prepare-for-prod-dt-deploy.yml +++ b/.github/workflows/prepare-for-prod-dt-deploy.yml @@ -32,7 +32,7 @@ jobs: tag_name_ut: ${{ steps.gen_tag_names.outputs.tag_name_ut }} steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 @@ -71,7 +71,7 @@ jobs: TF_IMAGE_REPOSITORY: rudderstack/rudder-transformer steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 diff --git a/.github/workflows/prepare-for-prod-ut-deploy.yml b/.github/workflows/prepare-for-prod-ut-deploy.yml index 468307b94a9..3053979b3e0 100644 --- a/.github/workflows/prepare-for-prod-ut-deploy.yml +++ b/.github/workflows/prepare-for-prod-ut-deploy.yml @@ -31,7 +31,7 @@ jobs: tag_name_ut: ${{ steps.gen_tag_names.outputs.tag_name_ut }} steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 @@ -74,7 +74,7 @@ jobs: TF_IMAGE_REPOSITORY: rudderstack/rudder-transformer steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 diff --git a/.github/workflows/prepare-for-staging-deploy.yml b/.github/workflows/prepare-for-staging-deploy.yml index 60a6238aa8e..8eeafc376ee 100644 --- a/.github/workflows/prepare-for-staging-deploy.yml +++ b/.github/workflows/prepare-for-staging-deploy.yml @@ -24,7 +24,7 @@ jobs: tag_name_ut: ${{ steps.gen_tag_names.outputs.tag_name_ut }} steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 @@ -82,7 +82,7 @@ jobs: UT_TAG_NAME: ${{ needs.generate-tag-names.outputs.tag_name_ut }} steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 diff --git a/.github/workflows/publish-new-release.yml b/.github/workflows/publish-new-release.yml index ee9f28e2350..a91a1e2b22b 100644 --- a/.github/workflows/publish-new-release.yml +++ b/.github/workflows/publish-new-release.yml @@ -25,12 +25,12 @@ jobs: echo "release_version=$version" >> $GITHUB_OUTPUT - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 0 - name: Setup Node - uses: actions/setup-node@v4.0.3 + uses: actions/setup-node@v4.0.4 with: node-version-file: '.nvmrc' cache: 'npm' diff --git a/.github/workflows/slack-notify.yml b/.github/workflows/slack-notify.yml index 1c5dbdbc063..3c4223752b4 100644 --- a/.github/workflows/slack-notify.yml +++ b/.github/workflows/slack-notify.yml @@ -16,7 +16,7 @@ jobs: if: ${{ inputs.should_notify }} steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 - name: notify uses: slackapi/slack-github-action@v1.27.0 diff --git a/.github/workflows/ut-tests.yml b/.github/workflows/ut-tests.yml index b825bdb9d3f..34442f83c55 100644 --- a/.github/workflows/ut-tests.yml +++ b/.github/workflows/ut-tests.yml @@ -25,12 +25,12 @@ jobs: run: go install sigs.k8s.io/kind@v0.17.0 - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 - name: Setup Node - uses: actions/setup-node@v4.0.3 + uses: actions/setup-node@v4.0.4 with: node-version-file: '.nvmrc' cache: 'npm' diff --git a/.github/workflows/verify-server-start.yml b/.github/workflows/verify-server-start.yml index f87ed57eb8b..5f9c247428a 100644 --- a/.github/workflows/verify-server-start.yml +++ b/.github/workflows/verify-server-start.yml @@ -14,12 +14,12 @@ jobs: steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: fetch-depth: 1 - name: Setup Node - uses: actions/setup-node@v4.0.3 + uses: actions/setup-node@v4.0.4 with: node-version-file: '.nvmrc' cache: 'npm' diff --git a/.github/workflows/verify.yml b/.github/workflows/verify.yml index 0d389f0e555..115cad42488 100644 --- a/.github/workflows/verify.yml +++ b/.github/workflows/verify.yml @@ -14,13 +14,13 @@ jobs: steps: - name: Checkout - uses: actions/checkout@v4.1.1 + uses: actions/checkout@v4.2.1 with: # Make sure the actual branch is checked out when running on pull requests ref: ${{ github.head_ref }} - name: Setup Node - uses: actions/setup-node@v4.0.3 + uses: actions/setup-node@v4.0.4 with: node-version-file: .nvmrc cache: 'npm' diff --git a/package-lock.json b/package-lock.json index a4295bd74c3..d3b578f6856 100644 --- a/package-lock.json +++ b/package-lock.json @@ -47,7 +47,7 @@ "json-size": "^1.0.0", "jsontoxml": "^1.0.1", "jstoxml": "^5.0.2", - "koa": "^2.14.1", + "koa": "^2.15.3", "koa-bodyparser": "^4.4.0", "koa2-swagger-ui": "^5.7.0", "libphonenumber-js": "^1.11.1", @@ -83,7 +83,7 @@ "@types/fast-json-stable-stringify": "^2.1.0", "@types/jest": "^29.5.1", "@types/jsonpath": "^0.2.4", - "@types/koa": "^2.13.6", + "@types/koa": "^2.15.0", "@types/koa-bodyparser": "^4.3.10", "@types/lodash": "^4.14.197", "@types/node": "^20.2.5", @@ -7791,8 +7791,9 @@ "license": "MIT" }, "node_modules/@types/koa": { - "version": "2.13.12", - "license": "MIT", + "version": "2.15.0", + "resolved": "https://registry.npmjs.org/@types/koa/-/koa-2.15.0.tgz", + "integrity": "sha512-7QFsywoE5URbuVnG3loe03QXuGajrnotr3gQkXcEBShORai23MePfFYdhz90FEtBBpkyIYQbVD+evKtloCgX3g==", "dependencies": { "@types/accepts": "*", "@types/content-disposition": "*", @@ -16327,8 +16328,9 @@ } }, "node_modules/koa": { - "version": "2.15.0", - "license": "MIT", + "version": "2.15.3", + "resolved": "https://registry.npmjs.org/koa/-/koa-2.15.3.tgz", + "integrity": "sha512-j/8tY9j5t+GVMLeioLaxweJiKUayFhlGqNTzf2ZGwL0ZCQijd2RLHK0SLW5Tsko8YyyqCZC2cojIb0/s62qTAg==", "dependencies": { "accepts": "^1.3.5", "cache-content-type": "^1.0.0", diff --git a/package.json b/package.json index 6b41457633a..f5d44d8e2b2 100644 --- a/package.json +++ b/package.json @@ -92,7 +92,7 @@ "json-size": "^1.0.0", "jsontoxml": "^1.0.1", "jstoxml": "^5.0.2", - "koa": "^2.14.1", + "koa": "^2.15.3", "koa-bodyparser": "^4.4.0", "koa2-swagger-ui": "^5.7.0", "libphonenumber-js": "^1.11.1", @@ -128,7 +128,7 @@ "@types/fast-json-stable-stringify": "^2.1.0", "@types/jest": "^29.5.1", "@types/jsonpath": "^0.2.4", - "@types/koa": "^2.13.6", + "@types/koa": "^2.15.0", "@types/koa-bodyparser": "^4.3.10", "@types/lodash": "^4.14.197", "@types/node": "^20.2.5", diff --git a/src/cdk/v2/destinations/intercom/utils.js b/src/cdk/v2/destinations/intercom/utils.js index 22af726e846..a75f8155aff 100644 --- a/src/cdk/v2/destinations/intercom/utils.js +++ b/src/cdk/v2/destinations/intercom/utils.js @@ -257,7 +257,7 @@ const filterCustomAttributes = (payload, type, destination, message) => { let customAttributes = { ...get(payload, 'custom_attributes') }; if (customAttributes) { ReservedAttributesList.forEach((trait) => { - if (customAttributes[trait]) delete customAttributes[trait]; + if (trait in customAttributes) delete customAttributes[trait]; }); if (isDefinedAndNotNull(customAttributes) && Object.keys(customAttributes).length > 0) { customAttributes = diff --git a/src/cdk/v2/destinations/intercom/utils.test.js b/src/cdk/v2/destinations/intercom/utils.test.js index c2bf3f8e892..e2c1fb9a072 100644 --- a/src/cdk/v2/destinations/intercom/utils.test.js +++ b/src/cdk/v2/destinations/intercom/utils.test.js @@ -318,6 +318,18 @@ describe('filterCustomAttributes utility test', () => { expect(result).toBeUndefined(); }); + it('Should filter out custom attributes that are reserved attributes and that are false', () => { + const payload = { custom_attributes: { unsubscribedFromEmails: false } }; + const result = filterCustomAttributes(payload, 'user', { Config: { apiVersion: 'v2' } }); + expect(result).toBeUndefined(); + }); + + it('Should filter out custom attributes that are reserved attributes and that are null', () => { + const payload = { custom_attributes: { unsubscribedFromEmails: null } }; + const result = filterCustomAttributes(payload, 'user', { Config: { apiVersion: 'v2' } }); + expect(result).toBeUndefined(); + }); + it('Should return a flattened object when custom attributes are not null, not reserved attributes and nested', () => { const payload = { custom_attributes: { source: 'rudder-js-sdk', data: { nestedAttribute: 'nestedValue' } }, diff --git a/src/cdk/v2/destinations/pinterest_tag/config.js b/src/cdk/v2/destinations/pinterest_tag/config.js new file mode 100644 index 00000000000..9e019e14368 --- /dev/null +++ b/src/cdk/v2/destinations/pinterest_tag/config.js @@ -0,0 +1,19 @@ +const ENDPOINT = 'https://ct.pinterest.com/events/v3'; +// ref: https://developers.pinterest.com/docs/api/v5/#tag/conversion_events +const getV5EventsEndpoint = (adAccountId) => + `https://api.pinterest.com/v5/ad_accounts/${adAccountId}/events`; + +const API_VERSION = { + v3: 'legacyApi', + v5: 'newApi', +}; + +// ref: https://s.pinimg.com/ct/docs/conversions_api/dist/v3.html +const MAX_BATCH_SIZE = 1000; + +module.exports = { + ENDPOINT, + MAX_BATCH_SIZE, + getV5EventsEndpoint, + API_VERSION, +}; diff --git a/src/cdk/v2/destinations/pinterest_tag/procWorkflow.yaml b/src/cdk/v2/destinations/pinterest_tag/procWorkflow.yaml index 1122a80404c..64d391c8882 100644 --- a/src/cdk/v2/destinations/pinterest_tag/procWorkflow.yaml +++ b/src/cdk/v2/destinations/pinterest_tag/procWorkflow.yaml @@ -3,8 +3,8 @@ bindings: path: ../../../../constants - path: ../../bindings/jsontemplate exportAll: true - - path: ../../../../v0/destinations/pinterest_tag/utils - - path: ../../../../v0/destinations/pinterest_tag/config + - path: ./utils + - path: ./config - name: removeUndefinedValues path: ../../../../v0/util - name: removeUndefinedAndNullAndEmptyValues @@ -66,7 +66,10 @@ steps: "opt_out": .context.device.adTrackingEnabled !== undefined ? !.context.device.adTrackingEnabled, "event_id": $.getOneByPaths(., ^.destination.Config.deduplicationKey) ?? .messageId, "app_id": ^.destination.Config.appId, - "advertiser_id": ^.destination.Config.advertiserId + "advertiser_id": ^.destination.Config.advertiserId, + "partner_name": .properties.partnerName, + "device_carrier": .context.network.carrier, + "wifi": .context.network.wifi }); $.outputs.apiVersion === {{$.API_VERSION.v5}} ? commonFields = commonFields{~["advertiser_id"]}; $.removeUndefinedValues(commonFields) @@ -103,7 +106,8 @@ steps: "client_ip_address": .context.ip ?? .request_ip, "client_user_agent": .context.userAgent, "external_id": {{{{$.getGenericPaths("userId")}}}}, - "click_id": .properties.clickId + "click_id": .properties.clickId, + "partner_id": .traits.partnerId ?? .context.traits.partnerId }); !.destination.Config.sendExternalId ? userFields = userFields{~["external_id"]} : null; userFields = $.removeUndefinedAndNullAndEmptyValues(userFields); @@ -129,7 +133,11 @@ steps: "num_items": .properties.numOfItems && Number(.properties.numOfItems), "order_id": .properties.order_id, "search_string": .properties.query, - "opt_out_type": .properties.optOutType + "opt_out_type": .properties.optOutType, + "content_name": .properties.contentName, + "content_category": .properties.contentCategory, + "content_brand": .properties.contentBrand, + "np": .properties.np }); $.removeUndefinedValues(customFields) @@ -143,7 +151,11 @@ steps: "content_ids": products.(.product_id ?? .sku ?? .id)[], "contents": .message.properties@prop.products.({ "quantity": Number(.quantity ?? prop.quantity ?? 1), - "item_price": String(.price ?? prop.price) + "item_price": String(.price ?? prop.price), + "item_name": String(.name), + "id": .product_id ?? .sku, + "item_category": .category, + "item_brand": .brand })[] } else: diff --git a/src/cdk/v2/destinations/pinterest_tag/rtWorkflow.yaml b/src/cdk/v2/destinations/pinterest_tag/rtWorkflow.yaml index 215ead12b12..bd4a9439f0f 100644 --- a/src/cdk/v2/destinations/pinterest_tag/rtWorkflow.yaml +++ b/src/cdk/v2/destinations/pinterest_tag/rtWorkflow.yaml @@ -1,5 +1,5 @@ bindings: - - path: ../../../../v0/destinations/pinterest_tag/config + - path: ./config - name: batchMultiplexedEvents path: ../../../../v0/util/index steps: diff --git a/src/cdk/v2/destinations/pinterest_tag/utils.js b/src/cdk/v2/destinations/pinterest_tag/utils.js new file mode 100644 index 00000000000..31a897f1338 --- /dev/null +++ b/src/cdk/v2/destinations/pinterest_tag/utils.js @@ -0,0 +1,150 @@ +/* eslint-disable no-param-reassign */ +const sha256 = require('sha256'); +const { InstrumentationError, ConfigurationError } = require('@rudderstack/integrations-lib'); + +const { API_VERSION } = require('./config'); + +const VALID_ACTION_SOURCES = ['app_android', 'app_ios', 'web', 'offline']; + +const ecomEventMaps = [ + { + src: ['order completed'], + dest: 'checkout', + }, + { + src: ['product added'], + dest: 'add_to_cart', + }, + { + src: ['products searched', 'product list filtered'], + dest: 'search', + }, +]; + +const USER_NON_ARRAY_PROPERTIES = ['client_user_agent', 'client_ip_address']; + +const getHashedValue = (key, value) => { + switch (key) { + case 'em': + case 'ct': + case 'st': + case 'country': + case 'ln': + case 'fn': + case 'ge': + value = Array.isArray(value) + ? value.map((val) => val.toString().trim().toLowerCase()) + : value.toString().trim().toLowerCase(); + break; + case 'ph': + // phone numbers should only contain digits & should not contain leading zeros + value = Array.isArray(value) + ? value.map((val) => val.toString().replace(/\D/g, '').replace(/^0+/, '')) + : value.toString().replace(/\D/g, '').replace(/^0+/, ''); + break; + case 'zp': + // zip fields should only contain digits + value = Array.isArray(value) + ? value.map((val) => val.toString().trim().replace(/\D/g, '')) + : value.toString().replace(/\D/g, ''); + break; + case 'hashed_maids': + case 'external_id': + case 'db': + // no action needed on value + break; + default: + return String(value); + } + return Array.isArray(value) ? value.map((val) => sha256(val)) : [sha256(value)]; +}; + +/** + * + * @param {*} userPayload Payload mapped from user fields + * @returns + * Further Processing the user fields following the instructions of Pinterest Conversion API + * Ref: https://s.pinimg.com/ct/docs/conversions_api/dist/v3.html + */ +const processUserPayload = (userPayload) => { + Object.keys(userPayload).forEach((key) => { + userPayload[key] = getHashedValue(key, userPayload[key]); + }); + return userPayload; +}; + +/** + * + * @param {*} eventName // ["WatchVideo", "ViewCategory", "Custom"] + * @returns // ["watch_video", "view_category", "custom""] + * This function will return the snake case name of the destination config mapped event + */ +const convertToSnakeCase = (eventName) => + eventName.map((str) => + str + .replace(/([a-z])([A-Z])/g, '$1_$2') + .replace(/\s+/g, '_') + .toLowerCase(), + ); + +/** + * + * @param {*} userPayload + * @param {*} message + * @returns converts every single hashed user data property to array, except for + * "client_user_agent", "client_ip_address" + * + */ +const processHashedUserPayload = (userPayload, message) => { + const processedHashedUserPayload = {}; + Object.keys(userPayload).forEach((key) => { + if (!USER_NON_ARRAY_PROPERTIES.includes(key)) { + if (Array.isArray(userPayload[key])) { + processedHashedUserPayload[key] = [...userPayload[key]]; + } else { + processedHashedUserPayload[key] = [userPayload[key]]; + } + } else { + processedHashedUserPayload[key] = userPayload[key]; + } + }); + // multiKeyMap will works on only specific values like m, male, MALE, f, F, Female + // if hashed data is sent from the user, it is directly set over here + const gender = message.traits?.gender || message.context?.traits?.gender; + if (gender && Array.isArray(gender)) { + processedHashedUserPayload.ge = [...gender]; + } else if (gender) { + processedHashedUserPayload.ge = [gender]; + } + return processedHashedUserPayload; +}; + +const validateInput = (message, { Config }) => { + const { apiVersion = API_VERSION.v3, advertiserId, adAccountId, conversionToken } = Config; + if (apiVersion === API_VERSION.v3 && !advertiserId) { + throw new ConfigurationError('Advertiser Id not found. Aborting'); + } + + if (apiVersion === API_VERSION.v5) { + if (!adAccountId) { + throw new ConfigurationError('Ad Account ID not found. Aborting'); + } + + if (!conversionToken) { + throw new ConfigurationError('Conversion Token not found. Aborting'); + } + } + + if (!message.type) { + throw new InstrumentationError('Event type is required'); + } +}; + +module.exports = { + processUserPayload, + processHashedUserPayload, + VALID_ACTION_SOURCES, + ecomEventMaps, + convertToSnakeCase, + validateInput, +}; diff --git a/src/v0/destinations/pinterest_tag/utils.test.js b/src/cdk/v2/destinations/pinterest_tag/utils.test.js similarity index 97% rename from src/v0/destinations/pinterest_tag/utils.test.js rename to src/cdk/v2/destinations/pinterest_tag/utils.test.js index 6b4cef95677..1c1d080ef51 100644 --- a/src/v0/destinations/pinterest_tag/utils.test.js +++ b/src/cdk/v2/destinations/pinterest_tag/utils.test.js @@ -1,4 +1,4 @@ -const { processUserPayload } = require('../../../../src/v0/destinations/pinterest_tag/utils'); +const { processUserPayload } = require('./utils'); const userFields = [ { diff --git a/src/v0/destinations/pinterest_tag/config.js b/src/v0/destinations/pinterest_tag/config.js deleted file mode 100644 index 9216b6f61b4..00000000000 --- a/src/v0/destinations/pinterest_tag/config.js +++ /dev/null @@ -1,31 +0,0 @@ -const { getMappingConfig } = require('../../util'); - -const ENDPOINT = 'https://ct.pinterest.com/events/v3'; -// ref: https://developers.pinterest.com/docs/api/v5/#tag/conversion_events -const getV5EventsEndpoint = (adAccountId) => - `https://api.pinterest.com/v5/ad_accounts/${adAccountId}/events`; - -const API_VERSION = { - v3: 'legacyApi', - v5: 'newApi', -}; - -// ref: https://s.pinimg.com/ct/docs/conversions_api/dist/v3.html -const MAX_BATCH_SIZE = 1000; - -const CONFIG_CATEGORIES = { - USER_CONFIGS: { name: 'pinterestUserConfig' }, - COMMON_CONFIGS: { name: 'pinterestCommonConfig' }, - CUSTOM_CONFIGS: { name: 'pinterestCustomConfig' }, -}; -const MAPPING_CONFIG = getMappingConfig(CONFIG_CATEGORIES, __dirname); - -module.exports = { - ENDPOINT, - MAX_BATCH_SIZE, - USER_CONFIGS: MAPPING_CONFIG[CONFIG_CATEGORIES.USER_CONFIGS.name], - COMMON_CONFIGS: MAPPING_CONFIG[CONFIG_CATEGORIES.COMMON_CONFIGS.name], - CUSTOM_CONFIGS: MAPPING_CONFIG[CONFIG_CATEGORIES.CUSTOM_CONFIGS.name], - getV5EventsEndpoint, - API_VERSION, -}; diff --git a/src/v0/destinations/pinterest_tag/data/pinterestCommonConfig.json b/src/v0/destinations/pinterest_tag/data/pinterestCommonConfig.json deleted file mode 100644 index 52645fa25a0..00000000000 --- a/src/v0/destinations/pinterest_tag/data/pinterestCommonConfig.json +++ /dev/null @@ -1,61 +0,0 @@ -[ - { - "destKey": "event_name", - "sourceKeys": "event" - }, - { - "destKey": "event_time", - "sourceKeys": "timestamp", - "sourceFromGenericMap": true, - "required": true, - "metadata": { - "type": "secondTimestamp" - } - }, - { - "destKey": "event_source_url", - "sourceKeys": "pageUrl", - "sourceFromGenericMap": true - }, - { - "destKey": "action_source", - "sourceKeys": [ - "traits.action_source", - "context.traits.action_source", - "traits.actionSource", - "context.traits.actionSource", - "properties.action_source", - "properties.actionSource", - "channel" - ], - "required": true - }, - { - "destKey": "app_name", - "sourceKeys": ["properties.appName", "context.app.name"] - }, - { - "destKey": "app_version", - "sourceKeys": ["properties.appVersion", "context.app.version"] - }, - { - "destKey": "device_brand", - "sourceKeys": ["properties.manufacturer", "context.device.manufacturer"] - }, - { - "destKey": "device_model", - "sourceKeys": ["properties.deviceModel", "context.device.model"] - }, - { - "destKey": "device_type", - "sourceKeys": ["properties.deviceType", "context.device.type"] - }, - { - "destKey": "os_version", - "sourceKeys": "context.os.version" - }, - { - "destKey": "language", - "sourceKeys": ["properties.language", "context.traits.language", "context.locale"] - } -] diff --git a/src/v0/destinations/pinterest_tag/data/pinterestCustomConfig.json b/src/v0/destinations/pinterest_tag/data/pinterestCustomConfig.json deleted file mode 100644 index 55c9e1e9ed0..00000000000 --- a/src/v0/destinations/pinterest_tag/data/pinterestCustomConfig.json +++ /dev/null @@ -1,38 +0,0 @@ -[ - { - "destKey": "currency", - "sourceKeys": "properties.currency", - "required": false - }, - { - "destKey": "value", - "sourceKeys": ["properties.value", "properties.total", "properties.revenue"], - "required": false, - "metadata": { - "type": "toString" - } - }, - { - "destKey": "num_items", - "sourceKeys": "properties.numOfItems", - "metadata": { - "type": "toInt" - }, - "required": false - }, - { - "destKey": "order_id", - "sourceKeys": "properties.order_id", - "required": false - }, - { - "destKey": "search_string", - "sourceKeys": "properties.query", - "required": false - }, - { - "destKey": "opt_out_type", - "sourceKeys": "properties.optOutType", - "required": false - } -] diff --git a/src/v0/destinations/pinterest_tag/data/pinterestUserConfig.json b/src/v0/destinations/pinterest_tag/data/pinterestUserConfig.json deleted file mode 100644 index b95f539e7ce..00000000000 --- a/src/v0/destinations/pinterest_tag/data/pinterestUserConfig.json +++ /dev/null @@ -1,93 +0,0 @@ -[ - { - "destKey": "em", - "sourceKeys": "emailOnly", - "sourceFromGenericMap": true, - "required": false - }, - { - "destKey": "ph", - "sourceKeys": "phone", - "sourceFromGenericMap": true, - "required": false - }, - { - "destKey": "ge", - "sourceKeys": ["traits.gender", "context.traits.gender"], - "required": false, - "metadata": { - "multikeyMap": [ - { - "sourceVal": ["f", "F", "Female", "female", "FEMALE"], - "destVal": "f" - }, - { - "sourceVal": ["m", "M", "Male", "male", "MALE"], - "destVal": "m" - }, - { - "sourceVal": ["n", "N", "non-binary", "non binary", "Non-Binary", "Non Binary"], - "destVal": "n" - } - ] - } - }, - { - "destKey": "db", - "sourceKeys": "birthday", - "required": false, - "sourceFromGenericMap": true - }, - { - "destKey": "ln", - "sourceKeys": "lastName", - "required": false, - "sourceFromGenericMap": true - }, - { - "destKey": "fn", - "sourceKeys": "firstName", - "required": false, - "sourceFromGenericMap": true - }, - { - "destKey": "ct", - "sourceKeys": ["traits.address.city", "context.traits.address.city"], - "required": false - }, - { - "destKey": "st", - "sourceKeys": ["traits.address.state", "context.traits.address.state"], - "required": false - }, - { - "destKey": "zp", - "sourceKeys": ["traits.address.zip", "context.traits.address.zip"], - "required": false - }, - { - "destKey": "country", - "sourceKeys": ["traits.address.country", "context.traits.address.country"], - "required": false - }, - { - "destKey": "hashed_maids", - "sourceKeys": ["context.device.advertisingId"], - "required": false - }, - { - "destKey": "client_ip_address", - "sourceKeys": ["context.ip", "request_ip"], - "required": false - }, - { - "destKey": "client_user_agent", - "sourceKeys": "context.userAgent", - "required": false - }, - { - "destKey": "external_id", - "sourceKeys": "userId", - "sourceFromGenericMap": true - } -] diff --git a/src/v0/destinations/pinterest_tag/transform.js b/src/v0/destinations/pinterest_tag/transform.js deleted file mode 100644 index f8ccfd48eab..00000000000 --- a/src/v0/destinations/pinterest_tag/transform.js +++ /dev/null @@ -1,202 +0,0 @@ -const { get } = require('lodash'); -const { InstrumentationError } = require('@rudderstack/integrations-lib'); -const { EventType } = require('../../../constants'); -const { - defaultRequestConfig, - defaultPostRequestConfig, - getSuccessRespEvents, - constructPayload, - defaultBatchRequestConfig, - removeUndefinedAndNullValues, - batchMultiplexedEvents, - handleRtTfSingleEventError, -} = require('../../util'); -const { - processUserPayload, - processCommonPayload, - deduceEventName, - postProcessEcomFields, - checkUserPayloadValidity, - processHashedUserPayload, - validateInput, -} = require('./utils'); - -const { - ENDPOINT, - MAX_BATCH_SIZE, - USER_CONFIGS, - getV5EventsEndpoint, - API_VERSION, -} = require('./config'); - -const responseBuilderSimple = (finalPayload, { Config }) => { - const { apiVersion = API_VERSION.v3, adAccountId, conversionToken, sendAsTestEvent } = Config; - const response = defaultRequestConfig(); - response.endpoint = ENDPOINT; - response.method = defaultPostRequestConfig.requestMethod; - response.body.JSON = removeUndefinedAndNullValues(finalPayload); - - response.headers = { 'Content-Type': 'application/json' }; - - if (apiVersion === API_VERSION.v5) { - response.endpoint = getV5EventsEndpoint(adAccountId); - response.headers = { - 'Content-Type': 'application/json', - Authorization: `Bearer ${conversionToken}`, - }; - } - if (sendAsTestEvent) { - response.params = { - test: true, - }; - } - - return response; -}; - -/** - * - * @param {*} message - * @param {*} destination.Config - * @param {*} messageType - * @param {*} eventName - * @returns the output of each input payload. - * message deduplication logic looks like below: - * This facility is provided *only* for the users who are using the *new configuration*. - * if "enableDeduplication" is set to *true* and "deduplicationKey" is set via webapp, that key value will be - * sent as "event_id". On it's absence it will fallback to "messageId". - * And if "enableDeduplication" is set to false, it will fallback to "messageId" - */ -const commonFieldResponseBuilder = (message, { Config }, messageType, eventName) => { - let processedUserPayload; - const { appId, advertiserId, deduplicationKey, sendingUnHashedData, sendExternalId, apiVersion } = - Config; - // ref: https://s.pinimg.com/ct/docs/conversions_api/dist/v3.html - const processedCommonPayload = processCommonPayload(message); - - processedCommonPayload.event_id = get(message, `${deduplicationKey}`) || message.messageId; - const userPayload = constructPayload(message, USER_CONFIGS, 'pinterest'); - - if (!sendExternalId) { - delete userPayload.external_id; - } - - const isValidUserPayload = checkUserPayloadValidity(userPayload); - if (isValidUserPayload === false) { - throw new InstrumentationError( - 'It is required at least one of em, hashed_maids or pair of client_ip_address and client_user_agent', - ); - } - - /** - * User can configure hashed checkbox to false if they are sending already hashed data to Rudderstack - * Otherwise we will hash data user data by default. - */ - if (sendingUnHashedData) { - processedUserPayload = processUserPayload(userPayload); - } else { - // when user is sending already hashed data to Rudderstack - processedUserPayload = processHashedUserPayload(userPayload, message); - } - - let response = { - ...processedCommonPayload, - event_name: eventName, - app_id: appId, - advertiser_id: advertiserId, - user_data: processedUserPayload, - }; - - if (apiVersion === API_VERSION.v5) { - delete response.advertiser_id; - } - - if (messageType === EventType.TRACK) { - response = postProcessEcomFields(message, response); - } - - return response; -}; - -const process = (event) => { - const toSendEvents = []; - const respList = []; - const deducedEventNameArray = []; - const { message, destination } = event; - const messageType = message.type?.toLowerCase(); - - validateInput(message, destination); - - switch (messageType) { - case EventType.PAGE: - case EventType.SCREEN: - case EventType.TRACK: - deducedEventNameArray.push(...deduceEventName(message, destination.Config)); - deducedEventNameArray.forEach((eventName) => { - toSendEvents.push(commonFieldResponseBuilder(message, destination, messageType, eventName)); - }); - - break; - default: - throw new InstrumentationError(`message type ${messageType} is not supported`); - } - - toSendEvents.forEach((sendEvent) => { - respList.push(responseBuilderSimple(sendEvent, destination)); - }); - return respList; -}; - -const generateBatchedPayloadForArray = (events) => { - const { batchedRequest } = defaultBatchRequestConfig(); - const batchResponseList = events.map((event) => event.body.JSON); - batchedRequest.body.JSON = { data: batchResponseList }; - batchedRequest.endpoint = events[0].endpoint; - batchedRequest.headers = events[0].headers; - - return batchedRequest; -}; - -const batchEvents = (successRespList) => { - const batchResponseList = []; - const batchedEvents = batchMultiplexedEvents(successRespList, MAX_BATCH_SIZE); - batchedEvents.forEach((batch) => { - const batchedRequest = generateBatchedPayloadForArray(batch.events); - batchResponseList.push( - getSuccessRespEvents(batchedRequest, batch.metadata, batch.destination, true), - ); - }); - - return batchResponseList; -}; - -const processRouterDest = (inputs, reqMetadata) => { - const successRespList = []; - const batchErrorRespList = []; - inputs.forEach((input) => { - try { - let resp = input.message; - // transform if not already done - if (!input.message.statusCode) { - resp = process(input); - } - - successRespList.push({ - message: Array.isArray(resp) ? resp : [resp], - metadata: input.metadata, - destination: input.destination, - }); - } catch (error) { - batchErrorRespList.push(handleRtTfSingleEventError(input, error, reqMetadata)); - } - }); - - let batchResponseList = []; - if (successRespList.length > 0) { - batchResponseList = batchEvents(successRespList); - } - - return [...batchResponseList, ...batchErrorRespList]; -}; - -module.exports = { process, processRouterDest }; diff --git a/src/v0/destinations/pinterest_tag/utils.js b/src/v0/destinations/pinterest_tag/utils.js deleted file mode 100644 index 57d595571fd..00000000000 --- a/src/v0/destinations/pinterest_tag/utils.js +++ /dev/null @@ -1,416 +0,0 @@ -/* eslint-disable no-param-reassign */ -const sha256 = require('sha256'); -const { InstrumentationError, ConfigurationError } = require('@rudderstack/integrations-lib'); -const { EventType } = require('../../../constants'); -const { - constructPayload, - isDefinedAndNotNull, - isDefined, - getHashFromArrayWithDuplicate, - removeUndefinedAndNullValues, - validateEventName, -} = require('../../util'); -const { COMMON_CONFIGS, CUSTOM_CONFIGS, API_VERSION } = require('./config'); - -const VALID_ACTION_SOURCES = ['app_android', 'app_ios', 'web', 'offline']; - -const ecomEventMaps = [ - { - src: ['order completed'], - dest: 'checkout', - }, - { - src: ['product added'], - dest: 'add_to_cart', - }, - { - src: ['products searched', 'product list filtered'], - dest: 'search', - }, -]; - -const USER_NON_ARRAY_PROPERTIES = ['client_user_agent', 'client_ip_address']; - -const getHashedValue = (key, value) => { - switch (key) { - case 'em': - case 'ct': - case 'st': - case 'country': - case 'ln': - case 'fn': - case 'ge': - value = Array.isArray(value) - ? value.map((val) => val.toString().trim().toLowerCase()) - : value.toString().trim().toLowerCase(); - break; - case 'ph': - // phone numbers should only contain digits & should not contain leading zeros - value = Array.isArray(value) - ? value.map((val) => val.toString().replace(/\D/g, '').replace(/^0+/, '')) - : value.toString().replace(/\D/g, '').replace(/^0+/, ''); - break; - case 'zp': - // zip fields should only contain digits - value = Array.isArray(value) - ? value.map((val) => val.toString().trim().replace(/\D/g, '')) - : value.toString().replace(/\D/g, ''); - break; - case 'hashed_maids': - case 'external_id': - case 'db': - // no action needed on value - break; - default: - return String(value); - } - return Array.isArray(value) ? value.map((val) => sha256(val)) : [sha256(value)]; -}; - -/** - * - * @param {*} userPayload Payload mapped from user fields - * @returns - * Further Processing the user fields following the instructions of Pinterest Conversion API - * Ref: https://s.pinimg.com/ct/docs/conversions_api/dist/v3.html - */ -const processUserPayload = (userPayload) => { - Object.keys(userPayload).forEach((key) => { - userPayload[key] = getHashedValue(key, userPayload[key]); - }); - return userPayload; -}; - -/** - * - * @param {*} message - * @returns opt_out status - * - */ - -const deduceOptOutStatus = (message) => { - const adTrackingEnabled = message.context?.device?.adTrackingEnabled; - let optOut; - - // for ios - if (isDefinedAndNotNull(adTrackingEnabled)) { - if (adTrackingEnabled === true) { - optOut = false; - } else if (adTrackingEnabled === false) { - optOut = true; - } - } - - return optOut; -}; - -/** - * - * @param {*} message - * @returns - * Maps the required common parameters accross event types. Checks for the correct - * action source types and deduces opt_out status - * Ref: https://s.pinimg.com/ct/docs/conversions_api/dist/v3.html - */ -const processCommonPayload = (message) => { - const commonPayload = constructPayload(message, COMMON_CONFIGS); - const presentActionSource = commonPayload.action_source; - if (presentActionSource && !VALID_ACTION_SOURCES.includes(presentActionSource.toLowerCase())) { - throw new InstrumentationError( - `Action source must be one of ${VALID_ACTION_SOURCES.join(', ')}`, - ); - } - - commonPayload.opt_out = deduceOptOutStatus(message); - - return commonPayload; -}; - -/** - * - * @param {*} eventName // ["WatchVideo", "ViewCategory", "Custom"] - * @returns // ["watch_video", "view_category", "custom""] - * This function will return the snake case name of the destination config mapped event - */ -const convertToSnakeCase = (eventName) => - eventName.map((str) => - str - .replace(/([a-z])([A-Z])/g, '$1_$2') - .replace(/\s+/g, '_') - .toLowerCase(), - ); - -/** - * - * @param {*} message - * @param {*} Config - * @returns - * For the few ecommerce events the mapping is like following: - * const ecomEventMaps = [ - { - src: ["order completed"], - dest: "checkout", - }, - { - src: ["product added"], - dest: "add_to_cart", - }, - { - src: ["products searched", "product list filtered"], - dest: "search", - }, - ]; - * For others, it depends on mapping from the UI. If any event, other than mapped events are sent, - * will be labled as "custom" events. - */ -const deduceTrackScreenEventName = (message, Config) => { - let eventName; - const { event, name } = message; - const { eventsMapping, sendAsCustomEvent } = Config; - const trackEventOrScreenName = event || name; - if (!trackEventOrScreenName) { - throw new InstrumentationError('event_name could not be mapped. Aborting'); - } - validateEventName(trackEventOrScreenName); - - /* - Step 1: If the event is not amongst the above list of ecommerce events, will look for - the event mapping in the UI. In case it is similar, will map to that. - */ - if (eventsMapping.length > 0) { - const keyMap = getHashFromArrayWithDuplicate(eventsMapping, 'from', 'to', false); - eventName = keyMap[trackEventOrScreenName]; - } - if (isDefined(eventName)) { - return convertToSnakeCase([...eventName]); - } - - /* - Step 2: To find if the particular event is amongst the list of standard - Rudderstack ecommerce events, used specifically for Pinterest Conversion API - mappings. - */ - if (!eventName) { - const eventMapInfo = ecomEventMaps.find((eventMap) => { - if (eventMap.src.includes(trackEventOrScreenName.toLowerCase())) { - return eventMap; - } - return false; - }); - - if (isDefinedAndNotNull(eventMapInfo)) { - return [eventMapInfo.dest]; - } - } - - /* - Step 3: In case both of the above stated cases fail, will check if sendAsCustomEvent toggle is enabled in UI. - If yes, then we will send it as custom event - */ - if (sendAsCustomEvent) { - return ['custom']; - } - - /* - Step 4: In case all of the above stated cases failed, will send the event name as it is. - This is going to be reflected as "unknown" event in conversion API dashboard. - */ - return [trackEventOrScreenName]; -}; - -/** - * - * @param {*} message event.message - * @param {*} Config event.destination.Config - * @returns - * Returns the appropriate event name for each event types - * For identify : "identify". - * For page : "ViewCategory" in case category is present, "PageVisit" otherwise. - * For track : Depends on the event name - */ -const deduceEventName = (message, Config) => { - const { type, category } = message; - let eventName = []; - switch (type) { - case EventType.PAGE: - eventName = isDefinedAndNotNull(category) ? ['view_category'] : ['page_visit']; - break; - case EventType.TRACK: - case EventType.SCREEN: - eventName = deduceTrackScreenEventName(message, Config); - break; - default: - throw new InstrumentationError(`The event of type ${type} is not supported`); - } - return eventName; -}; - -/** - * - * @param {*} rootObject object from where the price, quantity and ids will be fetched - * @param {*} message event.message - * @returns - * Object containing the deduced parameters - */ -const setIdPriceQuantity = (rootObject, message) => { - const contentObj = { - // we are yet to check how the destination behaves if one of quantity and item_price is missing - quantity: parseInt(rootObject.quantity || message.properties.quantity || 1, 10), - item_price: String(rootObject.price || message.properties.price), - }; - return { - contentId: rootObject.product_id || rootObject.sku || rootObject.id, - content: contentObj, - }; -}; - -/** - * @param {*} userPayload Payload mapped from user fields - * @returns returns true if at least one of: em, hashed_maids or combination of client_ip_address and - * client_user_agent is present. And false otherwise. - */ -const checkUserPayloadValidity = (userPayload) => { - const userFields = Object.keys(userPayload); - if (userFields.includes('em') || userFields.includes('hashed_maids')) { - return true; - } - return userFields.includes('client_ip_address') && userFields.includes('client_user_agent'); -}; - -/** - * - * @param {*} userPayload - * @param {*} message - * @returns converts every single hashed user data property to array, except for - * "client_user_agent", "client_ip_address" - * - */ -const processHashedUserPayload = (userPayload, message) => { - const processedHashedUserPayload = {}; - Object.keys(userPayload).forEach((key) => { - if (!USER_NON_ARRAY_PROPERTIES.includes(key)) { - if (Array.isArray(userPayload[key])) { - processedHashedUserPayload[key] = [...userPayload[key]]; - } else { - processedHashedUserPayload[key] = [userPayload[key]]; - } - } else { - processedHashedUserPayload[key] = userPayload[key]; - } - }); - // multiKeyMap will works on only specific values like m, male, MALE, f, F, Female - // if hashed data is sent from the user, it is directly set over here - const gender = message.traits?.gender || message.context?.traits?.gender; - if (gender && Array.isArray(gender)) { - processedHashedUserPayload.ge = [...gender]; - } else if (gender) { - processedHashedUserPayload.ge = [gender]; - } - return processedHashedUserPayload; -}; - -/** - * This function will process the ecommerce fields and return the final payload - * @param {*} message - * @param {*} mandatoryPayload - * @returns - */ -const postProcessEcomFields = (message, mandatoryPayload) => { - let totalQuantity = 0; - let quantityInconsistent = false; - const contentArray = []; - const contentIds = []; - const { properties } = message; - // ref: https://s.pinimg.com/ct/docs/conversions_api/dist/v3.html - let customPayload = constructPayload(message, CUSTOM_CONFIGS); - - // if product array is present will look for the product level information - if (properties.products && Array.isArray(properties.products) && properties.products.length > 0) { - const { products, quantity } = properties; - products.forEach((product) => { - const prodParams = setIdPriceQuantity(product, message); - if (prodParams.contentId) { - contentIds.push(prodParams.contentId); - } - contentArray.push(prodParams.content); - if (!product.quantity) { - quantityInconsistent = true; - } - totalQuantity = product.quantity ? totalQuantity + product.quantity : totalQuantity; - }); - - if (totalQuantity === 0) { - /* - in case any of the products inside product array does not have quantity, - will map the quantity of root level - */ - totalQuantity = quantity; - } - } else { - /* - for the events where product array is not present, root level id, price and - quantity are taken into consideration - */ - const prodParams = setIdPriceQuantity(properties, message); - if (prodParams.contentId) { - contentIds.push(prodParams.contentId); - } - contentArray.push(prodParams.content); - totalQuantity = properties.quantity ? totalQuantity + properties.quantity : totalQuantity; - } - /* - if properties.numOfItems is not provided by the user, the total quantity of the products - will be sent as num_items - */ - if (!isDefinedAndNotNull(customPayload.num_items) && quantityInconsistent === false) { - customPayload.num_items = parseInt(totalQuantity, 10); - } - customPayload = { - ...customPayload, - contents: contentArray, - }; - - if (contentIds.length > 0) { - customPayload.content_ids = contentIds; - } - - return { - ...mandatoryPayload, - custom_data: { ...removeUndefinedAndNullValues(customPayload) }, - }; -}; - -const validateInput = (message, { Config }) => { - const { apiVersion = API_VERSION.v3, advertiserId, adAccountId, conversionToken } = Config; - if (apiVersion === API_VERSION.v3 && !advertiserId) { - throw new ConfigurationError('Advertiser Id not found. Aborting'); - } - - if (apiVersion === API_VERSION.v5) { - if (!adAccountId) { - throw new ConfigurationError('Ad Account ID not found. Aborting'); - } - - if (!conversionToken) { - throw new ConfigurationError('Conversion Token not found. Aborting'); - } - } - - if (!message.type) { - throw new InstrumentationError('Event type is required'); - } -}; - -module.exports = { - processUserPayload, - processCommonPayload, - deduceEventName, - setIdPriceQuantity, - checkUserPayloadValidity, - processHashedUserPayload, - VALID_ACTION_SOURCES, - postProcessEcomFields, - ecomEventMaps, - convertToSnakeCase, - validateInput, -}; diff --git a/src/warehouse/index.js b/src/warehouse/index.js index 4afa8f72c2d..3491a257da0 100644 --- a/src/warehouse/index.js +++ b/src/warehouse/index.js @@ -30,7 +30,7 @@ const whExtractEventTableColumnMappingRules = require('./config/WHExtractEventTa const maxColumnsInEvent = parseInt(process.env.WH_MAX_COLUMNS_IN_EVENT || '200', 10); const WH_POPULATE_SRC_DEST_INFO_IN_CONTEXT = - process.env.WH_POPULATE_SRC_DEST_INFO_IN_CONTEXT || true; + process.env.WH_POPULATE_SRC_DEST_INFO_IN_CONTEXT !== 'false'; const getDataType = (key, val, options, jsonKey = false) => { const type = typeof val; diff --git a/test/__tests__/data/pinterest_tag_input.json b/test/__tests__/data/pinterest_tag_input.json index f0755ddb383..15e378caf6f 100644 --- a/test/__tests__/data/pinterest_tag_input.json +++ b/test/__tests__/data/pinterest_tag_input.json @@ -47,6 +47,7 @@ "optOutType": "LDP", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -57,6 +58,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -153,6 +155,7 @@ "requestIP": "123.0.0.0", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -163,6 +166,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -554,6 +558,7 @@ "numOfItems": 2, "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -564,6 +569,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -981,6 +987,7 @@ "numOfItems": 2, "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -991,6 +998,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -1773,6 +1781,7 @@ "checkout_id": "fksdjfsdjfisjf9sdfjsd9f", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -1954,6 +1963,7 @@ "optOutType": "LDP", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -1964,6 +1974,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -2065,6 +2076,7 @@ "optOutType": "LDP", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -2075,6 +2087,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -2176,6 +2189,7 @@ "optOutType": "LDP", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -2186,6 +2200,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, diff --git a/test/__tests__/data/pinterest_tag_output.json b/test/__tests__/data/pinterest_tag_output.json index 9fb809d112d..dccdb248c99 100644 --- a/test/__tests__/data/pinterest_tag_output.json +++ b/test/__tests__/data/pinterest_tag_output.json @@ -41,10 +41,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -58,6 +66,7 @@ "files": {} } ], + [ { "version": "1", @@ -96,10 +105,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -210,10 +227,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -277,10 +302,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -649,6 +682,10 @@ "content_ids": ["507f1f77bcf86cd799439011"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" } @@ -752,10 +789,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -808,10 +853,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -888,10 +941,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } diff --git a/test/__tests__/data/pinterest_tag_router_batch_output.json b/test/__tests__/data/pinterest_tag_router_batch_output.json index 995d68428a4..0eb8f0532ae 100644 --- a/test/__tests__/data/pinterest_tag_router_batch_output.json +++ b/test/__tests__/data/pinterest_tag_router_batch_output.json @@ -43,10 +43,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -83,10 +91,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -122,10 +138,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -272,10 +296,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -311,10 +343,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -572,12 +612,20 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { - "item_price": "19", - "quantity": 1 + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", + "quantity": 1, + "item_price": "19" }, { - "item_price": "3", - "quantity": 2 + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", + "quantity": 2, + "item_price": "3" } ], "currency": "USD", @@ -611,12 +659,20 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { - "item_price": "19", - "quantity": 1 + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", + "quantity": 1, + "item_price": "19" }, { - "item_price": "3", - "quantity": 2 + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", + "quantity": 2, + "item_price": "3" } ], "currency": "USD", @@ -650,12 +706,20 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { - "item_price": "19", - "quantity": 1 + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", + "quantity": 1, + "item_price": "19" }, { - "item_price": "3", - "quantity": 2 + "item_brand": "testBrand", + "id": "505bd76785ebb509fc183733", + "item_category": "Games", + "item_name": "Uno Card Game", + "quantity": 2, + "item_price": "3" } ], "currency": "USD", @@ -767,12 +831,20 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { - "item_price": "19", - "quantity": 1 + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", + "quantity": 1, + "item_price": "19" }, { - "item_price": "3", - "quantity": 2 + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", + "quantity": 2, + "item_price": "3" } ], "currency": "USD", diff --git a/test/__tests__/data/pinterest_tag_router_input.json b/test/__tests__/data/pinterest_tag_router_input.json index 26febec456a..c1639382d72 100644 --- a/test/__tests__/data/pinterest_tag_router_input.json +++ b/test/__tests__/data/pinterest_tag_router_input.json @@ -48,6 +48,7 @@ "optOutType": "LDP", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -58,6 +59,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -170,6 +172,7 @@ "requestIP": "123.0.0.0", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -180,6 +183,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -395,6 +399,7 @@ "requestIP": "123.0.0.0", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -405,6 +410,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -517,6 +523,7 @@ "requestIP": "123.0.0.0", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -527,6 +534,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -639,6 +647,7 @@ "requestIP": "123.0.0.0", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -649,6 +658,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -866,6 +876,7 @@ "optOutType": "LDP", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -876,6 +887,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -990,6 +1002,7 @@ "requestIP": "123.0.0.0", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -1000,6 +1013,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, @@ -1114,6 +1128,7 @@ "requestIP": "123.0.0.0", "products": [ { + "brand": "testBrand", "sku": "45790-32", "url": "https://www.example.com/product/path", "name": "Monopoly: 3rd Edition", @@ -1124,6 +1139,7 @@ "product_id": "507f1f77bcf86cd799439011" }, { + "brand": "testBrand", "sku": "46493-32", "name": "Uno Card Game", "price": 3, diff --git a/test/__tests__/data/pinterest_tag_router_output.json b/test/__tests__/data/pinterest_tag_router_output.json index 2bfc7c3cf57..a54d3289786 100644 --- a/test/__tests__/data/pinterest_tag_router_output.json +++ b/test/__tests__/data/pinterest_tag_router_output.json @@ -43,10 +43,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -83,10 +91,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -122,10 +138,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -196,10 +220,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -235,10 +267,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -465,10 +505,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -504,10 +552,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -542,10 +598,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } @@ -580,10 +644,18 @@ "content_ids": ["507f1f77bcf86cd799439011", "505bd76785ebb509fc183733"], "contents": [ { + "id": "507f1f77bcf86cd799439011", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Monopoly: 3rd Edition", "quantity": 1, "item_price": "19" }, { + "id": "505bd76785ebb509fc183733", + "item_brand": "testBrand", + "item_category": "Games", + "item_name": "Uno Card Game", "quantity": 2, "item_price": "3" } diff --git a/test/__tests__/pinterestConversion.test.js b/test/__tests__/pinterestConversion.test.js deleted file mode 100644 index 4c145f0383b..00000000000 --- a/test/__tests__/pinterestConversion.test.js +++ /dev/null @@ -1,54 +0,0 @@ -const integration = "pinterest_tag"; -const name = "Pinterest Conversion API"; - -const fs = require("fs"); -const path = require("path"); - -const version = "v0"; - -const transformer = require(`../../src/${version}/destinations/${integration}/transform`); -const { assertRouterOutput } = require('../testHelper'); - -const inputDataFile = fs.readFileSync( - path.resolve(__dirname, `./data/${integration}_input.json`) -); -const outputDataFile = fs.readFileSync( - path.resolve(__dirname, `./data/${integration}_output.json`) -); -const inputData = JSON.parse(inputDataFile); -const expectedData = JSON.parse(outputDataFile); - -// Router Test Data -const inputRouterDataFile = fs.readFileSync( - path.resolve(__dirname, `./data/${integration}_router_input.json`) -); -const outputRouterDataFile = fs.readFileSync( - path.resolve(__dirname, `./data/${integration}_router_output.json`) -); -const inputRouterData = JSON.parse(inputRouterDataFile); -const expectedRouterData = JSON.parse(outputRouterDataFile); - -describe(`${name} Tests`, () => { - describe("Processor Tests", () => { - inputData.forEach((input, index) => { - it(`${name} - payload: ${index}`, async () => { - try { - const output = await transformer.process(input); - expect(output).toEqual(expectedData[index]); - } catch (error) { - expect(error.message).toEqual(expectedData[index].error); - } - }); - }); - }); - - describe("Router Tests", () => { - inputRouterData.forEach((input, index) => { - it(`Payload: ${index}`, async () => { - let output = await transformer.processRouterDest(input); - assertRouterOutput(output, input); - expect(output).toEqual(expectedRouterData[index]); - }); - }); - }); -}); diff --git a/test/apitests/service.api.test.ts b/test/apitests/service.api.test.ts index 30d2c568a6e..6ecd3f7374c 100644 --- a/test/apitests/service.api.test.ts +++ b/test/apitests/service.api.test.ts @@ -430,26 +430,6 @@ describe('Destination api tests', () => { expect(JSON.parse(response.text)).toEqual(data.output); }); - test('(pinterest) success scenario with multiplex events', async () => { - const data = getDataFromPath('./data_scenarios/destination/proc/multiplex_success.json'); - const response = await request(server) - .post('/v0/destinations/pinterest_tag') - .set('Accept', 'application/json') - .send(data.input); - expect(response.status).toEqual(200); - expect(JSON.parse(response.text)).toEqual(data.output); - }); - - test('(pinterest) failure scneario for multiplex but event fails at validation', async () => { - const data = getDataFromPath('./data_scenarios/destination/proc/multiplex_failure.json'); - const response = await request(server) - .post('/v0/destinations/pinterest_tag') - .set('Accept', 'application/json') - .send(data.input); - expect(response.status).toEqual(200); - expect(JSON.parse(response.text)).toEqual(data.output); - }); - test('(webhook) success snceario for batch of input', async () => { const data = getDataFromPath('./data_scenarios/destination/proc/batch_input.json'); const response = await request(server) @@ -459,28 +439,6 @@ describe('Destination api tests', () => { expect(response.status).toEqual(200); expect(JSON.parse(response.text)).toEqual(data.output); }); - - test('(webhook) success snceario for batch of input of 2 events and expect 3 output events', async () => { - const data = getDataFromPath('./data_scenarios/destination/proc/batch_input_multiplex.json'); - const response = await request(server) - .post('/v0/destinations/pinterest_tag') - .set('Accept', 'application/json') - .send(data.input); - expect(response.status).toEqual(200); - expect(JSON.parse(response.text)).toEqual(data.output); - }); - - test('(pinterest) partial success scenario for multiplex with 2 events and expect 3 output events with 3rd one failing', async () => { - const data = getDataFromPath( - './data_scenarios/destination/proc/multiplex_partial_failure.json', - ); - const response = await request(server) - .post('/v0/destinations/pinterest_tag') - .set('Accept', 'application/json') - .send(data.input); - expect(response.status).toEqual(200); - expect(JSON.parse(response.text)).toEqual(data.output); - }); }); describe('Batch transform tests', () => { @@ -516,16 +474,6 @@ describe('Destination api tests', () => { expect(JSON.parse(response.text)).toEqual(data.output); }); - test('(pinterest_tag) failure router transform(partial failure)', async () => { - const data = getDataFromPath('./data_scenarios/destination/router/failure_test.json'); - const response = await request(server) - .post('/routerTransform') - .set('Accept', 'application/json') - .send(data.input); - expect(response.status).toEqual(200); - expect(JSON.parse(response.text)).toEqual(data.output); - }); - test('(webhook) send events for 2 destinations router transform', async () => { const data = getDataFromPath('./data_scenarios/destination/router/two_destination_test.json'); const response = await request(server) @@ -604,45 +552,8 @@ describe('Source api tests', () => { }); }); -describe('CDK V2 api tests', () => { - test('(pinterest_tag) successful transform', async () => { - const data = getDataFromPath('./data_scenarios/cdk_v2/success.json'); - const response = await request(server) - .post('/v0/destinations/pinterest_tag') - .set('Accept', 'application/json') - .send(data.input); - expect(response.status).toEqual(200); - expect(JSON.parse(response.text)).toEqual(data.output); - }); - - test('(pinterest_tag) partial failure scenario', async () => { - const data = getDataFromPath('./data_scenarios/cdk_v2/failure.json'); - const response = await request(server) - .post('/v0/destinations/pinterest_tag') - .set('Accept', 'application/json') - .send(data.input); - expect(response.status).toEqual(200); - expect(JSON.parse(response.text)).toEqual(data.output); - }); -}); - jest.setTimeout(100000); describe('Comparsion service tests', () => { - test('compare cdk v2 and native', async () => { - process.env.COMPARATOR_ENABLED = 'true'; - const data = getDataFromPath('./data_scenarios/cdk_v2/success.json'); - data.input.forEach((input) => { - setValue(input, 'destination.DestinationDefinition.Config.comparisonTestEnabeld', true); - setValue(input, 'destination.DestinationDefinition.Config.comparisonService', 'native_dest'); - }); - const response = await request(server) - .post('/v0/destinations/pinterest_tag') - .set('Accept', 'application/json') - .send(data.input); - expect(response.status).toEqual(200); - expect(JSON.parse(response.text)).toEqual(data.output); - }); - test('compare native and cdk v2', async () => { process.env.COMPARATOR_ENABLED = 'true'; const data = getDataFromPath('./data_scenarios/destination/router/successful_test.json'); diff --git a/test/integrations/destinations/pinterest_tag/processor/data.ts b/test/integrations/destinations/pinterest_tag/processor/data.ts index 48b624645f9..b856d247d71 100644 --- a/test/integrations/destinations/pinterest_tag/processor/data.ts +++ b/test/integrations/destinations/pinterest_tag/processor/data.ts @@ -26,13 +26,21 @@ export const data = [ lastname: 'Rudderlabs', firstName: 'Test', address: { city: 'Kolkata', state: 'WB', zip: '700114', country: 'IN' }, + partnerId: '12345678', }, device: { advertisingId: 'abc123' }, library: { name: 'rudder-sdk-ruby-sync', version: '1.0.6' }, + network: { + carrier: 'VI', + wifi: true, + }, }, messageId: '7208bbb6-2c4e-45bb-bf5b-ad426f3593e9', timestamp: '2020-08-14T05:30:30.118Z', properties: { + contentBrand: 'LV', + partnerName: 'testPartner', + contentName: 'testContent', tax: 2, total: 27.5, coupon: 'hasbros', @@ -106,55 +114,77 @@ export const data = [ { metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, output: { - version: '1', - type: 'REST', - method: 'POST', - endpoint: 'https://ct.pinterest.com/events/v3', - headers: { 'Content-Type': 'application/json' }, - params: { test: true }, body: { + FORM: {}, JSON: { action_source: 'web', + advertiser_id: '429047995', + app_id: '429047995', + custom_data: { + content_brand: 'LV', + content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], + content_name: 'testContent', + contents: [ + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + item_price: '19', + quantity: 1, + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + item_price: '3', + quantity: 2, + }, + ], + currency: 'USD', + num_items: 3, + opt_out_type: 'LDP', + order_id: '50314b8e9bcf000000000000', + value: '27.5', + }, + device_carrier: 'VI', + event_id: '7208bbb6-2c4e-45bb-bf5b-ad426f3593e9', event_name: 'watch_video', event_time: 1597383030, - event_id: '7208bbb6-2c4e-45bb-bf5b-ad426f3593e9', - app_id: '429047995', - advertiser_id: '429047995', + partner_name: 'testPartner', user_data: { + click_id: 'dummy_clickId', + client_user_agent: 'chrome', + country: ['582967534d0f909d196b97f9e6921342777aea87b46fa52df165389db1fb8ccf'], + ct: ['6689106ca7922c30b2fd2c175c85bc7fc2d52cc4941bdd7bb622c6cdc6284a85'], em: ['48ddb93f0b30c475423fe177832912c5bcdce3cc72872f8051627967ef278e08'], - ph: ['d164bbe036663cb5c96835e9ccc6501e9a521127ea62f6359744928ba932413b'], - ln: ['dcf000c2386fb76d22cefc0d118a8511bb75999019cd373df52044bccd1bd251'], fn: ['9f86d081884c7d659a2feaa0c55ad015a3bf4f1b2b0b822cd15d6c15b0f00a08'], - ct: ['6689106ca7922c30b2fd2c175c85bc7fc2d52cc4941bdd7bb622c6cdc6284a85'], - st: ['3b45022ab36728cdae12e709e945bba267c50ee8a91e6e4388539a8e03a3fdcd'], - zp: ['1a4292e00780e18d00e76fde9850aee5344e939ba593333cd5e4b4aa2cd33b0c'], - country: ['582967534d0f909d196b97f9e6921342777aea87b46fa52df165389db1fb8ccf'], + ge: ['1b16b1df538ba12dc3f97edbb85caa7050d46c148134290feba80f8236c83db9'], hashed_maids: [ '6ca13d52ca70c883e0f0bb101e425a89e8624de51db2d2392593af6a84118090', ], - client_user_agent: 'chrome', - click_id: 'dummy_clickId', - ge: ['1b16b1df538ba12dc3f97edbb85caa7050d46c148134290feba80f8236c83db9'], - }, - custom_data: { - currency: 'USD', - value: '27.5', - order_id: '50314b8e9bcf000000000000', - opt_out_type: 'LDP', - num_items: 3, - content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], - contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, - ], + ln: ['dcf000c2386fb76d22cefc0d118a8511bb75999019cd373df52044bccd1bd251'], + partner_id: '12345678', + ph: ['d164bbe036663cb5c96835e9ccc6501e9a521127ea62f6359744928ba932413b'], + st: ['3b45022ab36728cdae12e709e945bba267c50ee8a91e6e4388539a8e03a3fdcd'], + zp: ['1a4292e00780e18d00e76fde9850aee5344e939ba593333cd5e4b4aa2cd33b0c'], }, + wifi: true, }, JSON_ARRAY: {}, XML: {}, - FORM: {}, }, + endpoint: 'https://ct.pinterest.com/events/v3', files: {}, + headers: { + 'Content-Type': 'application/json', + }, + method: 'POST', + params: { + test: true, + }, + type: 'REST', userId: '', + version: '1', }, statusCode: 200, }, @@ -302,8 +332,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -835,8 +877,20 @@ export const data = [ order_id: '50314b8e9bcf000000000000', content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -1357,8 +1411,20 @@ export const data = [ order_id: '50314b8e9bcf000000000000', content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -2486,7 +2552,15 @@ export const data = [ order_id: '50314b8e9bcf000000000000', num_items: 1, content_ids: ['507f1f77bcf86cd799439011'], - contents: [{ quantity: 1, item_price: '19' }], + contents: [ + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + ], }, }, JSON_ARRAY: {}, @@ -2785,8 +2859,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -2951,8 +3037,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -2980,7 +3078,7 @@ export const data = [ body: [ { description: - 'Custom event with v5 Api version, with unhashed User Data and the values are an array of strings', + 'Custom event with v5 Api version, with unhashed User Data and the values are an of strings', message: { type: 'track', event: 'random', @@ -3147,8 +3245,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, diff --git a/test/integrations/destinations/pinterest_tag/router/data.ts b/test/integrations/destinations/pinterest_tag/router/data.ts index c02b1781e32..c9ab29a45a9 100644 --- a/test/integrations/destinations/pinterest_tag/router/data.ts +++ b/test/integrations/destinations/pinterest_tag/router/data.ts @@ -674,8 +674,20 @@ export const data = [ opt_out_type: 'LDP', content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -710,8 +722,20 @@ export const data = [ opt_out_type: 'LDP', content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -745,8 +769,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -812,8 +848,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -847,8 +895,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -981,7 +1041,7 @@ export const data = [ }, { destType: 'pinterest_tag', - description: 'Test 0', + description: 'Test 1', feature: 'router', module: 'destination', version: 'v0', @@ -1328,8 +1388,20 @@ export const data = [ opt_out_type: 'LDP', content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -1363,8 +1435,20 @@ export const data = [ opt_out_type: 'LDP', content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -1397,8 +1481,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -1431,8 +1527,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -1488,7 +1596,7 @@ export const data = [ }, { destType: 'pinterest_tag', - description: 'Test 0', + description: 'Test 2', feature: 'router', module: 'destination', version: 'v0', diff --git a/test/integrations/destinations/pinterest_tag/step/data.ts b/test/integrations/destinations/pinterest_tag/step/data.ts index cbd0b243bbf..b607e3c9faf 100644 --- a/test/integrations/destinations/pinterest_tag/step/data.ts +++ b/test/integrations/destinations/pinterest_tag/step/data.ts @@ -75,6 +75,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -90,6 +91,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -101,6 +103,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -139,8 +144,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -232,6 +249,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -247,6 +265,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -258,6 +277,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -294,8 +316,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -368,6 +402,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -383,6 +418,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -394,6 +430,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -519,6 +558,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -534,6 +574,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -545,13 +586,17 @@ export const data = [ status: 200, body: [ { - error: 'Advertiser Id not found. Aborting', + error: + 'Advertiser Id not found. Aborting: Workflow: procWorkflow, Step: validateInput, ChildStep: undefined, OriginalError: Advertiser Id not found. Aborting', + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, statTags: { destType: 'PINTEREST_TAG', errorCategory: 'dataValidation', errorType: 'configuration', feature: 'processor', - implementation: 'native', + implementation: 'cdkV2', module: 'destination', }, statusCode: 400, @@ -633,6 +678,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -648,6 +694,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -660,13 +707,16 @@ export const data = [ body: [ { error: - 'It is required at least one of em, hashed_maids or pair of client_ip_address and client_user_agent', + 'It is required at least one of em, hashed_maids or pair of client_ip_address and client_user_agent: Workflow: procWorkflow, Step: validateUserFields, ChildStep: undefined, OriginalError: It is required at least one of em, hashed_maids or pair of client_ip_address and client_user_agent', + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, statTags: { destType: 'PINTEREST_TAG', errorCategory: 'dataValidation', errorType: 'instrumentation', feature: 'processor', - implementation: 'native', + implementation: 'cdkV2', module: 'destination', }, statusCode: 400, @@ -751,6 +801,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -766,6 +817,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -777,6 +829,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -813,8 +868,20 @@ export const data = [ order_id: '50314b8e9bcf000000000000', content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -907,6 +974,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -922,6 +990,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -933,13 +1002,17 @@ export const data = [ status: 200, body: [ { - error: 'Advertiser Id not found. Aborting', + error: + 'Advertiser Id not found. Aborting: Workflow: procWorkflow, Step: validateInput, ChildStep: undefined, OriginalError: Advertiser Id not found. Aborting', + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, statTags: { destType: 'PINTEREST_TAG', errorCategory: 'dataValidation', errorType: 'configuration', feature: 'processor', - implementation: 'native', + implementation: 'cdkV2', module: 'destination', }, statusCode: 400, @@ -1023,6 +1096,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -1038,6 +1112,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -1049,13 +1124,17 @@ export const data = [ status: 200, body: [ { - error: 'message type group is not supported', + error: + 'message type group is not supported: Workflow: procWorkflow, Step: validateInput, ChildStep: undefined, OriginalError: message type group is not supported', + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, statTags: { destType: 'PINTEREST_TAG', errorCategory: 'dataValidation', errorType: 'instrumentation', feature: 'processor', - implementation: 'native', + implementation: 'cdkV2', module: 'destination', }, statusCode: 400, @@ -1140,6 +1219,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -1155,6 +1235,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -1166,13 +1247,17 @@ export const data = [ status: 200, body: [ { - error: 'Action source must be one of app_android, app_ios, web, offline', + error: + 'Action source must be one of app_android, app_ios, web, offline: Workflow: procWorkflow, Step: validateCommonFields, ChildStep: undefined, OriginalError: Action source must be one of app_android, app_ios, web, offline', + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, statTags: { destType: 'PINTEREST_TAG', errorCategory: 'dataValidation', errorType: 'instrumentation', feature: 'processor', - implementation: 'native', + implementation: 'cdkV2', module: 'destination', }, statusCode: 400, @@ -1257,6 +1342,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -1273,6 +1359,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -1284,6 +1371,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -1320,8 +1410,20 @@ export const data = [ order_id: '50314b8e9bcf000000000000', content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -1378,6 +1480,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -1393,6 +1496,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -1404,6 +1508,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -1488,6 +1595,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -1503,6 +1611,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -1514,6 +1623,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -1598,6 +1710,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -1613,6 +1726,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -1624,6 +1738,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -1709,6 +1826,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -1724,6 +1842,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -1735,6 +1854,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -1821,6 +1943,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -1834,6 +1957,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -1845,6 +1969,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -1933,6 +2060,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -1946,6 +2074,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -1957,6 +2086,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -2096,6 +2228,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -2114,6 +2247,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -2125,6 +2259,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { body: { JSON: { @@ -2216,6 +2353,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -2232,6 +2370,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -2243,6 +2382,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -2360,6 +2502,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -2376,6 +2519,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -2387,6 +2531,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -2422,7 +2569,15 @@ export const data = [ order_id: '50314b8e9bcf000000000000', num_items: 1, content_ids: ['507f1f77bcf86cd799439011'], - contents: [{ quantity: 1, item_price: '19' }], + contents: [ + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + ], }, }, JSON_ARRAY: {}, @@ -2491,6 +2646,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -2506,6 +2662,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -2517,6 +2674,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { body: { FORM: {}, @@ -2644,6 +2804,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -2662,6 +2823,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -2673,6 +2835,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -2715,8 +2880,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -2810,6 +2987,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -2828,6 +3006,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -2839,6 +3018,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -2878,8 +3060,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -2979,6 +3173,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -2997,6 +3192,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -3008,6 +3204,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', @@ -3071,8 +3270,20 @@ export const data = [ num_items: 3, content_ids: ['507f1f77bcf86cd799439011', '505bd76785ebb509fc183733'], contents: [ - { quantity: 1, item_price: '19' }, - { quantity: 2, item_price: '3' }, + { + id: '507f1f77bcf86cd799439011', + item_category: 'Games', + item_name: 'Monopoly: 3rd Edition', + quantity: 1, + item_price: '19', + }, + { + id: '505bd76785ebb509fc183733', + item_category: 'Games', + item_name: 'Uno Card Game', + quantity: 2, + item_price: '3', + }, ], }, }, @@ -3129,6 +3340,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -3147,6 +3359,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -3158,13 +3371,17 @@ export const data = [ status: 200, body: [ { - error: 'Ad Account ID not found. Aborting', + error: + 'Ad Account ID not found. Aborting: Workflow: procWorkflow, Step: validateInput, ChildStep: undefined, OriginalError: Ad Account ID not found. Aborting', + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, statTags: { destType: 'PINTEREST_TAG', errorCategory: 'dataValidation', errorType: 'configuration', feature: 'processor', - implementation: 'native', + implementation: 'cdkV2', module: 'destination', }, statusCode: 400, @@ -3213,6 +3430,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -3231,6 +3449,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -3242,13 +3461,17 @@ export const data = [ status: 200, body: [ { - error: 'Conversion Token not found. Aborting', + error: + 'Conversion Token not found. Aborting: Workflow: procWorkflow, Step: validateInput, ChildStep: undefined, OriginalError: Conversion Token not found. Aborting', + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, statTags: { destType: 'PINTEREST_TAG', errorCategory: 'dataValidation', errorType: 'configuration', feature: 'processor', - implementation: 'native', + implementation: 'cdkV2', module: 'destination', }, statusCode: 400, @@ -3310,6 +3533,7 @@ export const data = [ destination: { ID: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', Name: 'PINTEREST_TAG', + DestinationDefinition: { Config: { cdkV2Enabled: true } }, Config: { sendAsTestEvent: false, tagId: '123456789', @@ -3328,6 +3552,7 @@ export const data = [ Enabled: true, Transformations: [], }, + metadata: { destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq' }, }, ], method: 'POST', @@ -3339,6 +3564,9 @@ export const data = [ status: 200, body: [ { + metadata: { + destintionId: '1pYpzzvcn7AQ2W9GGIAZSsN6Mfq', + }, output: { version: '1', type: 'REST', From 2070bb63f8b443ef7709d510fdb405b57d2d61d8 Mon Sep 17 00:00:00 2001 From: GitHub Actions Date: Fri, 18 Oct 2024 06:12:43 +0000 Subject: [PATCH 2/2] chore(release): 1.83.0 --- CHANGELOG.md | 7 +++++++ package-lock.json | 4 ++-- package.json | 2 +- 3 files changed, 10 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index a81c5b5feeb..dfe4f748426 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,13 @@ All notable changes to this project will be documented in this file. See [standard-version](https://github.com/conventional-changelog/standard-version) for commit guidelines. +## [1.83.0](https://github.com/rudderlabs/rudder-transformer/compare/v1.82.1...v1.83.0) (2024-10-18) + + +### Features + +* add missing fields on the pinterest_tag mapping ([#3798](https://github.com/rudderlabs/rudder-transformer/issues/3798)) ([eed35d3](https://github.com/rudderlabs/rudder-transformer/commit/eed35d30fbd6c51bec07d38edbc7026391ab146a)), closes [#3796](https://github.com/rudderlabs/rudder-transformer/issues/3796) + ### [1.82.1](https://github.com/rudderlabs/rudder-transformer/compare/v1.82.0...v1.82.1) (2024-10-16) diff --git a/package-lock.json b/package-lock.json index d3b578f6856..ccf7ed2c2ae 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "rudder-transformer", - "version": "1.82.1", + "version": "1.83.0", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "rudder-transformer", - "version": "1.82.1", + "version": "1.83.0", "license": "ISC", "dependencies": { "@amplitude/ua-parser-js": "0.7.24", diff --git a/package.json b/package.json index f5d44d8e2b2..79571462d3a 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "rudder-transformer", - "version": "1.82.1", + "version": "1.83.0", "description": "", "homepage": "https://github.com/rudderlabs/rudder-transformer#readme", "bugs": {