Skip to content

Commit b24d1f5

Browse files
authored
Updated LoggerEmailSender to include all Database.Error fields (#591)
* Resolved #590 by updating the Apex class LoggerEmailSender to include all Database.Error fields in the generated emails
1 parent 53af967 commit b24d1f5

6 files changed

Lines changed: 48 additions & 21 deletions

File tree

README.md

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,13 +7,13 @@ The most robust logger for Salesforce. Works with Apex, Lightning Components, Fl
77

88
## Unlocked Package - v4.12.0
99

10-
[![Install Unlocked Package in a Sandbox](./images/btn-install-unlocked-package-sandbox.png)](https://test.salesforce.com/packaging/installPackage.apexp?p0=04t5Y000001Mk1wQAC)
11-
[![Install Unlocked Package in Production](./images/btn-install-unlocked-package-production.png)](https://login.salesforce.com/packaging/installPackage.apexp?p0=04t5Y000001Mk1wQAC)
10+
[![Install Unlocked Package in a Sandbox](./images/btn-install-unlocked-package-sandbox.png)](https://test.salesforce.com/packaging/installPackage.apexp?p0=04t5Y000001Mk4bQAC)
11+
[![Install Unlocked Package in Production](./images/btn-install-unlocked-package-production.png)](https://login.salesforce.com/packaging/installPackage.apexp?p0=04t5Y000001Mk4bQAC)
1212
[![View Documentation](./images/btn-view-documentation.png)](https://jongpie.github.io/NebulaLogger/)
1313

14-
`sf package install --wait 20 --security-type AdminsOnly --package 04t5Y000001Mk1wQAC`
14+
`sf package install --wait 20 --security-type AdminsOnly --package 04t5Y000001Mk4bQAC`
1515

16-
`sfdx force:package:install --wait 20 --securitytype AdminsOnly --package 04t5Y000001Mk1wQAC`
16+
`sfdx force:package:install --wait 20 --securitytype AdminsOnly --package 04t5Y000001Mk4bQAC`
1717

1818
---
1919

nebula-logger/core/main/log-management/classes/LoggerEmailSender.cls

Lines changed: 19 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -108,12 +108,28 @@ public without sharing class LoggerEmailSender {
108108
sendEmail(messages);
109109
}
110110

111+
private static String getErrorMessageFromDatabaseError(Database.Error error) {
112+
List<String> messageParts = new List<String>();
113+
114+
// Add the status code
115+
messageParts.add('StatusCode: ' + error.getStatusCode());
116+
// Add the message
117+
messageParts.add('Message: ' + error.getMessage());
118+
// Add the fields if available
119+
List<String> fields = error.getFields();
120+
if (fields?.isEmpty() == false) {
121+
messageParts.add('Field(s): [' + String.join(fields, ', ') + ']');
122+
}
123+
124+
return String.join(messageParts, ', ');
125+
}
126+
111127
private static List<String> getErrorMessages(List<Database.SaveResult> saveResults) {
112128
List<String> errorMessages = new List<String>();
113129
for (Database.SaveResult result : saveResults) {
114130
if (result.isSuccess() == false) {
115131
for (Database.Error error : result.getErrors()) {
116-
errorMessages.add(error.getMessage());
132+
errorMessages.add(getErrorMessageFromDatabaseError(error));
117133
}
118134
}
119135
}
@@ -125,7 +141,7 @@ public without sharing class LoggerEmailSender {
125141
for (Database.UpsertResult result : upsertResults) {
126142
if (result.isSuccess() == false) {
127143
for (Database.Error error : result.getErrors()) {
128-
errorMessages.add(error.getMessage());
144+
errorMessages.add(getErrorMessageFromDatabaseError(error));
129145
}
130146
}
131147
}
@@ -161,7 +177,7 @@ public without sharing class LoggerEmailSender {
161177
}
162178

163179
private static String buildHtmlBody(Schema.SObjectType sobjectType, List<String> errorMessages) {
164-
final String emailBodyTemplate = 'Logger failed to save {0} {1} records for {2} (User ID: {3})<br /><br />Error Messages:<ul>{4}</ul>';
180+
final String emailBodyTemplate = 'Logger failed to save {0} {1} records for {2} (User ID: {3})<br /><br />Errors:<ul>{4}</ul>';
165181
final String formattedErrorMessages = '<li>' + String.join(errorMessages, '</li><li>') + '</li>';
166182
List<Object> emailBodyInputs = new List<Object>{
167183
errorMessages.size(),

nebula-logger/core/tests/configuration/utilities/LoggerMockDataCreator.cls

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -143,7 +143,7 @@ public class LoggerMockDataCreator {
143143
return (Database.SaveResult) JSON.deserialize('{"success": true, "id": "' + recordId + '"}', Database.SaveResult.class);
144144
} else {
145145
return (Database.SaveResult) JSON.deserialize(
146-
'{"success":false,"errors":[{"message": "Could not save...", "statusCode": "FIELD_CUSTOM_VALIDATION_EXCEPTION"}]}',
146+
'{"success":false,"errors":[{"message": "Could not save...", "statusCode": "FIELD_CUSTOM_VALIDATION_EXCEPTION", "fields": ["Name"]}]}',
147147
Database.SaveResult.class
148148
);
149149
}
@@ -172,7 +172,7 @@ public class LoggerMockDataCreator {
172172
return (Database.UndeleteResult) JSON.deserialize('{"success": true, "id": "' + recordId + '"}', Database.UndeleteResult.class);
173173
} else {
174174
return (Database.UndeleteResult) JSON.deserialize(
175-
'{"success":false,"errors":[{"message": "Could not undelete...", "statusCode": "FIELD_CUSTOM_VALIDATION_EXCEPTION"}]}',
175+
'{"success":false,"errors":[{"message": "Could not undelete...", "statusCode": "FIELD_CUSTOM_VALIDATION_EXCEPTION", "fields": ["Name"]}]}',
176176
Database.UndeleteResult.class
177177
);
178178
}
@@ -208,7 +208,7 @@ public class LoggerMockDataCreator {
208208
return (Database.UpsertResult) JSON.deserialize(
209209
'{"success":false, "created":' +
210210
isCreated +
211-
', "errors":[{"message": "Could not upsert...", "statusCode": "FIELD_CUSTOM_VALIDATION_EXCEPTION"}]}',
211+
', "errors":[{"message": "Could not upsert...", "statusCode": "FIELD_CUSTOM_VALIDATION_EXCEPTION", "fields": ["Name"]}]}',
212212
Database.UpsertResult.class
213213
);
214214
}

nebula-logger/core/tests/log-management/classes/LoggerEmailSender_Tests.cls

Lines changed: 14 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -54,11 +54,16 @@ private class LoggerEmailSender_Tests {
5454
Database.SaveResult saveResultWithError = LoggerMockDataCreator.createDatabaseSaveResult(false);
5555
LoggerEmailSender.sendErrorEmail(Schema.LogEntry__c.SObjectType, new List<Database.SaveResult>{ saveResultWithError });
5656

57-
System.Assert.areEqual(
58-
true,
57+
System.Assert.isTrue(
5958
LoggerEmailSender.SENT_EMAILS.get(0).getHtmlBody().contains(saveResultWithError.errors.get(0).getMessage()),
6059
'Email message should contain SaveResult error message'
6160
);
61+
List<String> errorFields = saveResultWithError.getErrors().get(0).getFields();
62+
String expectedFieldsError = 'Field(s): [' + String.join(errorFields, ', ') + ']';
63+
System.Assert.isTrue(
64+
LoggerEmailSender.SENT_EMAILS.get(0).getHtmlBody().contains(expectedFieldsError),
65+
'Email message should contain SaveResult error fields: ' + expectedFieldsError
66+
);
6267
if (LoggerEmailSender.IS_EMAIL_DELIVERABILITY_AVAILABLE) {
6368
System.Assert.areEqual(1, System.Limits.getEmailInvocations(), 'Email should have been sent');
6469
} else {
@@ -104,11 +109,16 @@ private class LoggerEmailSender_Tests {
104109
Database.UpsertResult upsertResultWithError = LoggerMockDataCreator.createDatabaseUpsertResult(false, false);
105110
LoggerEmailSender.sendErrorEmail(Schema.LogEntry__c.SObjectType, new List<Database.UpsertResult>{ upsertResultWithError });
106111

107-
System.Assert.areEqual(
108-
true,
112+
System.Assert.isTrue(
109113
LoggerEmailSender.SENT_EMAILS.get(0).getHtmlBody().contains(upsertResultWithError.errors.get(0).getMessage()),
110114
'Email message should contain UpsertResult error message'
111115
);
116+
List<String> errorFields = upsertResultWithError.getErrors().get(0).getFields();
117+
String expectedFieldsError = 'Field(s): [' + String.join(errorFields, ', ') + ']';
118+
System.Assert.isTrue(
119+
LoggerEmailSender.SENT_EMAILS.get(0).getHtmlBody().contains(expectedFieldsError),
120+
'Email message should contain UpsertResult error fields: ' + expectedFieldsError
121+
);
112122
if (LoggerEmailSender.IS_EMAIL_DELIVERABILITY_AVAILABLE) {
113123
System.Assert.areEqual(1, System.Limits.getEmailInvocations(), 'Email should have been sent');
114124
} else {

nebula-logger/managed-package/sfdx-project.json

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -10,10 +10,10 @@
1010
"definitionFile": "./config/scratch-orgs/base-scratch-def.json",
1111
"postInstallScript": "LoggerInstallHandler",
1212
"ancestorVersion": "HIGHEST",
13-
"versionNumber": "4.12.0.NEXT",
14-
"versionName": "Winter '24 Release",
15-
"versionDescription": "View the v4.12.0 milestone in GitHub for the list of changes - https://github.com/jongpie/NebulaLogger/milestone/12?closed=1",
16-
"releaseNotesUrl": "https://github.com/jongpie/NebulaLogger/releases/tag/v4.11.0"
13+
"versionNumber": "4.13.0.NEXT",
14+
"versionName": "Spring '24 Release",
15+
"versionDescription": "View the v4.13.0 milestone in GitHub for the list of changes - https://github.com/jongpie/NebulaLogger/milestone/13?closed=1",
16+
"releaseNotesUrl": "https://github.com/jongpie/NebulaLogger/releases/tag/v4.13.0"
1717
}
1818
],
1919
"packageAliases": {

sfdx-project.json

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,9 @@
1313
"package": "Nebula Logger - Core",
1414
"path": "./nebula-logger/core",
1515
"definitionFile": "./config/scratch-orgs/base-scratch-def.json",
16-
"versionNumber": "4.12.0.NEXT",
17-
"versionName": "Winter '24 Release",
18-
"versionDescription": "Updated all metadata to API v59.0, fixed a bug with logging Map<Id, SObject>, added new formula fields on Log__c & LogEntry__c for scenario names, added more metadata to the managed package",
16+
"versionNumber": "4.12.1.NEXT",
17+
"versionName": "Improved Error Emails",
18+
"versionDescription": "Updated error emails (sent by LoggerEmailSender) to include all Database.Error fields",
1919
"releaseNotesUrl": "https://github.com/jongpie/NebulaLogger/releases",
2020
"unpackagedMetadata": {
2121
"path": "./nebula-logger/extra-tests"
@@ -161,6 +161,7 @@
161161
"Nebula Logger - Core@4.11.11-reduced-usage-of-email-limits-consumption-in-loggeremailsender": "04t5Y000001Oih7QAC",
162162
"Nebula Logger - Core@4.11.12-bugfix-for-lightning-component-entries-not-always-saving": "04t5Y000001Mjx5QAC",
163163
"Nebula Logger - Core@4.12.0-winter-'24-release": "04t5Y000001Mk1wQAC",
164+
"Nebula Logger - Core@4.12.1-improved-error-emails": "04t5Y000001Mk4bQAC",
164165
"Nebula Logger - Core Plugin - Async Failure Additions": "0Ho5Y000000blO4SAI",
165166
"Nebula Logger - Core Plugin - Async Failure Additions@1.0.0": "04t5Y0000015lhiQAA",
166167
"Nebula Logger - Core Plugin - Async Failure Additions@1.0.1": "04t5Y0000015lhsQAA",

0 commit comments

Comments
 (0)