@lodashventure/medusa-login-provider 4.1.3 → 4.1.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,351 +0,0 @@
1
- "use strict";
2
- var __importDefault = (this && this.__importDefault) || function (mod) {
3
- return (mod && mod.__esModule) ? mod : { "default": mod };
4
- };
5
- Object.defineProperty(exports, "__esModule", { value: true });
6
- const crypto_1 = __importDefault(require("crypto"));
7
- const utils_1 = require("@medusajs/framework/utils");
8
- const utils_2 = require("../utils");
9
- // Mock crypto for consistent testing
10
- jest.mock("crypto");
11
- const mockCrypto = crypto_1.default;
12
- describe("LINE Utils", () => {
13
- beforeEach(() => {
14
- jest.clearAllMocks();
15
- // Reset Date.now mock
16
- jest.spyOn(Date, "now").mockRestore();
17
- });
18
- describe("generateState", () => {
19
- it("should generate a 64-character hex string", () => {
20
- const mockBuffer = Buffer.from("a".repeat(32));
21
- mockCrypto.randomBytes.mockReturnValue(mockBuffer);
22
- const state = (0, utils_2.generateState)();
23
- expect(mockCrypto.randomBytes).toHaveBeenCalledWith(32);
24
- expect(state).toBe("a".repeat(64));
25
- expect(state).toHaveLength(64);
26
- });
27
- it("should generate different values on subsequent calls", () => {
28
- mockCrypto.randomBytes
29
- .mockReturnValueOnce(Buffer.from("a".repeat(32)))
30
- .mockReturnValueOnce(Buffer.from("b".repeat(32)));
31
- const state1 = (0, utils_2.generateState)();
32
- const state2 = (0, utils_2.generateState)();
33
- expect(state1).not.toBe(state2);
34
- });
35
- });
36
- describe("generateNonce", () => {
37
- it("should generate a 32-character hex string", () => {
38
- const mockBuffer = Buffer.from("c".repeat(16));
39
- mockCrypto.randomBytes.mockReturnValue(mockBuffer);
40
- const nonce = (0, utils_2.generateNonce)();
41
- expect(mockCrypto.randomBytes).toHaveBeenCalledWith(16);
42
- expect(nonce).toBe("c".repeat(32));
43
- expect(nonce).toHaveLength(32);
44
- });
45
- });
46
- describe("generatePlaceholderEmail", () => {
47
- it("should generate email with default domain", () => {
48
- const email = (0, utils_2.generatePlaceholderEmail)("U123456");
49
- expect(email).toBe("line-U123456@line.local");
50
- });
51
- it("should generate email with custom domain", () => {
52
- const email = (0, utils_2.generatePlaceholderEmail)("U123456", "example.com");
53
- expect(email).toBe("line-U123456@example.com");
54
- });
55
- it("should handle empty LINE user ID", () => {
56
- const email = (0, utils_2.generatePlaceholderEmail)("");
57
- expect(email).toBe("line-@line.local");
58
- });
59
- it("should handle special characters in LINE user ID", () => {
60
- const email = (0, utils_2.generatePlaceholderEmail)("U123-456_789");
61
- expect(email).toBe("line-U123-456_789@line.local");
62
- });
63
- });
64
- describe("parseDisplayName", () => {
65
- it("should parse single name", () => {
66
- const result = (0, utils_2.parseDisplayName)("John");
67
- expect(result).toEqual({
68
- firstName: "John",
69
- lastName: "",
70
- });
71
- });
72
- it("should parse full name", () => {
73
- const result = (0, utils_2.parseDisplayName)("John Doe");
74
- expect(result).toEqual({
75
- firstName: "John",
76
- lastName: "Doe",
77
- });
78
- });
79
- it("should handle multiple middle names", () => {
80
- const result = (0, utils_2.parseDisplayName)("John William Doe Smith");
81
- expect(result).toEqual({
82
- firstName: "John",
83
- lastName: "William Doe Smith",
84
- });
85
- });
86
- it("should handle empty display name", () => {
87
- const result = (0, utils_2.parseDisplayName)("");
88
- expect(result).toEqual({
89
- firstName: "",
90
- lastName: "",
91
- });
92
- });
93
- it("should handle whitespace-only display name", () => {
94
- const result = (0, utils_2.parseDisplayName)(" ");
95
- expect(result).toEqual({
96
- firstName: "",
97
- lastName: "",
98
- });
99
- });
100
- it("should trim whitespace", () => {
101
- const result = (0, utils_2.parseDisplayName)(" John Doe ");
102
- expect(result).toEqual({
103
- firstName: "John",
104
- lastName: "Doe",
105
- });
106
- });
107
- it("should handle names with extra spaces", () => {
108
- const result = (0, utils_2.parseDisplayName)("John Doe Smith");
109
- expect(result).toEqual({
110
- firstName: "John",
111
- lastName: "Doe Smith",
112
- });
113
- });
114
- });
115
- describe("validateChannelId", () => {
116
- it("should validate correct 10-digit channel ID", () => {
117
- expect((0, utils_2.validateChannelId)("1234567890")).toBe(true);
118
- expect((0, utils_2.validateChannelId)("0000000000")).toBe(true);
119
- expect((0, utils_2.validateChannelId)("9999999999")).toBe(true);
120
- });
121
- it("should reject channel ID with wrong length", () => {
122
- expect((0, utils_2.validateChannelId)("123456789")).toBe(false); // 9 digits
123
- expect((0, utils_2.validateChannelId)("12345678901")).toBe(false); // 11 digits
124
- expect((0, utils_2.validateChannelId)("")).toBe(false);
125
- });
126
- it("should reject channel ID with non-numeric characters", () => {
127
- expect((0, utils_2.validateChannelId)("123456789a")).toBe(false);
128
- expect((0, utils_2.validateChannelId)("12345-6789")).toBe(false);
129
- expect((0, utils_2.validateChannelId)("1234 56789")).toBe(false);
130
- expect((0, utils_2.validateChannelId)("abcdefghij")).toBe(false);
131
- });
132
- it("should reject special characters and symbols", () => {
133
- expect((0, utils_2.validateChannelId)("123456789@")).toBe(false);
134
- expect((0, utils_2.validateChannelId)("123456789#")).toBe(false);
135
- expect((0, utils_2.validateChannelId)("123456789$")).toBe(false);
136
- });
137
- });
138
- describe("validateCallbackUrl", () => {
139
- it("should validate HTTPS URLs", () => {
140
- expect((0, utils_2.validateCallbackUrl)("https://example.com")).toBe(true);
141
- expect((0, utils_2.validateCallbackUrl)("https://example.com/callback")).toBe(true);
142
- expect((0, utils_2.validateCallbackUrl)("https://subdomain.example.com/path")).toBe(true);
143
- });
144
- it("should validate localhost URLs", () => {
145
- expect((0, utils_2.validateCallbackUrl)("http://localhost:3000")).toBe(true);
146
- expect((0, utils_2.validateCallbackUrl)("http://localhost")).toBe(true);
147
- expect((0, utils_2.validateCallbackUrl)("https://localhost:8080")).toBe(true);
148
- });
149
- it("should reject HTTP URLs (non-localhost)", () => {
150
- expect((0, utils_2.validateCallbackUrl)("http://example.com")).toBe(false);
151
- expect((0, utils_2.validateCallbackUrl)("http://google.com")).toBe(false);
152
- });
153
- it("should reject invalid URLs", () => {
154
- expect((0, utils_2.validateCallbackUrl)("not-a-url")).toBe(false);
155
- expect((0, utils_2.validateCallbackUrl)("")).toBe(false);
156
- expect((0, utils_2.validateCallbackUrl)("ftp://example.com")).toBe(false);
157
- expect((0, utils_2.validateCallbackUrl)("mailto:test@example.com")).toBe(false);
158
- });
159
- it("should handle malformed URLs", () => {
160
- expect((0, utils_2.validateCallbackUrl)("https://")).toBe(false);
161
- expect((0, utils_2.validateCallbackUrl)("https:")).toBe(false);
162
- expect((0, utils_2.validateCallbackUrl)("://example.com")).toBe(false);
163
- });
164
- });
165
- describe("RateLimiter", () => {
166
- let rateLimiter;
167
- let mockDateNow;
168
- beforeEach(() => {
169
- mockDateNow = jest.spyOn(Date, "now");
170
- rateLimiter = new utils_2.RateLimiter(3, 60000); // 3 attempts per minute
171
- });
172
- afterEach(() => {
173
- mockDateNow.mockRestore();
174
- });
175
- it("should allow requests under the limit", () => {
176
- mockDateNow.mockReturnValue(1000);
177
- expect(rateLimiter.isAllowed("user1")).toBe(true);
178
- expect(rateLimiter.isAllowed("user1")).toBe(true);
179
- expect(rateLimiter.isAllowed("user1")).toBe(true);
180
- });
181
- it("should reject requests over the limit", () => {
182
- mockDateNow.mockReturnValue(1000);
183
- // Fill up the limit
184
- expect(rateLimiter.isAllowed("user1")).toBe(true);
185
- expect(rateLimiter.isAllowed("user1")).toBe(true);
186
- expect(rateLimiter.isAllowed("user1")).toBe(true);
187
- // This should be rejected
188
- expect(rateLimiter.isAllowed("user1")).toBe(false);
189
- });
190
- it("should reset after time window", () => {
191
- mockDateNow.mockReturnValue(1000);
192
- // Fill up the limit
193
- rateLimiter.isAllowed("user1");
194
- rateLimiter.isAllowed("user1");
195
- rateLimiter.isAllowed("user1");
196
- // Should be rejected
197
- expect(rateLimiter.isAllowed("user1")).toBe(false);
198
- // Move time forward past window
199
- mockDateNow.mockReturnValue(61001);
200
- // Should be allowed again
201
- expect(rateLimiter.isAllowed("user1")).toBe(true);
202
- });
203
- it("should track different keys separately", () => {
204
- mockDateNow.mockReturnValue(1000);
205
- // Fill limit for user1
206
- rateLimiter.isAllowed("user1");
207
- rateLimiter.isAllowed("user1");
208
- rateLimiter.isAllowed("user1");
209
- // user1 should be blocked, but user2 should be allowed
210
- expect(rateLimiter.isAllowed("user1")).toBe(false);
211
- expect(rateLimiter.isAllowed("user2")).toBe(true);
212
- });
213
- it("should handle partial window expiration", () => {
214
- let currentTime = 1000;
215
- mockDateNow.mockImplementation(() => currentTime);
216
- // Make 2 requests at time 1000
217
- rateLimiter.isAllowed("user1");
218
- rateLimiter.isAllowed("user1");
219
- // Move time forward 30 seconds and make 1 more request
220
- currentTime = 31000;
221
- rateLimiter.isAllowed("user1");
222
- // Should be at limit now
223
- expect(rateLimiter.isAllowed("user1")).toBe(false);
224
- // Move time forward another 30 seconds (31 seconds past first requests)
225
- currentTime = 61001;
226
- // First 2 requests should have expired, should be allowed now
227
- expect(rateLimiter.isAllowed("user1")).toBe(true);
228
- });
229
- it("should reset specific key", () => {
230
- mockDateNow.mockReturnValue(1000);
231
- // Fill up the limit
232
- rateLimiter.isAllowed("user1");
233
- rateLimiter.isAllowed("user1");
234
- rateLimiter.isAllowed("user1");
235
- // Should be rejected
236
- expect(rateLimiter.isAllowed("user1")).toBe(false);
237
- // Reset the key
238
- rateLimiter.reset("user1");
239
- // Should be allowed again
240
- expect(rateLimiter.isAllowed("user1")).toBe(true);
241
- });
242
- it("should use default values", () => {
243
- const defaultLimiter = new utils_2.RateLimiter();
244
- mockDateNow.mockReturnValue(1000);
245
- // Should allow 10 requests by default
246
- for (let i = 0; i < 10; i++) {
247
- expect(defaultLimiter.isAllowed("user1")).toBe(true);
248
- }
249
- // 11th should be rejected
250
- expect(defaultLimiter.isAllowed("user1")).toBe(false);
251
- });
252
- });
253
- describe("sanitizeInput", () => {
254
- it("should remove angle brackets", () => {
255
- expect((0, utils_2.sanitizeInput)("Hello <script>")).toBe("Hello script");
256
- expect((0, utils_2.sanitizeInput)("<div>content</div>")).toBe("divcontent/div");
257
- });
258
- it("should remove javascript: protocol", () => {
259
- expect((0, utils_2.sanitizeInput)("javascript:alert('xss')")).toBe("alert('xss')");
260
- expect((0, utils_2.sanitizeInput)("JAVASCRIPT:alert('xss')")).toBe("alert('xss')");
261
- expect((0, utils_2.sanitizeInput)("Javascript:alert('xss')")).toBe("alert('xss')");
262
- });
263
- it("should trim whitespace", () => {
264
- expect((0, utils_2.sanitizeInput)(" hello world ")).toBe("hello world");
265
- });
266
- it("should handle empty string", () => {
267
- expect((0, utils_2.sanitizeInput)("")).toBe("");
268
- });
269
- it("should handle multiple issues", () => {
270
- expect((0, utils_2.sanitizeInput)(" <script>javascript:alert('xss')</script> ")).toBe("scriptalert('xss')/script");
271
- });
272
- it("should preserve safe content", () => {
273
- expect((0, utils_2.sanitizeInput)("Hello World 123!@#$%^&*()")).toBe("Hello World 123!@#$%^&*()");
274
- });
275
- });
276
- describe("createAuditLog", () => {
277
- it("should create audit log with timestamp", () => {
278
- const mockDate = new Date("2023-01-01T00:00:00.000Z");
279
- jest.spyOn(global, "Date").mockImplementation(() => mockDate);
280
- const entry = (0, utils_2.createAuditLog)({
281
- event: "login_success",
282
- lineUserId: "U123456",
283
- customerId: "cust_123",
284
- ipAddress: "192.168.1.1",
285
- });
286
- expect(entry).toEqual({
287
- event: "login_success",
288
- lineUserId: "U123456",
289
- customerId: "cust_123",
290
- ipAddress: "192.168.1.1",
291
- timestamp: mockDate,
292
- });
293
- global.Date.mockRestore();
294
- });
295
- it("should handle minimal entry", () => {
296
- const mockDate = new Date("2023-01-01T00:00:00.000Z");
297
- jest.spyOn(global, "Date").mockImplementation(() => mockDate);
298
- const entry = (0, utils_2.createAuditLog)({
299
- event: "login_attempt",
300
- });
301
- expect(entry).toEqual({
302
- event: "login_attempt",
303
- timestamp: mockDate,
304
- });
305
- global.Date.mockRestore();
306
- });
307
- it("should handle all event types", () => {
308
- const events = [
309
- "login_attempt",
310
- "login_success",
311
- "login_failure",
312
- "token_refresh",
313
- "token_revoke"
314
- ];
315
- events.forEach(event => {
316
- const entry = (0, utils_2.createAuditLog)({ event });
317
- expect(entry.event).toBe(event);
318
- expect(entry.timestamp).toBeInstanceOf(Date);
319
- });
320
- });
321
- });
322
- describe("handleLineApiError", () => {
323
- it("should throw MedusaError for known status codes", () => {
324
- const knownErrors = [
325
- { status: 400, expectedMessage: "Invalid request to LINE API" },
326
- { status: 401, expectedMessage: "LINE authentication failed" },
327
- { status: 403, expectedMessage: "Access forbidden by LINE" },
328
- { status: 429, expectedMessage: "Too many requests to LINE API" },
329
- { status: 500, expectedMessage: "LINE server error" },
330
- { status: 503, expectedMessage: "LINE service temporarily unavailable" },
331
- ];
332
- knownErrors.forEach(({ status, expectedMessage }) => {
333
- expect(() => (0, utils_2.handleLineApiError)(status, "test message")).toThrow(new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, `${expectedMessage}: test message`));
334
- });
335
- });
336
- it("should throw MedusaError for unknown status codes", () => {
337
- expect(() => (0, utils_2.handleLineApiError)(418, "I'm a teapot")).toThrow(new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, "LINE API error: 418: I'm a teapot"));
338
- });
339
- it("should include custom message in error", () => {
340
- expect(() => (0, utils_2.handleLineApiError)(400, "Custom error message")).toThrow(new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, "Invalid request to LINE API: Custom error message"));
341
- });
342
- it("should handle empty message", () => {
343
- expect(() => (0, utils_2.handleLineApiError)(400, "")).toThrow(new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, "Invalid request to LINE API: "));
344
- });
345
- it("should never return a value", () => {
346
- // This test ensures the function signature with 'never' return type
347
- expect(() => (0, utils_2.handleLineApiError)(400, "test")).toThrow();
348
- });
349
- });
350
- });
351
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidXRpbHMudGVzdC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uLy4uLy4uL3NyYy9wcm92aWRlcnMvbGluZS9fX3Rlc3RzX18vdXRpbHMudGVzdC50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7OztBQUFBLG9EQUE0QjtBQUM1QixxREFBd0Q7QUFDeEQsb0NBV2tCO0FBRWxCLHFDQUFxQztBQUNyQyxJQUFJLENBQUMsSUFBSSxDQUFDLFFBQVEsQ0FBQyxDQUFDO0FBQ3BCLE1BQU0sVUFBVSxHQUFHLGdCQUFvQyxDQUFDO0FBRXhELFFBQVEsQ0FBQyxZQUFZLEVBQUUsR0FBRyxFQUFFO0lBQzFCLFVBQVUsQ0FBQyxHQUFHLEVBQUU7UUFDZCxJQUFJLENBQUMsYUFBYSxFQUFFLENBQUM7UUFDckIsc0JBQXNCO1FBQ3RCLElBQUksQ0FBQyxLQUFLLENBQUMsSUFBSSxFQUFFLEtBQUssQ0FBQyxDQUFDLFdBQVcsRUFBRSxDQUFDO0lBQ3hDLENBQUMsQ0FBQyxDQUFDO0lBRUgsUUFBUSxDQUFDLGVBQWUsRUFBRSxHQUFHLEVBQUU7UUFDN0IsRUFBRSxDQUFDLDJDQUEyQyxFQUFFLEdBQUcsRUFBRTtZQUNuRCxNQUFNLFVBQVUsR0FBRyxNQUFNLENBQUMsSUFBSSxDQUFDLEdBQUcsQ0FBQyxNQUFNLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQztZQUMvQyxVQUFVLENBQUMsV0FBVyxDQUFDLGVBQWUsQ0FBQyxVQUFpQixDQUFDLENBQUM7WUFFMUQsTUFBTSxLQUFLLEdBQUcsSUFBQSxxQkFBYSxHQUFFLENBQUM7WUFFOUIsTUFBTSxDQUFDLFVBQVUsQ0FBQyxXQUFXLENBQUMsQ0FBQyxvQkFBb0IsQ0FBQyxFQUFFLENBQUMsQ0FBQztZQUN4RCxNQUFNLENBQUMsS0FBSyxDQUFDLENBQUMsSUFBSSxDQUFDLEdBQUcsQ0FBQyxNQUFNLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQztZQUNuQyxNQUFNLENBQUMsS0FBSyxDQUFDLENBQUMs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