From ef89c4deeb676450d75423b5886e8d0d6bdf13bb Mon Sep 17 00:00:00 2001
From: Yashasvi Bajpai <33063622+yashasvibajpai@users.noreply.github.com>
Date: Thu, 30 Nov 2023 10:02:23 +0530
Subject: [PATCH 1/7] chore: init onboard
---
src/features.json | 1 +
src/v0/destinations/adobe_analytics/config.js | 1 +
.../adobe_analytics/networkHandler.js | 71 +++++++++++++++++++
3 files changed, 73 insertions(+)
create mode 100644 src/v0/destinations/adobe_analytics/networkHandler.js
diff --git a/src/features.json b/src/features.json
index 224968c99b..848b606b47 100644
--- a/src/features.json
+++ b/src/features.json
@@ -1,6 +1,7 @@
{
"routerTransform": {
"ACTIVE_CAMPAIGN": true,
+ "ADOBE_ANALYTICS": true,
"ALGOLIA": true,
"CANDU": true,
"DELIGHTED": true,
diff --git a/src/v0/destinations/adobe_analytics/config.js b/src/v0/destinations/adobe_analytics/config.js
index 7a66b32a48..232fe61f7f 100644
--- a/src/v0/destinations/adobe_analytics/config.js
+++ b/src/v0/destinations/adobe_analytics/config.js
@@ -44,4 +44,5 @@ module.exports = {
ECOM_PRODUCT_EVENTS,
commonConfig: MAPPING_CONFIG[CONFIG_CATEGORIES.COMMON.name],
formatDestinationConfig,
+ DESTINATION: 'ADOBE_ANALYTICS'
};
diff --git a/src/v0/destinations/adobe_analytics/networkHandler.js b/src/v0/destinations/adobe_analytics/networkHandler.js
new file mode 100644
index 0000000000..4b8de886e3
--- /dev/null
+++ b/src/v0/destinations/adobe_analytics/networkHandler.js
@@ -0,0 +1,71 @@
+const { NetworkError } = require('@rudderstack/integrations-lib');
+const { proxyRequest, prepareProxyRequest } = require('../../../adapters/network');
+const {
+ getDynamicErrorType,
+ processAxiosResponse,
+} = require('../../../adapters/utils/networkUtils');
+const { DESTINATION } = require('./config');
+const { isDefinedAndNotNull, isDefined, isHttpStatusSuccess } = require('../../util');
+
+const tags = require('../../util/tags');
+
+const responseHandler = (destinationResponse, dest) => {
+ const message = `[${DESTINATION}] - Request Processed Successfully`;
+ let { status, reason } = destinationResponse;
+ const { response } = destinationResponse;
+ if (status === 204) {
+ // GA4 always returns a 204 response, other than in case of
+ // validation endpoint.
+ status = 200;
+ } else if (
+ status === 200 &&
+ isDefinedAndNotNull(response) &&
+ isDefined(response.validationMessages)
+ ) {
+ // for GA4 debug validation endpoint, status is always 200
+ // validationMessages[] is empty, thus event is valid
+ if (response.validationMessages?.length === 0) {
+ status = 200;
+ } else {
+ // Build the error in case the validationMessages[] is non-empty
+ const { description, validationCode, fieldPath } = response.validationMessages[0];
+ throw new NetworkError(
+ `Validation Server Response Handler:: Validation Error for ${dest} of field path :${fieldPath} | ${validationCode}-${description}`,
+ status,
+ {
+ [tags.TAG_NAMES.ERROR_TYPE]: getDynamicErrorType(status),
+ },
+ response?.validationMessages[0]?.description,
+ );
+ }
+ }
+
+ // if the response from destination is not a success case build an explicit error
+ if (!isHttpStatusSuccess(status)) {
+ throw new NetworkError(
+ `[GA4 Response Handler] Request failed for destination ${dest} with status: ${status}`,
+ status,
+ {
+ [tags.TAG_NAMES.ERROR_TYPE]: getDynamicErrorType(status),
+ },
+ destinationResponse,
+ );
+ }
+
+ return {
+ status,
+ message,
+ destinationResponse,
+ };
+};
+
+function networkHandler() {
+ this.responseHandler = responseHandler;
+ this.proxy = proxyRequest;
+ this.prepareProxy = prepareProxyRequest;
+ this.processAxiosResponse = processAxiosResponse;
+}
+
+module.exports = {
+ networkHandler,
+};
From ba3c162e2e2314feae548d021694fc9d5cf6c306 Mon Sep 17 00:00:00 2001
From: Yashasvi Bajpai <33063622+yashasvibajpai@users.noreply.github.com>
Date: Thu, 30 Nov 2023 13:33:35 +0530
Subject: [PATCH 2/7] chore: add network handler
---
src/features.json | 1 -
.../adobe_analytics/networkHandler.js | 65 +++++++------------
2 files changed, 24 insertions(+), 42 deletions(-)
diff --git a/src/features.json b/src/features.json
index 848b606b47..224968c99b 100644
--- a/src/features.json
+++ b/src/features.json
@@ -1,7 +1,6 @@
{
"routerTransform": {
"ACTIVE_CAMPAIGN": true,
- "ADOBE_ANALYTICS": true,
"ALGOLIA": true,
"CANDU": true,
"DELIGHTED": true,
diff --git a/src/v0/destinations/adobe_analytics/networkHandler.js b/src/v0/destinations/adobe_analytics/networkHandler.js
index 4b8de886e3..b5b58ade0c 100644
--- a/src/v0/destinations/adobe_analytics/networkHandler.js
+++ b/src/v0/destinations/adobe_analytics/networkHandler.js
@@ -1,57 +1,40 @@
-const { NetworkError } = require('@rudderstack/integrations-lib');
+const { InstrumentationError } = require('@rudderstack/integrations-lib');
const { proxyRequest, prepareProxyRequest } = require('../../../adapters/network');
const {
- getDynamicErrorType,
processAxiosResponse,
} = require('../../../adapters/utils/networkUtils');
const { DESTINATION } = require('./config');
-const { isDefinedAndNotNull, isDefined, isHttpStatusSuccess } = require('../../util');
-const tags = require('../../util/tags');
+
+/**
+ * Extract data inside different tags from an xml payload
+ * @param {*} xml
+ * @param {*} tagName
+ * @returns data inside the tagName
+ */
+function extractContent(xmlPayload, tagName) {
+ const pattern = new RegExp(`<${tagName}>(.*?)${tagName}>`);
+ const match = xmlPayload.match(pattern);
+ return match ? match[1] : null;
+}
const responseHandler = (destinationResponse, dest) => {
const message = `[${DESTINATION}] - Request Processed Successfully`;
- let { status, reason } = destinationResponse;
- const { response } = destinationResponse;
- if (status === 204) {
- // GA4 always returns a 204 response, other than in case of
- // validation endpoint.
- status = 200;
- } else if (
- status === 200 &&
- isDefinedAndNotNull(response) &&
- isDefined(response.validationMessages)
- ) {
- // for GA4 debug validation endpoint, status is always 200
- // validationMessages[] is empty, thus event is valid
- if (response.validationMessages?.length === 0) {
- status = 200;
+ const { response, status } = destinationResponse;
+
+ // Extract values between different tags
+ const responseStatus = extractContent(response, 'status');
+ const reason = extractContent(response, 'reason');
+
+ // if the status tag in XML contains FAILURE, we build and throw an explicit error
+ if (responseStatus === 'FAILURE') {
+ if (reason) {
+ throw new InstrumentationError(`[${DESTINATION} Response Handler] Request failed for destination ${dest} : ${reason}` )
} else {
- // Build the error in case the validationMessages[] is non-empty
- const { description, validationCode, fieldPath } = response.validationMessages[0];
- throw new NetworkError(
- `Validation Server Response Handler:: Validation Error for ${dest} of field path :${fieldPath} | ${validationCode}-${description}`,
- status,
- {
- [tags.TAG_NAMES.ERROR_TYPE]: getDynamicErrorType(status),
- },
- response?.validationMessages[0]?.description,
- );
+ throw new InstrumentationError(`[${DESTINATION} Response Handler] Request failed for destination ${dest} with a general error`)
}
}
- // if the response from destination is not a success case build an explicit error
- if (!isHttpStatusSuccess(status)) {
- throw new NetworkError(
- `[GA4 Response Handler] Request failed for destination ${dest} with status: ${status}`,
- status,
- {
- [tags.TAG_NAMES.ERROR_TYPE]: getDynamicErrorType(status),
- },
- destinationResponse,
- );
- }
-
return {
status,
message,
From a245f1817897f36b980f4033348eef41ed6ccfc8 Mon Sep 17 00:00:00 2001
From: Yashasvi Bajpai <33063622+yashasvibajpai@users.noreply.github.com>
Date: Tue, 5 Dec 2023 01:51:26 +0530
Subject: [PATCH 3/7] chore: add test
---
.../adobe_analytics/dataDelivery/data.ts | 53 +++++++++++++++++++
.../destinations/adobe_analytics/network.ts | 17 ++++++
2 files changed, 70 insertions(+)
create mode 100644 test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
create mode 100644 test/integrations/destinations/adobe_analytics/network.ts
diff --git a/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts b/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
new file mode 100644
index 0000000000..8f5442fb6f
--- /dev/null
+++ b/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
@@ -0,0 +1,53 @@
+export const data = [
+ {
+ name: 'adobe_analytics',
+ description: 'Test 0',
+ feature: 'dataDelivery',
+ module: 'destination',
+ version: 'v0',
+ input: {
+ request: {
+ body: {
+ version: '1',
+ type: 'REST',
+ method: 'POST',
+ endpoint: 'https://adobe.failure.omtrdc.net/b/ss//6',
+ headers: {
+ 'Content-type': 'application/xml',
+ },
+ params: {},
+ body: {
+ JSON: {},
+ JSON_ARRAY: {},
+ XML: {
+ payload:
+ '17941080sales campaignwebUSD127.0.0.1en-USDalvik/2.1.0 (Linux; U; Android 9; Android SDK built for x86 Build/PSR1.180720.075)https://www.google.com/search?q=estore+bestsellerprodViewGames;;11;148.39rudderstackfootlockerpoc',
+ },
+ FORM: {},
+ },
+ files: {},
+ },
+ method: 'POST',
+ },
+ },
+ output: {
+ response: {
+ status: 500,
+ statTags: {
+ errorCategory: 'dataValidation',
+ errorType: 'instrumentation',
+ destType: 'ADOBE_ANALYTICS',
+ module: 'destination',
+ implementation: 'native',
+ feature: 'dataDelivery',
+ destinationId: '2S3s0dFD0DqL7m0UkfBwyblDrzs',
+ workspaceId: '1pKWrE6GwAvFwKBikka1SbRgrSN',
+ },
+ destinationResponse: '',
+ authErrorCategory: '',
+ message:
+ '[ADOBE_ANALYTICS Response Handler] Request failed for destination adobe_analytics : NO pagename OR pageurl',
+ },
+ },
+ },
+];
diff --git a/test/integrations/destinations/adobe_analytics/network.ts b/test/integrations/destinations/adobe_analytics/network.ts
new file mode 100644
index 0000000000..35fe44804c
--- /dev/null
+++ b/test/integrations/destinations/adobe_analytics/network.ts
@@ -0,0 +1,17 @@
+export const networkCallsData = [
+ {
+ httpReq: {
+ url: 'https://adobe.failure.omtrdc.net/b/ss//6',
+ params: {},
+ headers: {
+ 'Content-type': 'application/xml',
+ },
+ method: 'POST',
+ },
+ httpRes: {
+ status: 400,
+ message:
+ '[ADOBE_ANALYTICS Response Handler] Request failed for destination adobe_analytics : NO pagename OR pageurl',
+ },
+ },
+];
From 5b403cacdbfe5baf381704f196d4b03f3deccfa1 Mon Sep 17 00:00:00 2001
From: Sai Sankeerth
Date: Mon, 11 Dec 2023 14:23:51 +0530
Subject: [PATCH 4/7] fix: adding correct mock with corrections & modify the
status-code in test-case
Signed-off-by: Sai Sankeerth
---
.../destinations/adobe_analytics/dataDelivery/data.ts | 2 +-
test/integrations/destinations/adobe_analytics/network.ts | 8 ++++----
2 files changed, 5 insertions(+), 5 deletions(-)
diff --git a/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts b/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
index 8f5442fb6f..b3aa1e7860 100644
--- a/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
+++ b/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
@@ -32,7 +32,7 @@ export const data = [
},
output: {
response: {
- status: 500,
+ status: 400,
statTags: {
errorCategory: 'dataValidation',
errorType: 'instrumentation',
diff --git a/test/integrations/destinations/adobe_analytics/network.ts b/test/integrations/destinations/adobe_analytics/network.ts
index 35fe44804c..c6d83e9813 100644
--- a/test/integrations/destinations/adobe_analytics/network.ts
+++ b/test/integrations/destinations/adobe_analytics/network.ts
@@ -2,16 +2,16 @@ export const networkCallsData = [
{
httpReq: {
url: 'https://adobe.failure.omtrdc.net/b/ss//6',
+ data: '17941080sales campaignwebUSD127.0.0.1en-USDalvik/2.1.0 (Linux; U; Android 9; Android SDK built for x86 Build/PSR1.180720.075)https://www.google.com/search?q=estore+bestsellerprodViewGames;;11;148.39rudderstackfootlockerpoc',
params: {},
headers: {
- 'Content-type': 'application/xml',
+ 'Content-Type': 'application/xml',
},
method: 'POST',
},
httpRes: {
- status: 400,
- message:
- '[ADOBE_ANALYTICS Response Handler] Request failed for destination adobe_analytics : NO pagename OR pageurl',
+ status: 200,
+ data: 'FAILURENO pagename OR pageurl',
},
},
];
From 554a5a159d80fba83f829bff997095fea7820857 Mon Sep 17 00:00:00 2001
From: Yashasvi Bajpai <33063622+yashasvibajpai@users.noreply.github.com>
Date: Mon, 11 Dec 2023 14:54:16 +0530
Subject: [PATCH 5/7] chore: add dummy destination id
---
.../destinations/adobe_analytics/dataDelivery/data.ts | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts b/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
index b3aa1e7860..e96f4ba81d 100644
--- a/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
+++ b/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
@@ -40,7 +40,7 @@ export const data = [
module: 'destination',
implementation: 'native',
feature: 'dataDelivery',
- destinationId: '2S3s0dFD0DqL7m0UkfBwyblDrzs',
+ destinationId: '2S3s0dXXXXXX7m0UfBwyblDrzs',
workspaceId: '1pKWrE6GwAvFwKBikka1SbRgrSN',
},
destinationResponse: '',
From 22db262474cca8f29ba6e008377262a9b77ca045 Mon Sep 17 00:00:00 2001
From: Yashasvi Bajpai <33063622+yashasvibajpai@users.noreply.github.com>
Date: Mon, 11 Dec 2023 15:10:53 +0530
Subject: [PATCH 6/7] chore: add dummy ws id
---
.../destinations/adobe_analytics/dataDelivery/data.ts | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts b/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
index e96f4ba81d..f63b6ab0e1 100644
--- a/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
+++ b/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
@@ -41,7 +41,7 @@ export const data = [
implementation: 'native',
feature: 'dataDelivery',
destinationId: '2S3s0dXXXXXX7m0UfBwyblDrzs',
- workspaceId: '1pKWrE6GwAvFwKBikka1SbRgrSN',
+ workspaceId: '1pKWrE6GXXXXXKBikka1SbRgrSN',
},
destinationResponse: '',
authErrorCategory: '',
From ecc73221c68ac9597561a33647b8f3d19c449038 Mon Sep 17 00:00:00 2001
From: Yashasvi Bajpai <33063622+yashasvibajpai@users.noreply.github.com>
Date: Mon, 11 Dec 2023 15:52:27 +0530
Subject: [PATCH 7/7] chore: add tests for success and generic error case
---
.../adobe_analytics/dataDelivery/data.ts | 93 ++++++++++++++++++-
.../destinations/adobe_analytics/network.ts | 32 ++++++-
2 files changed, 122 insertions(+), 3 deletions(-)
diff --git a/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts b/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
index f63b6ab0e1..182969da73 100644
--- a/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
+++ b/test/integrations/destinations/adobe_analytics/dataDelivery/data.ts
@@ -1,7 +1,7 @@
export const data = [
{
name: 'adobe_analytics',
- description: 'Test 0',
+ description: 'Test 0: Failure response from Adobe Analytics with reason',
feature: 'dataDelivery',
module: 'destination',
version: 'v0',
@@ -21,7 +21,7 @@ export const data = [
JSON_ARRAY: {},
XML: {
payload:
- '17941080sales campaignwebUSD127.0.0.1en-USDalvik/2.1.0 (Linux; U; Android 9; Android SDK built for x86 Build/PSR1.180720.075)https://www.google.com/search?q=estore+bestsellerprodViewGames;;11;148.39rudderstackfootlockerpoc',
+ '17941080sales campaignwebUSD127.0.0.1en-USDalvik/2.1.0 (Linux; U; Android 9; Android SDK built for x86 Build/PSR1.180720.075)https://www.google.com/search?q=estore+bestsellerprodViewGames;;11;148.39failureReport',
},
FORM: {},
},
@@ -50,4 +50,93 @@ export const data = [
},
},
},
+ {
+ name: 'adobe_analytics',
+ description: 'Test 1: Failure response from Adobe Analytics without reason (Generic error)',
+ feature: 'dataDelivery',
+ module: 'destination',
+ version: 'v0',
+ input: {
+ request: {
+ body: {
+ version: '1',
+ type: 'REST',
+ method: 'POST',
+ endpoint: 'https://adobe.failure2.omtrdc.net/b/ss//6',
+ headers: {
+ 'Content-type': 'application/xml',
+ },
+ params: {},
+ body: {
+ JSON: {},
+ JSON_ARRAY: {},
+ XML: {
+ payload:
+ '17941080sales campaignwebUSD127.0.0.1en-USDalvik/2.1.0 (Linux; U; Android 9; Android SDK built for x86 Build/PSR1.180720.075)https://www.google.com/search?q=estore+bestsellerprodViewGames;;11;148.39failureReportgeneric',
+ },
+ FORM: {},
+ },
+ files: {},
+ },
+ method: 'POST',
+ },
+ },
+ output: {
+ response: {
+ status: 400,
+ statTags: {
+ errorCategory: 'dataValidation',
+ errorType: 'instrumentation',
+ destType: 'ADOBE_ANALYTICS',
+ module: 'destination',
+ implementation: 'native',
+ feature: 'dataDelivery',
+ destinationId: '2S3s0dXXXXXX7m0UfBwyblDrzs',
+ workspaceId: '1pKWrE6GXXXXXKBikka1SbRgrSN',
+ },
+ destinationResponse: '',
+ authErrorCategory: '',
+ message:
+ '[ADOBE_ANALYTICS Response Handler] Request failed for destination adobe_analytics with a general error',
+ },
+ },
+ },
+ {
+ name: 'adobe_analytics',
+ description: 'Test 2: Success response from Adobe Analytics',
+ feature: 'dataDelivery',
+ module: 'destination',
+ version: 'v0',
+ input: {
+ request: {
+ body: {
+ version: '1',
+ type: 'REST',
+ method: 'POST',
+ endpoint: 'https://adobe.success.omtrdc.net/b/ss//6',
+ headers: {
+ 'Content-type': 'application/xml',
+ },
+ params: {},
+ body: {
+ JSON: {},
+ JSON_ARRAY: {},
+ XML: {
+ payload:
+ '127.0.1.0www.google.co.inGoogleid1110011prodViewGames;Monopoly;1;14.00,Games;UNO;2;6.90successreport',
+ },
+ FORM: {},
+ },
+ files: {},
+ },
+ method: 'POST',
+ },
+ },
+ output: {
+ response: {
+ status: 200,
+ destinationResponse: 'SUCCESS',
+ },
+ },
+ },
];
diff --git a/test/integrations/destinations/adobe_analytics/network.ts b/test/integrations/destinations/adobe_analytics/network.ts
index c6d83e9813..2fe4f0204e 100644
--- a/test/integrations/destinations/adobe_analytics/network.ts
+++ b/test/integrations/destinations/adobe_analytics/network.ts
@@ -2,7 +2,7 @@ export const networkCallsData = [
{
httpReq: {
url: 'https://adobe.failure.omtrdc.net/b/ss//6',
- data: '17941080sales campaignwebUSD127.0.0.1en-USDalvik/2.1.0 (Linux; U; Android 9; Android SDK built for x86 Build/PSR1.180720.075)https://www.google.com/search?q=estore+bestsellerprodViewGames;;11;148.39rudderstackfootlockerpoc',
+ data: '17941080sales campaignwebUSD127.0.0.1en-USDalvik/2.1.0 (Linux; U; Android 9; Android SDK built for x86 Build/PSR1.180720.075)https://www.google.com/search?q=estore+bestsellerprodViewGames;;11;148.39failureReport',
params: {},
headers: {
'Content-Type': 'application/xml',
@@ -14,4 +14,34 @@ export const networkCallsData = [
data: 'FAILURENO pagename OR pageurl',
},
},
+ {
+ httpReq: {
+ url: 'https://adobe.failure2.omtrdc.net/b/ss//6',
+ data: '17941080sales campaignwebUSD127.0.0.1en-USDalvik/2.1.0 (Linux; U; Android 9; Android SDK built for x86 Build/PSR1.180720.075)https://www.google.com/search?q=estore+bestsellerprodViewGames;;11;148.39failureReportgeneric',
+ params: {},
+ headers: {
+ 'Content-Type': 'application/xml',
+ },
+ method: 'POST',
+ },
+ httpRes: {
+ status: 200,
+ data: 'FAILURE',
+ },
+ },
+ {
+ httpReq: {
+ url: 'https://adobe.success.omtrdc.net/b/ss//6',
+ data: '127.0.1.0www.google.co.inGoogleid1110011prodViewGames;Monopoly;1;14.00,Games;UNO;2;6.90successreport',
+ params: {},
+ headers: {
+ 'Content-Type': 'application/xml',
+ },
+ method: 'POST',
+ },
+ httpRes: {
+ status: 200,
+ data: 'SUCCESS',
+ },
+ },
];