Skip to content

Commit

Permalink
Updated LoggerEmailSender to include all Database.Error fields (#591)
Browse files Browse the repository at this point in the history
* Resolved #590 by updating the Apex class LoggerEmailSender to include all Database.Error fields in the generated emails
  • Loading branch information
alanjaouen authored Jan 18, 2024
1 parent 53af967 commit b24d1f5
Show file tree
Hide file tree
Showing 6 changed files with 48 additions and 21 deletions.
8 changes: 4 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,13 @@ The most robust logger for Salesforce. Works with Apex, Lightning Components, Fl

## Unlocked Package - v4.12.0

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

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

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

---

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -108,12 +108,28 @@ public without sharing class LoggerEmailSender {
sendEmail(messages);
}

private static String getErrorMessageFromDatabaseError(Database.Error error) {
List<String> messageParts = new List<String>();

// Add the status code
messageParts.add('StatusCode: ' + error.getStatusCode());
// Add the message
messageParts.add('Message: ' + error.getMessage());
// Add the fields if available
List<String> fields = error.getFields();
if (fields?.isEmpty() == false) {
messageParts.add('Field(s): [' + String.join(fields, ', ') + ']');
}

return String.join(messageParts, ', ');
}

private static List<String> getErrorMessages(List<Database.SaveResult> saveResults) {
List<String> errorMessages = new List<String>();
for (Database.SaveResult result : saveResults) {
if (result.isSuccess() == false) {
for (Database.Error error : result.getErrors()) {
errorMessages.add(error.getMessage());
errorMessages.add(getErrorMessageFromDatabaseError(error));
}
}
}
Expand All @@ -125,7 +141,7 @@ public without sharing class LoggerEmailSender {
for (Database.UpsertResult result : upsertResults) {
if (result.isSuccess() == false) {
for (Database.Error error : result.getErrors()) {
errorMessages.add(error.getMessage());
errorMessages.add(getErrorMessageFromDatabaseError(error));
}
}
}
Expand Down Expand Up @@ -161,7 +177,7 @@ public without sharing class LoggerEmailSender {
}

private static String buildHtmlBody(Schema.SObjectType sobjectType, List<String> errorMessages) {
final String emailBodyTemplate = 'Logger failed to save {0} {1} records for {2} (User ID: {3})<br /><br />Error Messages:<ul>{4}</ul>';
final String emailBodyTemplate = 'Logger failed to save {0} {1} records for {2} (User ID: {3})<br /><br />Errors:<ul>{4}</ul>';
final String formattedErrorMessages = '<li>' + String.join(errorMessages, '</li><li>') + '</li>';
List<Object> emailBodyInputs = new List<Object>{
errorMessages.size(),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -143,7 +143,7 @@ public class LoggerMockDataCreator {
return (Database.SaveResult) JSON.deserialize('{"success": true, "id": "' + recordId + '"}', Database.SaveResult.class);
} else {
return (Database.SaveResult) JSON.deserialize(
'{"success":false,"errors":[{"message": "Could not save...", "statusCode": "FIELD_CUSTOM_VALIDATION_EXCEPTION"}]}',
'{"success":false,"errors":[{"message": "Could not save...", "statusCode": "FIELD_CUSTOM_VALIDATION_EXCEPTION", "fields": ["Name"]}]}',
Database.SaveResult.class
);
}
Expand Down Expand Up @@ -172,7 +172,7 @@ public class LoggerMockDataCreator {
return (Database.UndeleteResult) JSON.deserialize('{"success": true, "id": "' + recordId + '"}', Database.UndeleteResult.class);
} else {
return (Database.UndeleteResult) JSON.deserialize(
'{"success":false,"errors":[{"message": "Could not undelete...", "statusCode": "FIELD_CUSTOM_VALIDATION_EXCEPTION"}]}',
'{"success":false,"errors":[{"message": "Could not undelete...", "statusCode": "FIELD_CUSTOM_VALIDATION_EXCEPTION", "fields": ["Name"]}]}',
Database.UndeleteResult.class
);
}
Expand Down Expand Up @@ -208,7 +208,7 @@ public class LoggerMockDataCreator {
return (Database.UpsertResult) JSON.deserialize(
'{"success":false, "created":' +
isCreated +
', "errors":[{"message": "Could not upsert...", "statusCode": "FIELD_CUSTOM_VALIDATION_EXCEPTION"}]}',
', "errors":[{"message": "Could not upsert...", "statusCode": "FIELD_CUSTOM_VALIDATION_EXCEPTION", "fields": ["Name"]}]}',
Database.UpsertResult.class
);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -54,11 +54,16 @@ private class LoggerEmailSender_Tests {
Database.SaveResult saveResultWithError = LoggerMockDataCreator.createDatabaseSaveResult(false);
LoggerEmailSender.sendErrorEmail(Schema.LogEntry__c.SObjectType, new List<Database.SaveResult>{ saveResultWithError });

System.Assert.areEqual(
true,
System.Assert.isTrue(
LoggerEmailSender.SENT_EMAILS.get(0).getHtmlBody().contains(saveResultWithError.errors.get(0).getMessage()),
'Email message should contain SaveResult error message'
);
List<String> errorFields = saveResultWithError.getErrors().get(0).getFields();
String expectedFieldsError = 'Field(s): [' + String.join(errorFields, ', ') + ']';
System.Assert.isTrue(
LoggerEmailSender.SENT_EMAILS.get(0).getHtmlBody().contains(expectedFieldsError),
'Email message should contain SaveResult error fields: ' + expectedFieldsError
);
if (LoggerEmailSender.IS_EMAIL_DELIVERABILITY_AVAILABLE) {
System.Assert.areEqual(1, System.Limits.getEmailInvocations(), 'Email should have been sent');
} else {
Expand Down Expand Up @@ -104,11 +109,16 @@ private class LoggerEmailSender_Tests {
Database.UpsertResult upsertResultWithError = LoggerMockDataCreator.createDatabaseUpsertResult(false, false);
LoggerEmailSender.sendErrorEmail(Schema.LogEntry__c.SObjectType, new List<Database.UpsertResult>{ upsertResultWithError });

System.Assert.areEqual(
true,
System.Assert.isTrue(
LoggerEmailSender.SENT_EMAILS.get(0).getHtmlBody().contains(upsertResultWithError.errors.get(0).getMessage()),
'Email message should contain UpsertResult error message'
);
List<String> errorFields = upsertResultWithError.getErrors().get(0).getFields();
String expectedFieldsError = 'Field(s): [' + String.join(errorFields, ', ') + ']';
System.Assert.isTrue(
LoggerEmailSender.SENT_EMAILS.get(0).getHtmlBody().contains(expectedFieldsError),
'Email message should contain UpsertResult error fields: ' + expectedFieldsError
);
if (LoggerEmailSender.IS_EMAIL_DELIVERABILITY_AVAILABLE) {
System.Assert.areEqual(1, System.Limits.getEmailInvocations(), 'Email should have been sent');
} else {
Expand Down
8 changes: 4 additions & 4 deletions nebula-logger/managed-package/sfdx-project.json
Original file line number Diff line number Diff line change
Expand Up @@ -10,10 +10,10 @@
"definitionFile": "./config/scratch-orgs/base-scratch-def.json",
"postInstallScript": "LoggerInstallHandler",
"ancestorVersion": "HIGHEST",
"versionNumber": "4.12.0.NEXT",
"versionName": "Winter '24 Release",
"versionDescription": "View the v4.12.0 milestone in GitHub for the list of changes - https://github.com/jongpie/NebulaLogger/milestone/12?closed=1",
"releaseNotesUrl": "https://github.com/jongpie/NebulaLogger/releases/tag/v4.11.0"
"versionNumber": "4.13.0.NEXT",
"versionName": "Spring '24 Release",
"versionDescription": "View the v4.13.0 milestone in GitHub for the list of changes - https://github.com/jongpie/NebulaLogger/milestone/13?closed=1",
"releaseNotesUrl": "https://github.com/jongpie/NebulaLogger/releases/tag/v4.13.0"
}
],
"packageAliases": {
Expand Down
7 changes: 4 additions & 3 deletions sfdx-project.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,9 @@
"package": "Nebula Logger - Core",
"path": "./nebula-logger/core",
"definitionFile": "./config/scratch-orgs/base-scratch-def.json",
"versionNumber": "4.12.0.NEXT",
"versionName": "Winter '24 Release",
"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",
"versionNumber": "4.12.1.NEXT",
"versionName": "Improved Error Emails",
"versionDescription": "Updated error emails (sent by LoggerEmailSender) to include all Database.Error fields",
"releaseNotesUrl": "https://github.com/jongpie/NebulaLogger/releases",
"unpackagedMetadata": {
"path": "./nebula-logger/extra-tests"
Expand Down Expand Up @@ -161,6 +161,7 @@
"Nebula Logger - Core@4.11.11-reduced-usage-of-email-limits-consumption-in-loggeremailsender": "04t5Y000001Oih7QAC",
"Nebula Logger - Core@4.11.12-bugfix-for-lightning-component-entries-not-always-saving": "04t5Y000001Mjx5QAC",
"Nebula Logger - [email protected]'24-release": "04t5Y000001Mk1wQAC",
"Nebula Logger - [email protected]": "04t5Y000001Mk4bQAC",
"Nebula Logger - Core Plugin - Async Failure Additions": "0Ho5Y000000blO4SAI",
"Nebula Logger - Core Plugin - Async Failure [email protected]": "04t5Y0000015lhiQAA",
"Nebula Logger - Core Plugin - Async Failure [email protected]": "04t5Y0000015lhsQAA",
Expand Down

0 comments on commit b24d1f5

Please sign in to comment.