Skip to content

Commit 8cdf519

Browse files
add tests for auto-optin message handler
1 parent 53112d7 commit 8cdf519

File tree

1 file changed

+321
-0
lines changed

1 file changed

+321
-0
lines changed
Lines changed: 321 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,321 @@
1+
import {
2+
preMessageSave,
3+
postMessageSave
4+
} from "../../../src/extensions/message-handlers/auto-optin";
5+
import { cacheableData, r } from "../../../src/server/models";
6+
7+
import {
8+
setupTest,
9+
cleanupTest,
10+
createStartedCampaign
11+
} from "../../test_helpers";
12+
13+
const CacheableMessage = require("../../../src/server/models/cacheable_queries/message");
14+
const saveMessage = CacheableMessage.default.save;
15+
16+
const AutoOptin = require("../../../src/extensions/message-handlers/auto-optin");
17+
18+
const config = require("../../../src/server/api/lib/config");
19+
20+
describe("Auto Opt-In Tests", () => {
21+
let messageToSave;
22+
let organization;
23+
24+
beforeEach(() => {
25+
jest.resetAllMocks();
26+
27+
global.DEFAULT_SERVICE = "fakeservice";
28+
29+
jest.spyOn(cacheableData.optIn, "save").mockResolvedValue(null);
30+
jest.spyOn(cacheableData.campaignContact, "load").mockResolvedValue({
31+
id: 1,
32+
assignment_id: 2
33+
});
34+
jest.spyOn(AutoOptin, "available").mockReturnValue(true);
35+
jest.spyOn(config, "getConfig").mockReturnValue("");
36+
37+
messageToSave = {
38+
is_from_contact: true,
39+
contact_number: "+1234567890",
40+
capmaign_contact_id: 1,
41+
text: "START",
42+
campaign_contact_id: 42
43+
};
44+
// I think this is the structure,
45+
// even if wrong, doesnt affect test
46+
organization = 1;
47+
})
48+
49+
afterEach(() => {
50+
global.DEFAULT_SERVICE = "fakeservice";
51+
});
52+
53+
describe("preMessageSave", () => {
54+
it("returns object on default settings", async () => {
55+
const result = preMessageSave({
56+
messageToSave,
57+
organization
58+
});
59+
60+
expect(config.getConfig).toHaveBeenCalled();
61+
expect(result).toEqual({
62+
contactUpdates: {
63+
is_opted_in: true
64+
},
65+
handlerContext: {
66+
autoOptInReason: "start"
67+
},
68+
messageToSave
69+
})
70+
});
71+
72+
it("does not return with a non matching message", async () => {
73+
messageToSave = {
74+
...messageToSave,
75+
text: "just another message"
76+
};
77+
78+
const result = preMessageSave({
79+
messageToSave,
80+
organization
81+
});
82+
83+
expect(config.getConfig).toHaveBeenCalled();
84+
expect(result).toEqual(undefined);
85+
});
86+
87+
it("does not return, even when START is apart of the text", async () => {
88+
// This is inline with DEFAULT_AUTO_OPTIN_REGEX_LIST_BASE64.
89+
// If AUTO_OPTIN_REGEX_LIST_BASE64 is enabled, may change behavior.
90+
messageToSave = {
91+
...messageToSave,
92+
text: "START, but do not opt me in"
93+
};
94+
95+
const result = preMessageSave({
96+
messageToSave,
97+
organization
98+
});
99+
100+
expect(config.getConfig).toHaveBeenCalled();
101+
expect(result).toEqual(undefined);
102+
});
103+
104+
it("returns an object after changing default regex", async () => {
105+
// this also tests autoOptInReason is "optin"
106+
jest.spyOn(config, "getConfig").mockReturnValue(
107+
"W3sicmVnZXgiOiAiXk9QVC1JTiQiLCAicmVhc29uIjogIm9wdGluIn1d"
108+
); // [{"regex": "^OPT-IN$"", "reason": "optin"}]
109+
110+
messageToSave = {
111+
...messageToSave,
112+
text:"OPT-IN"
113+
};
114+
115+
const result = preMessageSave({
116+
messageToSave,
117+
organization
118+
})
119+
120+
expect(result).toEqual({
121+
contactUpdates: {
122+
is_opted_in: true
123+
},
124+
handlerContext: {
125+
autoOptInReason: "optin"
126+
},
127+
messageToSave
128+
})
129+
});
130+
131+
it("tests autoOptInReason defaults to \"auto_optin\" when no reason is given in regex", async () => {
132+
jest.spyOn(config, "getConfig").mockReturnValue(
133+
"W3sicmVnZXgiOiAiXk9QVC1JTiQifV0="
134+
); // [{"regex": "^OPT-IN$"}]
135+
136+
messageToSave = {
137+
...messageToSave,
138+
text: "OPT-IN"
139+
};
140+
141+
const result = preMessageSave({
142+
messageToSave,
143+
organization
144+
});
145+
146+
expect(result).toEqual({
147+
contactUpdates: {
148+
is_opted_in: true
149+
},
150+
handlerContext: {
151+
autoOptInReason: "auto_optin"
152+
},
153+
messageToSave
154+
})
155+
});
156+
})
157+
158+
describe("postMessageSave", () => {
159+
let message;
160+
let organization;
161+
let handlerContext;
162+
let campaign;
163+
164+
beforeEach( async () => {
165+
jest.restoreAllMocks();
166+
167+
global.DEFAULT_SERVICE = "fakeservice";
168+
169+
message = {
170+
is_from_contact: true,
171+
campaign_contact_id: 42
172+
};
173+
174+
organization = {
175+
id: 2
176+
};
177+
178+
handlerContext = {
179+
autoOptInReason: "start"
180+
};
181+
182+
campaign = {}
183+
184+
jest.spyOn(cacheableData.campaignContact, "load").mockReturnValue(null);
185+
jest.spyOn(cacheableData.optIn, "save").mockReturnValue(null);
186+
});
187+
188+
afterEach(async () => {
189+
jest.restoreAllMocks();
190+
global.DEFAULT_SERVICE = "fakeservice";
191+
});
192+
193+
it("saves to optIn table", async () => {
194+
await postMessageSave({
195+
message,
196+
organization,
197+
handlerContext,
198+
campaign
199+
});
200+
201+
expect(cacheableData.campaignContact.load).toHaveBeenCalled();
202+
expect(cacheableData.optIn.save).toHaveBeenCalled();
203+
});
204+
205+
it("does not save to optin table with no handlerContext.autoOptInReason", async () => {
206+
handlerContext = {};
207+
208+
await postMessageSave({
209+
message,
210+
organization,
211+
handlerContext,
212+
campaign
213+
});
214+
215+
expect(cacheableData.campaignContact.load).toHaveBeenCalledTimes(0);
216+
expect(cacheableData.optIn.save).toHaveBeenCalledTimes(0);
217+
});
218+
219+
it("does not save to optin table with when message is not from contact", async () => {
220+
message = {};
221+
222+
await postMessageSave({
223+
message,
224+
organization,
225+
handlerContext,
226+
campaign
227+
});
228+
229+
expect(cacheableData.campaignContact.load).toHaveBeenCalledTimes(0);
230+
expect(cacheableData.optIn.save).toHaveBeenCalledTimes(0);
231+
});
232+
});
233+
});
234+
235+
describe("Tests for Auto Opt-Out's members getting called from messageCache.save", () => {
236+
let contacts;
237+
let organization;
238+
let texter;
239+
240+
let service;
241+
let messageServiceSID;
242+
243+
beforeEach(async () => {
244+
await cleanupTest();
245+
await setupTest();
246+
jest.restoreAllMocks();
247+
248+
global.MESSAGE_HANDLERS = "auto-optin";
249+
250+
const startedCampaign = await createStartedCampaign();
251+
252+
({
253+
testContacts: contacts,
254+
testTexterUser: texter,
255+
testOrganization: {
256+
data: { createOrganization: organization }
257+
}
258+
} = startedCampaign);
259+
260+
service = "twilio";
261+
messageServiceSID = "some_messsage_service_id";
262+
263+
const messageToContact = {
264+
is_from_contact: false,
265+
contact_number: contacts[0].cell,
266+
campaign_contact_id: contacts[0].id,
267+
send_status: "SENT",
268+
text: "Hi",
269+
service,
270+
texter,
271+
messageservice_sid: messageServiceSID
272+
};
273+
274+
await saveMessage({
275+
messageInstance: messageToContact,
276+
contact: contacts[0],
277+
organization,
278+
texter
279+
});
280+
}, global.DATABASE_SETUP_TEARDOWN_TIMEOUT);
281+
282+
afterEach(async () => {
283+
await cleanupTest();
284+
}, global.DATABASE_SETUP_TEARDOWN_TIMEOUT);
285+
286+
it("gets called", async () => {
287+
const message = {
288+
is_from_contact: true,
289+
contact_number: contacts[0].cell,
290+
service,
291+
messageservice_sid: messageServiceSID,
292+
text: "START",
293+
send_status: "DELIVERED" // ??
294+
};
295+
296+
jest.spyOn(AutoOptin, "preMessageSave").mockResolvedValue(null);
297+
jest.spyOn(AutoOptin, "postMessageSave").mockResolvedValue(null);
298+
299+
await saveMessage({
300+
messageInstance: message
301+
});
302+
303+
expect(AutoOptin.preMessageSave).toHaveBeenCalledWith(
304+
expect.objectContaining({
305+
messageToSave: expect.objectContaining({
306+
text: "START",
307+
contact_number: contacts[0].cell
308+
})
309+
})
310+
);
311+
312+
expect(AutoOptin.postMessageSave).toHaveBeenCalledWith(
313+
expect.objectContaining({
314+
message: expect.objectContaining({
315+
text: "START",
316+
contact_number: contacts[0].cell
317+
})
318+
})
319+
);
320+
});
321+
});

0 commit comments

Comments
 (0)