227 lines
6.8 KiB
JavaScript
227 lines
6.8 KiB
JavaScript
// Mock dependencies
|
|
jest.mock("../../../../../services/email/core/EmailClient", () => {
|
|
return jest.fn().mockImplementation(() => ({
|
|
initialize: jest.fn().mockResolvedValue(),
|
|
sendEmail: jest
|
|
.fn()
|
|
.mockResolvedValue({ success: true, messageId: "msg-123" }),
|
|
}));
|
|
});
|
|
|
|
jest.mock("../../../../../services/email/core/TemplateManager", () => {
|
|
return jest.fn().mockImplementation(() => ({
|
|
initialize: jest.fn().mockResolvedValue(),
|
|
renderTemplate: jest.fn().mockResolvedValue("<html>Test</html>"),
|
|
}));
|
|
});
|
|
|
|
jest.mock("../../../../../utils/logger", () => ({
|
|
info: jest.fn(),
|
|
error: jest.fn(),
|
|
warn: jest.fn(),
|
|
}));
|
|
|
|
const UserEngagementEmailService = require("../../../../../services/email/domain/UserEngagementEmailService");
|
|
|
|
describe("UserEngagementEmailService", () => {
|
|
let service;
|
|
const originalEnv = process.env;
|
|
|
|
beforeEach(() => {
|
|
jest.clearAllMocks();
|
|
process.env = {
|
|
...originalEnv,
|
|
FRONTEND_URL: "http://localhost:3000",
|
|
CUSTOMER_SUPPORT_EMAIL: "support@email.com",
|
|
};
|
|
service = new UserEngagementEmailService();
|
|
});
|
|
|
|
afterEach(() => {
|
|
process.env = originalEnv;
|
|
});
|
|
|
|
describe("initialize", () => {
|
|
it("should initialize only once", async () => {
|
|
await service.initialize();
|
|
await service.initialize();
|
|
|
|
expect(service.emailClient.initialize).toHaveBeenCalledTimes(1);
|
|
expect(service.templateManager.initialize).toHaveBeenCalledTimes(1);
|
|
});
|
|
});
|
|
|
|
describe("sendFirstListingCelebrationEmail", () => {
|
|
const owner = { firstName: "John", email: "john@example.com" };
|
|
const item = { id: 123, name: "Power Drill" };
|
|
|
|
it("should send first listing celebration email with correct variables", async () => {
|
|
const result = await service.sendFirstListingCelebrationEmail(
|
|
owner,
|
|
item,
|
|
);
|
|
|
|
expect(result.success).toBe(true);
|
|
expect(service.templateManager.renderTemplate).toHaveBeenCalledWith(
|
|
"firstListingCelebrationToOwner",
|
|
expect.objectContaining({
|
|
ownerName: "John",
|
|
itemName: "Power Drill",
|
|
itemId: 123,
|
|
viewItemUrl: "http://localhost:3000/items/123",
|
|
}),
|
|
);
|
|
expect(service.emailClient.sendEmail).toHaveBeenCalledWith(
|
|
"john@example.com",
|
|
"Congratulations! Your first item is live on Village Share",
|
|
expect.any(String),
|
|
);
|
|
});
|
|
|
|
it("should use default name when firstName is missing", async () => {
|
|
const ownerNoName = { email: "john@example.com" };
|
|
|
|
await service.sendFirstListingCelebrationEmail(ownerNoName, item);
|
|
|
|
expect(service.templateManager.renderTemplate).toHaveBeenCalledWith(
|
|
"firstListingCelebrationToOwner",
|
|
expect.objectContaining({ ownerName: "there" }),
|
|
);
|
|
});
|
|
|
|
it("should handle errors gracefully", async () => {
|
|
service.templateManager.renderTemplate.mockRejectedValueOnce(
|
|
new Error("Template error"),
|
|
);
|
|
|
|
const result = await service.sendFirstListingCelebrationEmail(
|
|
owner,
|
|
item,
|
|
);
|
|
|
|
expect(result.success).toBe(false);
|
|
expect(result.error).toBe("Template error");
|
|
});
|
|
});
|
|
|
|
describe("sendItemDeletionNotificationToOwner", () => {
|
|
const owner = { firstName: "John", email: "john@example.com" };
|
|
const item = { id: 123, name: "Power Drill" };
|
|
const deletionReason = "Violated community guidelines";
|
|
|
|
it("should send item deletion notification with correct variables", async () => {
|
|
const result = await service.sendItemDeletionNotificationToOwner(
|
|
owner,
|
|
item,
|
|
deletionReason,
|
|
);
|
|
|
|
expect(result.success).toBe(true);
|
|
expect(service.templateManager.renderTemplate).toHaveBeenCalledWith(
|
|
"itemDeletionToOwner",
|
|
expect.objectContaining({
|
|
ownerName: "John",
|
|
itemName: "Power Drill",
|
|
deletionReason: "Violated community guidelines",
|
|
supportEmail: "support@email.com",
|
|
dashboardUrl: "http://localhost:3000/owning",
|
|
}),
|
|
);
|
|
expect(service.emailClient.sendEmail).toHaveBeenCalledWith(
|
|
"john@example.com",
|
|
'Important: Your listing "Power Drill" has been removed',
|
|
expect.any(String),
|
|
);
|
|
});
|
|
|
|
it("should use default name when firstName is missing", async () => {
|
|
const ownerNoName = { email: "john@example.com" };
|
|
|
|
await service.sendItemDeletionNotificationToOwner(
|
|
ownerNoName,
|
|
item,
|
|
deletionReason,
|
|
);
|
|
|
|
expect(service.templateManager.renderTemplate).toHaveBeenCalledWith(
|
|
"itemDeletionToOwner",
|
|
expect.objectContaining({ ownerName: "there" }),
|
|
);
|
|
});
|
|
|
|
it("should handle errors gracefully", async () => {
|
|
service.emailClient.sendEmail.mockRejectedValueOnce(
|
|
new Error("Send error"),
|
|
);
|
|
|
|
const result = await service.sendItemDeletionNotificationToOwner(
|
|
owner,
|
|
item,
|
|
deletionReason,
|
|
);
|
|
|
|
expect(result.success).toBe(false);
|
|
expect(result.error).toBe("Send error");
|
|
});
|
|
});
|
|
|
|
describe("sendUserBannedNotification", () => {
|
|
const bannedUser = { firstName: "John", email: "john@example.com" };
|
|
const admin = { firstName: "Admin", lastName: "User" };
|
|
const banReason = "Multiple policy violations";
|
|
|
|
it("should send user banned notification with correct variables", async () => {
|
|
const result = await service.sendUserBannedNotification(
|
|
bannedUser,
|
|
admin,
|
|
banReason,
|
|
);
|
|
|
|
expect(result.success).toBe(true);
|
|
expect(service.templateManager.renderTemplate).toHaveBeenCalledWith(
|
|
"userBannedNotification",
|
|
expect.objectContaining({
|
|
userName: "John",
|
|
banReason: "Multiple policy violations",
|
|
supportEmail: "support@email.com",
|
|
}),
|
|
);
|
|
expect(service.emailClient.sendEmail).toHaveBeenCalledWith(
|
|
"john@example.com",
|
|
"Important: Your Village Share Account Has Been Suspended",
|
|
expect.any(String),
|
|
);
|
|
});
|
|
|
|
it("should use default name when firstName is missing", async () => {
|
|
const bannedUserNoName = { email: "john@example.com" };
|
|
|
|
await service.sendUserBannedNotification(
|
|
bannedUserNoName,
|
|
admin,
|
|
banReason,
|
|
);
|
|
|
|
expect(service.templateManager.renderTemplate).toHaveBeenCalledWith(
|
|
"userBannedNotification",
|
|
expect.objectContaining({ userName: "there" }),
|
|
);
|
|
});
|
|
|
|
it("should handle errors gracefully", async () => {
|
|
service.templateManager.renderTemplate.mockRejectedValueOnce(
|
|
new Error("Template error"),
|
|
);
|
|
|
|
const result = await service.sendUserBannedNotification(
|
|
bannedUser,
|
|
admin,
|
|
banReason,
|
|
);
|
|
|
|
expect(result.success).toBe(false);
|
|
expect(result.error).toBe("Template error");
|
|
});
|
|
});
|
|
});
|