diff --git a/Manifest/manifest_authors.json b/Manifest/manifest_authors.json
index ba6aa5ee2..f069ae919 100644
--- a/Manifest/manifest_authors.json
+++ b/Manifest/manifest_authors.json
@@ -1,7 +1,7 @@
{
"$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.5/MicrosoftTeams.schema.json",
"manifestVersion": "1.5",
- "version": "4.1.4",
+ "version": "4.1.5",
"id": "1c07cd26-a088-4db8-8928-ace382fa219f",
"packageName": "com.microsoft.teams.companycommunicator.authors",
"developer": {
diff --git a/Manifest/manifest_users.json b/Manifest/manifest_users.json
index c43d80dd3..be5985a3c 100644
--- a/Manifest/manifest_users.json
+++ b/Manifest/manifest_users.json
@@ -1,7 +1,7 @@
{
"$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.5/MicrosoftTeams.schema.json",
"manifestVersion": "1.5",
- "version": "4.1.4",
+ "version": "4.1.5",
"id": "148a66bb-e83d-425a-927d-09f4299a9274",
"packageName": "com.microsoft.teams.companycommunicator",
"developer": {
diff --git a/Source/CompanyCommunicator.Common/Repositories/BaseRepository.cs b/Source/CompanyCommunicator.Common/Repositories/BaseRepository.cs
index 9911f124e..4dd7b787e 100644
--- a/Source/CompanyCommunicator.Common/Repositories/BaseRepository.cs
+++ b/Source/CompanyCommunicator.Common/Repositories/BaseRepository.cs
@@ -59,7 +59,7 @@ public BaseRepository(
protected ILogger Logger { get; }
///
- public async Task CreateOrUpdateAsync(T entity)
+ public virtual async Task CreateOrUpdateAsync(T entity)
{
try
{
@@ -113,7 +113,7 @@ public async Task DeleteAsync(T entity)
}
///
- public async Task GetAsync(string partitionKey, string rowKey)
+ public virtual async Task GetAsync(string partitionKey, string rowKey)
{
try
{
diff --git a/Source/CompanyCommunicator.Common/Repositories/NotificationData/NotificationDataRepository.cs b/Source/CompanyCommunicator.Common/Repositories/NotificationData/NotificationDataRepository.cs
index 95f0368bd..5cad11b52 100644
--- a/Source/CompanyCommunicator.Common/Repositories/NotificationData/NotificationDataRepository.cs
+++ b/Source/CompanyCommunicator.Common/Repositories/NotificationData/NotificationDataRepository.cs
@@ -16,6 +16,13 @@ namespace Microsoft.Teams.Apps.CompanyCommunicator.Common.Repositories.Notificat
///
public class NotificationDataRepository : BaseRepository, INotificationDataRepository
{
+ ///
+ /// Maximum length of error and warning messages to save in the entity.
+ /// This limit ensures that we don't hit the Azure table storage limits for the max size of the data
+ /// in a column, and the total size of an entity.
+ ///
+ public const int MaxMessageLengthToSave = 1024;
+
///
/// Initializes a new instance of the class.
///
@@ -172,8 +179,14 @@ public async Task SaveExceptionInNotificationDataEntityAsync(
notificationDataEntityId);
if (notificationDataEntity != null)
{
- notificationDataEntity.ErrorMessage =
- this.AppendNewLine(notificationDataEntity.ErrorMessage, errorMessage);
+ var newMessage = this.AppendNewLine(notificationDataEntity.ErrorMessage, errorMessage);
+
+ // Restrict the total length of stored message to avoid hitting table storage limits
+ if (newMessage.Length <= MaxMessageLengthToSave)
+ {
+ notificationDataEntity.ErrorMessage = newMessage;
+ }
+
notificationDataEntity.Status = NotificationStatus.Failed.ToString();
// Set the end date as current date.
@@ -195,8 +208,14 @@ public async Task SaveWarningInNotificationDataEntityAsync(
notificationDataEntityId);
if (notificationDataEntity != null)
{
- notificationDataEntity.WarningMessage =
- this.AppendNewLine(notificationDataEntity.WarningMessage, warningMessage);
+ var newMessage = this.AppendNewLine(notificationDataEntity.WarningMessage, warningMessage);
+
+ // Restrict the total length of stored message to avoid hitting table storage limits
+ if (newMessage.Length <= MaxMessageLengthToSave)
+ {
+ notificationDataEntity.WarningMessage = newMessage;
+ }
+
await this.CreateOrUpdateAsync(notificationDataEntity);
}
}
diff --git a/Source/CompanyCommunicator/ClientApp/package-lock.json b/Source/CompanyCommunicator/ClientApp/package-lock.json
index 593b7edd9..f756ac4f2 100644
--- a/Source/CompanyCommunicator/ClientApp/package-lock.json
+++ b/Source/CompanyCommunicator/ClientApp/package-lock.json
@@ -1,6 +1,6 @@
{
"name": "company-communicator",
- "version": "4.1.4",
+ "version": "4.1.5",
"lockfileVersion": 1,
"requires": true,
"dependencies": {
diff --git a/Source/CompanyCommunicator/ClientApp/package.json b/Source/CompanyCommunicator/ClientApp/package.json
index 0b76cc079..d164499ff 100644
--- a/Source/CompanyCommunicator/ClientApp/package.json
+++ b/Source/CompanyCommunicator/ClientApp/package.json
@@ -1,6 +1,6 @@
{
"name": "company-communicator",
- "version": "4.1.4",
+ "version": "4.1.5",
"private": true,
"dependencies": {
"@fluentui/react-northstar": "^0.52.0",
diff --git a/Source/Test/CompanyCommunicator.Common.Test/Repositories/NotificationData/NotificationDataRepositoryTests.cs b/Source/Test/CompanyCommunicator.Common.Test/Repositories/NotificationData/NotificationDataRepositoryTests.cs
new file mode 100644
index 000000000..5ae1a6eaa
--- /dev/null
+++ b/Source/Test/CompanyCommunicator.Common.Test/Repositories/NotificationData/NotificationDataRepositoryTests.cs
@@ -0,0 +1,215 @@
+//
+// Copyright (c) Microsoft Corporation.
+// Licensed under the MIT License.
+//
+
+namespace Microsoft.Teams.App.CompanyCommunicator.Common.Test.Repositories.NotificationData
+{
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using FluentAssertions;
+ using Microsoft.Extensions.Logging;
+ using Microsoft.Extensions.Options;
+ using Microsoft.Teams.Apps.CompanyCommunicator.Common.Repositories;
+ using Microsoft.Teams.Apps.CompanyCommunicator.Common.Repositories.NotificationData;
+ using Moq;
+ using Xunit;
+
+ ///
+ /// Notification Data Repository unit tests.
+ ///
+ public class NotificationDataRepositoryTests
+ {
+ private Mock> logger = new Mock>();
+ private Mock> repositoryOptions = new Mock>();
+ private TableRowKeyGenerator rowKeyGenerator = new TableRowKeyGenerator();
+
+ ///
+ /// Gets data for SaveExceptionInNotificationDataEntityAsync_SavesExceptionInfo and SaveWarningInNotificationDataEntityAsync_SavesWarningInfo.
+ ///
+ public static IEnumerable