strapi-plugin-magic-mail 2.3.0 → 2.3.1
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.
- package/dist/server/index.js +23 -16
- package/dist/server/index.mjs +23 -16
- package/package.json +1 -1
package/dist/server/index.js
CHANGED
|
@@ -606,7 +606,7 @@ function requireAccounts() {
|
|
|
606
606
|
if (!testEmail) {
|
|
607
607
|
ctx.throw(400, "testEmail is required");
|
|
608
608
|
}
|
|
609
|
-
strapi.log.info("[magic-mail]
|
|
609
|
+
strapi.log.info("[magic-mail] [TEST] Testing Strapi Email Service integration...");
|
|
610
610
|
strapi.log.info('[magic-mail] [EMAIL] Calling strapi.plugin("email").service("email").send()');
|
|
611
611
|
if (accountName) {
|
|
612
612
|
strapi.log.info(`[magic-mail] [FORCE] Forcing specific account: ${accountName}`);
|
|
@@ -2322,7 +2322,7 @@ function requireTest() {
|
|
|
2322
2322
|
async testRelations(ctx) {
|
|
2323
2323
|
try {
|
|
2324
2324
|
console.log("\n" + "=".repeat(60));
|
|
2325
|
-
console.log("
|
|
2325
|
+
console.log("[TEST] Template - Version Relations (Document Service API)");
|
|
2326
2326
|
console.log("=".repeat(60));
|
|
2327
2327
|
let test1Success = false;
|
|
2328
2328
|
let test1ReverseSuccess = false;
|
|
@@ -2490,7 +2490,7 @@ function requireTest() {
|
|
|
2490
2490
|
} else {
|
|
2491
2491
|
console.log(` [ERROR] FEHLER: Falsche Anzahl Versionen!`);
|
|
2492
2492
|
}
|
|
2493
|
-
console.log("\n
|
|
2493
|
+
console.log("\n[CLEANUP] Cleanup Test 3...");
|
|
2494
2494
|
if (afterSecondUpdate.versions) {
|
|
2495
2495
|
for (const version3 of afterSecondUpdate.versions) {
|
|
2496
2496
|
await strapi.documents(EMAIL_TEMPLATE_VERSION_UID).delete({ documentId: version3.documentId });
|
|
@@ -2508,7 +2508,7 @@ function requireTest() {
|
|
|
2508
2508
|
console.log(`
|
|
2509
2509
|
[INFO] Template: "${finalTemplate.name}" (documentId: ${finalTemplate.documentId})`);
|
|
2510
2510
|
console.log(` Anzahl Versionen: ${finalTemplate.versions?.length || 0}`);
|
|
2511
|
-
console.log("\n
|
|
2511
|
+
console.log("\n[CLEANUP] Aufraumen...");
|
|
2512
2512
|
await strapi.documents(EMAIL_TEMPLATE_VERSION_UID).delete({ documentId: version1.documentId });
|
|
2513
2513
|
await strapi.documents(EMAIL_TEMPLATE_VERSION_UID).delete({ documentId: version2.documentId });
|
|
2514
2514
|
await strapi.documents(EMAIL_TEMPLATE_UID).delete({ documentId: testTemplate.documentId });
|
|
@@ -3491,7 +3491,7 @@ function requireEncryption() {
|
|
|
3491
3491
|
let encrypted = cipher.update(jsonData, "utf8", "hex");
|
|
3492
3492
|
encrypted += cipher.final("hex");
|
|
3493
3493
|
const authTag = cipher.getAuthTag();
|
|
3494
|
-
return `${iv.toString("hex")}:${authTag.toString("hex")}:${encrypted}
|
|
3494
|
+
return { encrypted: `${iv.toString("hex")}:${authTag.toString("hex")}:${encrypted}` };
|
|
3495
3495
|
} catch (err) {
|
|
3496
3496
|
console.error("[magic-mail] Encryption failed:", err);
|
|
3497
3497
|
throw new Error("Failed to encrypt credentials");
|
|
@@ -3501,7 +3501,8 @@ function requireEncryption() {
|
|
|
3501
3501
|
if (!encryptedData) return null;
|
|
3502
3502
|
try {
|
|
3503
3503
|
const key = getEncryptionKey();
|
|
3504
|
-
const
|
|
3504
|
+
const encryptedString = typeof encryptedData === "object" && encryptedData.encrypted ? encryptedData.encrypted : encryptedData;
|
|
3505
|
+
const parts = encryptedString.split(":");
|
|
3505
3506
|
if (parts.length !== 3) {
|
|
3506
3507
|
throw new Error("Invalid encrypted data format");
|
|
3507
3508
|
}
|
|
@@ -3575,7 +3576,7 @@ function requireEmailRouter() {
|
|
|
3575
3576
|
let templateRecord = null;
|
|
3576
3577
|
if (emailData.templateReferenceId) {
|
|
3577
3578
|
resolvedTemplateReferenceId = String(emailData.templateReferenceId).trim();
|
|
3578
|
-
strapi2.log.info(`[magic-mail]
|
|
3579
|
+
strapi2.log.info(`[magic-mail] [TEMPLATE] Using provided templateReferenceId="${resolvedTemplateReferenceId}"`);
|
|
3579
3580
|
}
|
|
3580
3581
|
if (!resolvedTemplateReferenceId && templateId) {
|
|
3581
3582
|
const numericTemplateId = Number(templateId);
|
|
@@ -3595,7 +3596,7 @@ function requireEmailRouter() {
|
|
|
3595
3596
|
);
|
|
3596
3597
|
} else {
|
|
3597
3598
|
resolvedTemplateReferenceId = String(templateId).trim();
|
|
3598
|
-
strapi2.log.info(`[magic-mail]
|
|
3599
|
+
strapi2.log.info(`[magic-mail] [TEMPLATE] Treating templateId value as referenceId="${resolvedTemplateReferenceId}"`);
|
|
3599
3600
|
}
|
|
3600
3601
|
}
|
|
3601
3602
|
if (!resolvedTemplateReferenceId) {
|
|
@@ -3708,7 +3709,7 @@ function requireEmailRouter() {
|
|
|
3708
3709
|
}
|
|
3709
3710
|
const canSend = await this.checkRateLimits(account);
|
|
3710
3711
|
if (!canSend) {
|
|
3711
|
-
const fallbackAccount = await this.selectAccount(type, priority, [account.
|
|
3712
|
+
const fallbackAccount = await this.selectAccount(type, priority, [account.documentId], emailData);
|
|
3712
3713
|
if (fallbackAccount) {
|
|
3713
3714
|
strapi2.log.info(`[magic-mail] Rate limit hit on ${account.name}, using fallback: ${fallbackAccount.name}`);
|
|
3714
3715
|
return await this.sendViaAccount(fallbackAccount, emailData);
|
|
@@ -3776,13 +3777,19 @@ ${text || "Email delivery failed. Please check your email settings."}`;
|
|
|
3776
3777
|
},
|
|
3777
3778
|
/**
|
|
3778
3779
|
* Select best account based on rules
|
|
3780
|
+
* @param {string} type - Email type (transactional, marketing, notification)
|
|
3781
|
+
* @param {string} priority - Priority level (high, normal, low)
|
|
3782
|
+
* @param {Array<string>} excludeDocumentIds - Array of documentIds to exclude from selection
|
|
3783
|
+
* @param {Object} emailData - Email data for routing rule matching
|
|
3784
|
+
* @returns {Promise<Object|null>} Selected account or null
|
|
3779
3785
|
*/
|
|
3780
|
-
async selectAccount(type, priority,
|
|
3786
|
+
async selectAccount(type, priority, excludeDocumentIds = [], emailData = {}) {
|
|
3787
|
+
const filters = { isActive: true };
|
|
3788
|
+
if (excludeDocumentIds.length > 0) {
|
|
3789
|
+
filters.documentId = { $notIn: excludeDocumentIds };
|
|
3790
|
+
}
|
|
3781
3791
|
const accounts2 = await strapi2.documents("plugin::magic-mail.email-account").findMany({
|
|
3782
|
-
filters
|
|
3783
|
-
isActive: true,
|
|
3784
|
-
id: { $notIn: excludeIds }
|
|
3785
|
-
},
|
|
3792
|
+
filters,
|
|
3786
3793
|
sort: [{ priority: "desc" }]
|
|
3787
3794
|
});
|
|
3788
3795
|
if (!accounts2 || accounts2.length === 0) {
|
|
@@ -5537,7 +5544,7 @@ function requireOauth() {
|
|
|
5537
5544
|
});
|
|
5538
5545
|
return oauth;
|
|
5539
5546
|
}
|
|
5540
|
-
const version = "2.
|
|
5547
|
+
const version = "2.3.0";
|
|
5541
5548
|
const require$$2 = {
|
|
5542
5549
|
version
|
|
5543
5550
|
};
|
|
@@ -6705,7 +6712,7 @@ function requireAnalytics() {
|
|
|
6705
6712
|
const randomToken = crypto.randomBytes(8).toString("hex");
|
|
6706
6713
|
const trackingUrl = `${baseUrl}/api/magic-mail/track/open/${emailId}/${recipientHash}?r=${randomToken}`;
|
|
6707
6714
|
const trackingPixel = `<img src="${trackingUrl}" width="1" height="1" style="display:none;" alt="" />`;
|
|
6708
|
-
strapi2.log.info(`[magic-mail]
|
|
6715
|
+
strapi2.log.info(`[magic-mail] [PIXEL] Tracking pixel URL: ${trackingUrl}`);
|
|
6709
6716
|
if (html.includes("</body>")) {
|
|
6710
6717
|
return html.replace("</body>", `${trackingPixel}</body>`);
|
|
6711
6718
|
}
|
package/dist/server/index.mjs
CHANGED
|
@@ -596,7 +596,7 @@ function requireAccounts() {
|
|
|
596
596
|
if (!testEmail) {
|
|
597
597
|
ctx.throw(400, "testEmail is required");
|
|
598
598
|
}
|
|
599
|
-
strapi.log.info("[magic-mail]
|
|
599
|
+
strapi.log.info("[magic-mail] [TEST] Testing Strapi Email Service integration...");
|
|
600
600
|
strapi.log.info('[magic-mail] [EMAIL] Calling strapi.plugin("email").service("email").send()');
|
|
601
601
|
if (accountName) {
|
|
602
602
|
strapi.log.info(`[magic-mail] [FORCE] Forcing specific account: ${accountName}`);
|
|
@@ -2312,7 +2312,7 @@ function requireTest() {
|
|
|
2312
2312
|
async testRelations(ctx) {
|
|
2313
2313
|
try {
|
|
2314
2314
|
console.log("\n" + "=".repeat(60));
|
|
2315
|
-
console.log("
|
|
2315
|
+
console.log("[TEST] Template - Version Relations (Document Service API)");
|
|
2316
2316
|
console.log("=".repeat(60));
|
|
2317
2317
|
let test1Success = false;
|
|
2318
2318
|
let test1ReverseSuccess = false;
|
|
@@ -2480,7 +2480,7 @@ function requireTest() {
|
|
|
2480
2480
|
} else {
|
|
2481
2481
|
console.log(` [ERROR] FEHLER: Falsche Anzahl Versionen!`);
|
|
2482
2482
|
}
|
|
2483
|
-
console.log("\n
|
|
2483
|
+
console.log("\n[CLEANUP] Cleanup Test 3...");
|
|
2484
2484
|
if (afterSecondUpdate.versions) {
|
|
2485
2485
|
for (const version3 of afterSecondUpdate.versions) {
|
|
2486
2486
|
await strapi.documents(EMAIL_TEMPLATE_VERSION_UID).delete({ documentId: version3.documentId });
|
|
@@ -2498,7 +2498,7 @@ function requireTest() {
|
|
|
2498
2498
|
console.log(`
|
|
2499
2499
|
[INFO] Template: "${finalTemplate.name}" (documentId: ${finalTemplate.documentId})`);
|
|
2500
2500
|
console.log(` Anzahl Versionen: ${finalTemplate.versions?.length || 0}`);
|
|
2501
|
-
console.log("\n
|
|
2501
|
+
console.log("\n[CLEANUP] Aufraumen...");
|
|
2502
2502
|
await strapi.documents(EMAIL_TEMPLATE_VERSION_UID).delete({ documentId: version1.documentId });
|
|
2503
2503
|
await strapi.documents(EMAIL_TEMPLATE_VERSION_UID).delete({ documentId: version2.documentId });
|
|
2504
2504
|
await strapi.documents(EMAIL_TEMPLATE_UID).delete({ documentId: testTemplate.documentId });
|
|
@@ -3481,7 +3481,7 @@ function requireEncryption() {
|
|
|
3481
3481
|
let encrypted = cipher.update(jsonData, "utf8", "hex");
|
|
3482
3482
|
encrypted += cipher.final("hex");
|
|
3483
3483
|
const authTag = cipher.getAuthTag();
|
|
3484
|
-
return `${iv.toString("hex")}:${authTag.toString("hex")}:${encrypted}
|
|
3484
|
+
return { encrypted: `${iv.toString("hex")}:${authTag.toString("hex")}:${encrypted}` };
|
|
3485
3485
|
} catch (err) {
|
|
3486
3486
|
console.error("[magic-mail] Encryption failed:", err);
|
|
3487
3487
|
throw new Error("Failed to encrypt credentials");
|
|
@@ -3491,7 +3491,8 @@ function requireEncryption() {
|
|
|
3491
3491
|
if (!encryptedData) return null;
|
|
3492
3492
|
try {
|
|
3493
3493
|
const key = getEncryptionKey();
|
|
3494
|
-
const
|
|
3494
|
+
const encryptedString = typeof encryptedData === "object" && encryptedData.encrypted ? encryptedData.encrypted : encryptedData;
|
|
3495
|
+
const parts = encryptedString.split(":");
|
|
3495
3496
|
if (parts.length !== 3) {
|
|
3496
3497
|
throw new Error("Invalid encrypted data format");
|
|
3497
3498
|
}
|
|
@@ -3565,7 +3566,7 @@ function requireEmailRouter() {
|
|
|
3565
3566
|
let templateRecord = null;
|
|
3566
3567
|
if (emailData.templateReferenceId) {
|
|
3567
3568
|
resolvedTemplateReferenceId = String(emailData.templateReferenceId).trim();
|
|
3568
|
-
strapi2.log.info(`[magic-mail]
|
|
3569
|
+
strapi2.log.info(`[magic-mail] [TEMPLATE] Using provided templateReferenceId="${resolvedTemplateReferenceId}"`);
|
|
3569
3570
|
}
|
|
3570
3571
|
if (!resolvedTemplateReferenceId && templateId) {
|
|
3571
3572
|
const numericTemplateId = Number(templateId);
|
|
@@ -3585,7 +3586,7 @@ function requireEmailRouter() {
|
|
|
3585
3586
|
);
|
|
3586
3587
|
} else {
|
|
3587
3588
|
resolvedTemplateReferenceId = String(templateId).trim();
|
|
3588
|
-
strapi2.log.info(`[magic-mail]
|
|
3589
|
+
strapi2.log.info(`[magic-mail] [TEMPLATE] Treating templateId value as referenceId="${resolvedTemplateReferenceId}"`);
|
|
3589
3590
|
}
|
|
3590
3591
|
}
|
|
3591
3592
|
if (!resolvedTemplateReferenceId) {
|
|
@@ -3698,7 +3699,7 @@ function requireEmailRouter() {
|
|
|
3698
3699
|
}
|
|
3699
3700
|
const canSend = await this.checkRateLimits(account);
|
|
3700
3701
|
if (!canSend) {
|
|
3701
|
-
const fallbackAccount = await this.selectAccount(type, priority, [account.
|
|
3702
|
+
const fallbackAccount = await this.selectAccount(type, priority, [account.documentId], emailData);
|
|
3702
3703
|
if (fallbackAccount) {
|
|
3703
3704
|
strapi2.log.info(`[magic-mail] Rate limit hit on ${account.name}, using fallback: ${fallbackAccount.name}`);
|
|
3704
3705
|
return await this.sendViaAccount(fallbackAccount, emailData);
|
|
@@ -3766,13 +3767,19 @@ ${text || "Email delivery failed. Please check your email settings."}`;
|
|
|
3766
3767
|
},
|
|
3767
3768
|
/**
|
|
3768
3769
|
* Select best account based on rules
|
|
3770
|
+
* @param {string} type - Email type (transactional, marketing, notification)
|
|
3771
|
+
* @param {string} priority - Priority level (high, normal, low)
|
|
3772
|
+
* @param {Array<string>} excludeDocumentIds - Array of documentIds to exclude from selection
|
|
3773
|
+
* @param {Object} emailData - Email data for routing rule matching
|
|
3774
|
+
* @returns {Promise<Object|null>} Selected account or null
|
|
3769
3775
|
*/
|
|
3770
|
-
async selectAccount(type, priority,
|
|
3776
|
+
async selectAccount(type, priority, excludeDocumentIds = [], emailData = {}) {
|
|
3777
|
+
const filters = { isActive: true };
|
|
3778
|
+
if (excludeDocumentIds.length > 0) {
|
|
3779
|
+
filters.documentId = { $notIn: excludeDocumentIds };
|
|
3780
|
+
}
|
|
3771
3781
|
const accounts2 = await strapi2.documents("plugin::magic-mail.email-account").findMany({
|
|
3772
|
-
filters
|
|
3773
|
-
isActive: true,
|
|
3774
|
-
id: { $notIn: excludeIds }
|
|
3775
|
-
},
|
|
3782
|
+
filters,
|
|
3776
3783
|
sort: [{ priority: "desc" }]
|
|
3777
3784
|
});
|
|
3778
3785
|
if (!accounts2 || accounts2.length === 0) {
|
|
@@ -5527,7 +5534,7 @@ function requireOauth() {
|
|
|
5527
5534
|
});
|
|
5528
5535
|
return oauth;
|
|
5529
5536
|
}
|
|
5530
|
-
const version = "2.
|
|
5537
|
+
const version = "2.3.0";
|
|
5531
5538
|
const require$$2 = {
|
|
5532
5539
|
version
|
|
5533
5540
|
};
|
|
@@ -6695,7 +6702,7 @@ function requireAnalytics() {
|
|
|
6695
6702
|
const randomToken = crypto.randomBytes(8).toString("hex");
|
|
6696
6703
|
const trackingUrl = `${baseUrl}/api/magic-mail/track/open/${emailId}/${recipientHash}?r=${randomToken}`;
|
|
6697
6704
|
const trackingPixel = `<img src="${trackingUrl}" width="1" height="1" style="display:none;" alt="" />`;
|
|
6698
|
-
strapi2.log.info(`[magic-mail]
|
|
6705
|
+
strapi2.log.info(`[magic-mail] [PIXEL] Tracking pixel URL: ${trackingUrl}`);
|
|
6699
6706
|
if (html.includes("</body>")) {
|
|
6700
6707
|
return html.replace("</body>", `${trackingPixel}</body>`);
|
|
6701
6708
|
}
|
package/package.json
CHANGED