Skip to content

Commit

Permalink
Add test for conflict resolution testing.
Browse files Browse the repository at this point in the history
  • Loading branch information
dompuiu committed Oct 9, 2024
1 parent 567fbeb commit 2666146
Show file tree
Hide file tree
Showing 2 changed files with 378 additions and 0 deletions.
251 changes: 251 additions & 0 deletions test/functional/fixtures/Personalization/conflictResolutions.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,251 @@
/*
Copyright 2024 Adobe. All rights reserved.
This file is licensed to you under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License. You may obtain a copy
of the License at http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software distributed under
the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR REPRESENTATIONS
OF ANY KIND, either express or implied. See the License for the specific language
governing permissions and limitations under the License.
*/
export const inAppMessagesPropositions = {
requestId: "09ead9d7-b91f-41d6-9bb5-e7a5396315d6",
handle: [
{
payload: [
{
id: "03560676528201411421379778603411811904",
namespace: {
code: "ECID",
},
},
],
type: "identity:result",
},
{
payload: [
{
id: "id2",
scope: "web://www.test.com/",
scopeDetails: {
rank: 2,
decisionProvider: "AJO",
correlationID: "3a034993-3bdb-4d8d-870f-0817e8949ebd-0",
characteristics: {
eventToken:
"eyJtZXNzYWdlRXhlY3V0aW9uIjp7Im1lc3NhZ2VFeGVjdXRpb25JRCI6IlVFOkluYm91bmQiLCJtZXNzYWdlSUQiOiIxYmQ4NWMwMC1iNGM5LTQ0NjQtYjIyMC1hYzY5ZTY5NGI1M2QiLCJtZXNzYWdlUHVibGljYXRpb25JRCI6IjNhMDM0OTkzLTNiZGItNGQ4ZC04NzBmLTA4MTdlODk0OWViZCIsIm1lc3NhZ2VUeXBlIjoibWFya2V0aW5nIiwiY2FtcGFpZ25JRCI6IjY4ODg5NDdjLTAyZDQtNDFhNi05YzZjLTE1YTU4ZTVlNzcyYyIsImNhbXBhaWduVmVyc2lvbklEIjoiNDU1NzE2MmQtNzgyMi00Zjg4LTkyZWItMmMxZmViZTFhMmViIiwiY2FtcGFpZ25BY3Rpb25JRCI6ImNhMzJlZjZmLWY3NTItNDA2Ny04YmFlLTE1NGY2MDAyN2E3ZSJ9LCJtZXNzYWdlUHJvZmlsZSI6eyJtZXNzYWdlUHJvZmlsZUlEIjoiYjBlM2M0YjctMWE3YS00NTljLWE2YzUtNTFlNDU0ZDVjYmRiIiwiY2hhbm5lbCI6eyJfaWQiOiJodHRwczovL25zLmFkb2JlLmNvbS94ZG0vY2hhbm5lbHMvaW5BcHAiLCJfdHlwZSI6Imh0dHBzOi8vbnMuYWRvYmUuY29tL3hkbS9jaGFubmVsLXR5cGVzL2luQXBwIn19fQ==",
},
activity: {
id: "6888947c-02d4-41a6-9c6c-15a58e5e772c#ca32ef6f-f752-4067-8bae-154f60027a7e",
matchedSurfaces: ["web://surface1/"],
},
},
items: [
{
id: "e1090531-caee-4749-a738-680f393cf4a9",
schema: "https://ns.adobe.com/personalization/ruleset-item",
data: {
version: 1,
rules: [
{
condition: {
definition: {
key: "~type",
matcher: "eq",
values: ["com.adobe.eventType.rulesEngine"],
},
type: "matcher",
},
consequences: [
{
id: "f03980c9-5344-4e32-84c7-d74ffebf06d6",
type: "schema",
detail: {
id: "f03980c9-5344-4e32-84c7-d74ffebf06d6",
schema:
"https://ns.adobe.com/personalization/message/in-app",
data: {
content:
"<!doctype html><html><body>Proposition 2</body></html>",
contentType: "text/html",
remoteAssets: [
"https://cdn.experience.adobe.net/solutions/cjm-inapp-editor/assets/InAppBlockImageDefault.aa849e19.svg",
],
webParameters: {
"alloy-content-iframe": {
style: {
border: "none",
height: "100%",
width: "100%",
},
params: {
enabled: true,
insertionMethod: "appendChild",
parentElement: "#alloy-messaging-container",
},
},
"alloy-messaging-container": {
style: {
backgroundColor: "#000000",
border: "none",
borderRadius: "15px",
height: "100vh",
overflow: "hidden",
position: "fixed",
width: "100%",
left: "50%",
transform:
"translateX(-50%) translateY(-50%)",
top: "50%",
},
params: {
enabled: true,
insertionMethod: "appendChild",
parentElement: "body",
},
},
"alloy-overlay-container": {
style: {
position: "fixed",
top: "0",
left: "0",
width: "100%",
height: "100%",
background: "transparent",
opacity: 0.2,
backgroundColor: "#000000",
},
params: {
enabled: true,
insertionMethod: "appendChild",
parentElement: "body",
},
},
},
publishedDate: 1727568749,
},
},
},
],
},
],
},
},
],
},
{
id: "id1",
scope: "web://www.test.com/",
scopeDetails: {
rank: 1,
decisionProvider: "AJO",
correlationID: "d4f5d677-1123-4605-ad9e-86fead923220-0",
characteristics: {
eventToken:
"eyJtZXNzYWdlRXhlY3V0aW9uIjp7Im1lc3NhZ2VFeGVjdXRpb25JRCI6IlVFOkluYm91bmQiLCJtZXNzYWdlSUQiOiJiNmY1ODVmZS1mNWE1LTQ0NWUtYjU0OC0yOThlMmQ1MDFkZTYiLCJtZXNzYWdlUHVibGljYXRpb25JRCI6ImQ0ZjVkNjc3LTExMjMtNDYwNS1hZDllLTg2ZmVhZDkyMzIyMCIsIm1lc3NhZ2VUeXBlIjoibWFya2V0aW5nIiwiY2FtcGFpZ25JRCI6ImI3NWNkNDAyLTIwNzMtNDc5OC1hMDJjLTc0YmQyMDg0MmQyNyIsImNhbXBhaWduVmVyc2lvbklEIjoiMmExMDJjZDMtZmM0NC00ZDI0LWEzMWMtNzZhZTBmY2FjMWJhIiwiY2FtcGFpZ25BY3Rpb25JRCI6ImNhMzJlZjZmLWY3NTItNDA2Ny04YmFlLTE1NGY2MDAyN2E3ZSJ9LCJtZXNzYWdlUHJvZmlsZSI6eyJtZXNzYWdlUHJvZmlsZUlEIjoiNzEyZjYwN2UtNjNmNS00NGExLTg3ZDYtM2Y1NWQzYjVmNGM2IiwiY2hhbm5lbCI6eyJfaWQiOiJodHRwczovL25zLmFkb2JlLmNvbS94ZG0vY2hhbm5lbHMvaW5BcHAiLCJfdHlwZSI6Imh0dHBzOi8vbnMuYWRvYmUuY29tL3hkbS9jaGFubmVsLXR5cGVzL2luQXBwIn19fQ==",
},
activity: {
id: "b75cd402-2073-4798-a02c-74bd20842d27#ca32ef6f-f752-4067-8bae-154f60027a7e",
matchedSurfaces: ["web://surface1/"],
},
},
items: [
{
id: "471af8f8-7806-47ce-885e-45fffe14108a",
schema: "https://ns.adobe.com/personalization/ruleset-item",
data: {
version: 1,
rules: [
{
condition: {
definition: {
key: "~type",
matcher: "eq",
values: ["com.adobe.eventType.rulesEngine"],
},
type: "matcher",
},
consequences: [
{
id: "613e9843-7291-4505-9cca-3f76caff6bec",
type: "schema",
detail: {
id: "613e9843-7291-4505-9cca-3f76caff6bec",
schema:
"https://ns.adobe.com/personalization/message/in-app",
data: {
content:
"<!doctype html><html><body>Proposition 1</body></html>",
contentType: "text/html",
remoteAssets: [
"https://cdn.experience.adobe.net/solutions/cjm-inapp-editor/assets/InAppBlockImageDefault.aa849e19.svg",
],
webParameters: {
"alloy-content-iframe": {
style: {
border: "none",
height: "100%",
width: "100%",
},
params: {
enabled: true,
insertionMethod: "appendChild",
parentElement: "#alloy-messaging-container",
},
},
"alloy-messaging-container": {
style: {
backgroundColor: "#000000",
border: "none",
borderRadius: "15px",
height: "100vh",
overflow: "hidden",
position: "fixed",
width: "100%",
left: "50%",
transform:
"translateX(-50%) translateY(-50%)",
top: "50%",
},
params: {
enabled: true,
insertionMethod: "appendChild",
parentElement: "body",
},
},
"alloy-overlay-container": {
style: {
position: "fixed",
top: "0",
left: "0",
width: "100%",
height: "100%",
background: "transparent",
opacity: 0.2,
backgroundColor: "#000000",
},
params: {
enabled: true,
insertionMethod: "appendChild",
parentElement: "body",
},
},
},
publishedDate: 1727568995,
},
},
},
],
},
],
},
},
],
},
],
type: "personalization:decisions",
eventIndex: 0,
},
],
};
127 changes: 127 additions & 0 deletions test/functional/specs/Personalization/conflictResolutions.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,127 @@
/*
Copyright 2024 Adobe. All rights reserved.
This file is licensed to you under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License. You may obtain a copy
of the License at http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software distributed under
the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR REPRESENTATIONS
OF ANY KIND, either express or implied. See the License for the specific language
governing permissions and limitations under the License.
*/
import { ClientFunction, RequestMock, t } from "testcafe";
import createNetworkLogger from "../../helpers/networkLogger/index.js";
import createFixture from "../../helpers/createFixture/index.js";
import { inAppMessagesPropositions } from "../../fixtures/Personalization/conflictResolutions.js";
import createAlloyProxy from "../../helpers/createAlloyProxy.js";
import getBaseConfig from "../../helpers/getBaseConfig.js";
import {
compose,
debugEnabled,
} from "../../helpers/constants/configParts/index.js";

const networkLogger = createNetworkLogger();

const organizationId = "5BFE274A5F6980A50A495C08@AdobeOrg";
const dataStreamId = "ae47e1ea-7625-49b9-b69f-8ad372e46344";

const orgMainConfigMain = getBaseConfig(organizationId, dataStreamId);
const config = compose(orgMainConfigMain, debugEnabled);

const firstInteractCallReturnsInAppMessagesMock = () => {
let i = 0;
return RequestMock()
.onRequestTo((request) => {
if (request.url.includes("/interact")) {
i += 1;
}

const r = request.url.includes("/interact") && i === 2;
return r;
})
.respond(JSON.stringify(inAppMessagesPropositions), 200, {
"access-control-allow-origin": "https://alloyio.com",
"access-control-allow-credentials": true,
"content-type": " application/json;charset=utf-8",
});
};

createFixture({
title:
"Conflict resoulution: show one in app message propositions sorted by rank",
requestHooks: [
firstInteractCallReturnsInAppMessagesMock(),
networkLogger.edgeEndpointLogs,
],
});

test("propositions are sorted ascending by rank", async () => {
const alloy = createAlloyProxy();
await alloy.configure(config);

// Sending an event for getting an Identity cookie.
await alloy.sendEvent();

await alloy.sendEvent({
renderDecisions: true,
});

const result = await alloy.evaluateRulesets({
renderDecisions: true,
});

// When we receive multiple In-App messages propositions, DecisioningEngine will sort them ascending by rank.
// Lower rank means higher priority. We need to diplay just one proposition (with the rank 1). There can be
// multiple propositions with the same rank but with different surfaces.
// The mock returns the propositions in descending order by rank.
// For the displayed propositions an event with the type decisioning.propositionDisplay is sent back to the edge.
// For the suppressed propositions an event with the type decisioning.propositionSuppressDisplay is sent back to the edge.
await t.expect(result.propositions[0].scopeDetails.rank).eql(1);
await t.expect(result.propositions[1].scopeDetails.rank).eql(2);

const edgeRequest = networkLogger.edgeEndpointLogs.requests;

const propositionDisplayEvent = edgeRequest[edgeRequest.length - 2];
const propositionDisplayEventBody = JSON.parse(
propositionDisplayEvent.request.body,
);

await t
.expect(propositionDisplayEventBody.events[0].xdm.eventType)
.eql("decisioning.propositionDisplay");
await t
.expect(
// eslint-disable-next-line no-underscore-dangle
propositionDisplayEventBody.events[0].xdm._experience.decisioning
.propositions[0].id,
)
.eql("id1");

const propositionSuppressDisplayEvent = edgeRequest[edgeRequest.length - 1];
const propositionSuppressDisplayEventBody = JSON.parse(
propositionSuppressDisplayEvent.request.body,
);

await t
.expect(propositionSuppressDisplayEventBody.events[0].xdm.eventType)
.eql("decisioning.propositionSuppressDisplay");
await t
.expect(
// eslint-disable-next-line no-underscore-dangle
propositionSuppressDisplayEventBody.events[0].xdm._experience.decisioning
.propositions[0].id,
)
.eql("id2");

// Check there is only one iframe in the DOM.
const iframesContent = await ClientFunction(() => {
const iframes = document.querySelectorAll("#alloy-content-iframe");
const r = [];
iframes.forEach((i) => {
r.push(i.contentDocument.body.textContent);
});
return r;
})();
await t.expect(iframesContent.length).eql(1);
await t.expect(iframesContent[0]).eql("Proposition 1");
});

0 comments on commit 2666146

Please sign in to comment.