diff --git a/.editorconfig b/.editorconfig
index 077a4c3..807c5e5 100644
--- a/.editorconfig
+++ b/.editorconfig
@@ -21,9 +21,6 @@ dotnet_diagnostic.RECS0117.severity = none
dotnet_diagnostic.SA0001.severity = none
dotnet_diagnostic.SA1649.severity = none
-# IDE0290: Use primary constructor
-dotnet_diagnostic.IDE0290.severity = none
-
# IDE0305: Simplify collection initialization
dotnet_diagnostic.IDE0305.severity = none
diff --git a/Directory.Build.props b/Directory.Build.props
index c0086ac..1bc40cd 100644
--- a/Directory.Build.props
+++ b/Directory.Build.props
@@ -11,7 +11,7 @@
https://github.com/squidex/squidex
true
snupkg
- 6.20.0
+ 6.21.0
diff --git a/Dockerfile b/Dockerfile
index 04ba21d..69f2151 100644
--- a/Dockerfile
+++ b/Dockerfile
@@ -9,6 +9,9 @@ WORKDIR /src
COPY *.sln ./
# Copy the main source project files
+COPY ai/*/*.csproj ./
+RUN for file in $(ls *.csproj); do mkdir -p assets/${file%.*}/ && mv $file ai/${file%.*}/; done
+
COPY assets/*/*.csproj ./
RUN for file in $(ls *.csproj); do mkdir -p assets/${file%.*}/ && mv $file assets/${file%.*}/; done
diff --git a/ai/Squidex.AI.Tests/OpenApiFunctionParserTests.cs b/ai/Squidex.AI.Tests/OpenApiFunctionParserTests.cs
index 5ce3dd2..878f6b8 100644
--- a/ai/Squidex.AI.Tests/OpenApiFunctionParserTests.cs
+++ b/ai/Squidex.AI.Tests/OpenApiFunctionParserTests.cs
@@ -5,8 +5,8 @@
// All rights reserved. Licensed under the MIT license.
// ==========================================================================
+using Betalgo.Ranul.OpenAI.ObjectModels.RequestModels;
using FluentAssertions;
-using OpenAI.ObjectModels.RequestModels;
using Squidex.AI.Implementation.OpenAI;
using Squidex.AI.Utils;
using Xunit;
diff --git a/ai/Squidex.AI.Tests/Squidex.AI.Tests.csproj b/ai/Squidex.AI.Tests/Squidex.AI.Tests.csproj
index f1e38bc..184f1d9 100644
--- a/ai/Squidex.AI.Tests/Squidex.AI.Tests.csproj
+++ b/ai/Squidex.AI.Tests/Squidex.AI.Tests.csproj
@@ -16,19 +16,19 @@
runtime; build; native; contentfiles; analyzers; buildtransitive
-
-
-
+
+
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
-
+
+
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/ai/Squidex.AI/DelegateChatTool.cs b/ai/Squidex.AI/DelegateChatTool.cs
index 07580b2..3a6886c 100644
--- a/ai/Squidex.AI/DelegateChatTool.cs
+++ b/ai/Squidex.AI/DelegateChatTool.cs
@@ -7,18 +7,9 @@
namespace Squidex.AI;
-public sealed class DelegateChatTool : IChatTool
+public sealed class DelegateChatTool(ToolSpec spec, Func> action) : IChatTool
{
- private readonly Func> action;
-
- public ToolSpec Spec { get; }
-
- public DelegateChatTool(ToolSpec spec, Func> action)
- {
- Spec = spec;
-
- this.action = action;
- }
+ public ToolSpec Spec { get; } = spec;
public Task ExecuteAsync(ToolContext toolContext,
CancellationToken ct)
diff --git a/ai/Squidex.AI/Implementation/ChatAgent.cs b/ai/Squidex.AI/Implementation/ChatAgent.cs
index fcb9069..513efee 100644
--- a/ai/Squidex.AI/Implementation/ChatAgent.cs
+++ b/ai/Squidex.AI/Implementation/ChatAgent.cs
@@ -11,30 +11,17 @@
namespace Squidex.AI.Implementation;
-public sealed class ChatAgent : IChatAgent
+public sealed class ChatAgent(
+ IChatProvider chatProvider,
+ IChatStore chatStore,
+ IEnumerable chatPipes,
+ IEnumerable chatToolProviders,
+ IOptions options) : IChatAgent
{
- private readonly ChatOptions options;
- private readonly IChatProvider chatProvider;
- private readonly IChatStore chatStore;
- private readonly IEnumerable chatPipes;
- private readonly IEnumerable chatToolProviders;
+ private readonly ChatOptions options = options.Value;
public bool IsConfigured => chatProvider is not NoopChatProvider;
- public ChatAgent(
- IChatProvider chatProvider,
- IChatStore chatStore,
- IEnumerable chatPipes,
- IEnumerable chatToolProviders,
- IOptions options)
- {
- this.options = options.Value;
- this.chatPipes = chatPipes;
- this.chatProvider = chatProvider;
- this.chatStore = chatStore;
- this.chatToolProviders = chatToolProviders;
- }
-
public async Task StopConversationAsync(string conversationId, ChatContext? context = null,
CancellationToken ct = default)
{
diff --git a/ai/Squidex.AI/Implementation/ChatCleaner.cs b/ai/Squidex.AI/Implementation/ChatCleaner.cs
index b753542..970ad3a 100644
--- a/ai/Squidex.AI/Implementation/ChatCleaner.cs
+++ b/ai/Squidex.AI/Implementation/ChatCleaner.cs
@@ -11,32 +11,17 @@
namespace Squidex.AI.Implementation;
-public sealed class ChatCleaner : IBackgroundProcess
+public sealed class ChatCleaner(
+ IChatAgent chatAgent,
+ IChatStore chatStore,
+ IEnumerable chatTools,
+ IOptions options,
+ TimeProvider timeProvider,
+ ILogger log) : IBackgroundProcess
{
- private readonly ChatOptions options;
- private readonly TimeProvider timeProvider;
- private readonly IChatAgent chatAgent;
- private readonly IChatStore chatStore;
- private readonly IEnumerable chatTools;
- private readonly ILogger log;
+ private readonly ChatOptions options = options.Value;
private SimpleTimer? cleanupTimer;
- public ChatCleaner(
- IChatAgent chatAgent,
- IChatStore chatStore,
- IEnumerable chatTools,
- IOptions options,
- TimeProvider timeProvider,
- ILogger log)
- {
- this.chatAgent = chatAgent;
- this.chatStore = chatStore;
- this.chatTools = chatTools;
- this.log = log;
- this.options = options.Value;
- this.timeProvider = timeProvider;
- }
-
public Task StartAsync(
CancellationToken ct)
{
diff --git a/ai/Squidex.AI/Implementation/ImagePipe.cs b/ai/Squidex.AI/Implementation/ImagePipe.cs
index 22b1466..bdd76c2 100644
--- a/ai/Squidex.AI/Implementation/ImagePipe.cs
+++ b/ai/Squidex.AI/Implementation/ImagePipe.cs
@@ -10,17 +10,11 @@
namespace Squidex.AI.Implementation;
-public sealed class ImagePipe : IChatPipe
+public sealed class ImagePipe(IImageTool imageGenerator) : IChatPipe
{
private const string ImageStart = "
";
private const string ImageEnd = "";
private const int BufferLength = 5;
- private readonly IImageTool imageGenerator;
-
- public ImagePipe(IImageTool imageGenerator)
- {
- this.imageGenerator = imageGenerator;
- }
public async IAsyncEnumerable StreamAsync(IAsyncEnumerable source, ChatProviderRequest request,
[EnumeratorCancellation] CancellationToken ct = default)
diff --git a/ai/Squidex.AI/Implementation/Mongo/MongoChatStore.cs b/ai/Squidex.AI/Implementation/Mongo/MongoChatStore.cs
index 85d7868..b52adaa 100644
--- a/ai/Squidex.AI/Implementation/Mongo/MongoChatStore.cs
+++ b/ai/Squidex.AI/Implementation/Mongo/MongoChatStore.cs
@@ -13,14 +13,9 @@
namespace Squidex.AI.Implementation.Mongo;
-public sealed class MongoChatStore : IChatStore, IInitializable
+public sealed class MongoChatStore(IMongoDatabase database, IOptions options) : IChatStore, IInitializable
{
- private readonly IMongoCollection collection;
-
- public MongoChatStore(IMongoDatabase database, IOptions options)
- {
- collection = database.GetCollection(options.Value.CollectionName);
- }
+ private readonly IMongoCollection collection = database.GetCollection(options.Value.CollectionName);
public Task InitializeAsync(
CancellationToken ct)
diff --git a/ai/Squidex.AI/Implementation/OpenAI/DallEOptions.cs b/ai/Squidex.AI/Implementation/OpenAI/DallEOptions.cs
index 6ec198f..e016d46 100644
--- a/ai/Squidex.AI/Implementation/OpenAI/DallEOptions.cs
+++ b/ai/Squidex.AI/Implementation/OpenAI/DallEOptions.cs
@@ -5,12 +5,12 @@
// All rights reserved. Licensed under the MIT license.
// ==========================================================================
-using OpenAI;
-using OpenAI.ObjectModels;
+using Betalgo.Ranul.OpenAI;
+using Betalgo.Ranul.OpenAI.ObjectModels;
namespace Squidex.AI.Implementation.OpenAI;
-public sealed class DallEOptions : OpenAiOptions
+public sealed class DallEOptions : OpenAIOptions
{
public string? Model { get; set; } = Models.Dall_e_3;
diff --git a/ai/Squidex.AI/Implementation/OpenAI/DallETool.cs b/ai/Squidex.AI/Implementation/OpenAI/DallETool.cs
index c2d38f0..a03d1ab 100644
--- a/ai/Squidex.AI/Implementation/OpenAI/DallETool.cs
+++ b/ai/Squidex.AI/Implementation/OpenAI/DallETool.cs
@@ -5,23 +5,24 @@
// All rights reserved. Licensed under the MIT license.
// ==========================================================================
+using Betalgo.Ranul.OpenAI.Managers;
+using Betalgo.Ranul.OpenAI.ObjectModels.RequestModels;
using Microsoft.Extensions.Options;
-using OpenAI.Managers;
-using OpenAI.ObjectModels.RequestModels;
using Squidex.Assets;
namespace Squidex.AI.Implementation.OpenAI;
-public sealed class DallETool : IImageTool
+public sealed class DallETool(
+ IOptions options,
+ IAssetStore assetStore,
+ IAssetThumbnailGenerator assetThumbnailGenerator,
+ IChatProvider chatProvider,
+ IHttpImageEndpoint httpImageEndpoint,
+ IHttpClientFactory httpClientFactory) : IImageTool
{
private const string DataPrefix = "dall_e_image";
- private readonly OpenAIService service;
- private readonly DallEOptions options;
- private readonly IAssetStore assetStore;
- private readonly IAssetThumbnailGenerator assetThumbnailGenerator;
- private readonly IChatProvider chatProvider;
- private readonly IHttpImageEndpoint httpImageEndpoint;
- private readonly IHttpClientFactory httpClientFactory;
+ private readonly OpenAIService service = new OpenAIService(options.Value);
+ private readonly DallEOptions options = options.Value;
public ToolSpec Spec { get; } =
new ToolSpec("dall-e", "Dall-E", "Generates images based on queries.")
@@ -35,24 +36,6 @@ public sealed class DallETool : IImageTool
}
};
- public DallETool(
- IOptions options,
- IAssetStore assetStore,
- IAssetThumbnailGenerator assetThumbnailGenerator,
- IChatProvider chatProvider,
- IHttpImageEndpoint httpImageEndpoint,
- IHttpClientFactory httpClientFactory)
- {
- service = new OpenAIService(options.Value);
-
- this.options = options.Value;
- this.assetStore = assetStore;
- this.assetThumbnailGenerator = assetThumbnailGenerator;
- this.chatProvider = chatProvider;
- this.httpImageEndpoint = httpImageEndpoint;
- this.httpClientFactory = httpClientFactory;
- }
-
public async Task CleanupAsync(Dictionary toolData,
CancellationToken ct)
{
diff --git a/ai/Squidex.AI/Implementation/OpenAI/Helper.cs b/ai/Squidex.AI/Implementation/OpenAI/Helper.cs
index b3f0bdb..a531e5f 100644
--- a/ai/Squidex.AI/Implementation/OpenAI/Helper.cs
+++ b/ai/Squidex.AI/Implementation/OpenAI/Helper.cs
@@ -7,10 +7,10 @@
using System.Text.Json;
using System.Text.Json.Nodes;
-using OpenAI.Builders;
-using OpenAI.ObjectModels.RequestModels;
-using OpenAI.ObjectModels.SharedModels;
-using OpenAIMessage = OpenAI.ObjectModels.RequestModels.ChatMessage;
+using Betalgo.Ranul.OpenAI.Builders;
+using Betalgo.Ranul.OpenAI.ObjectModels.RequestModels;
+using Betalgo.Ranul.OpenAI.ObjectModels.SharedModels;
+using OpenAIMessage = Betalgo.Ranul.OpenAI.ObjectModels.RequestModels.ChatMessage;
namespace Squidex.AI.Implementation.OpenAI;
diff --git a/ai/Squidex.AI/Implementation/OpenAI/OpenAIChatOptions.cs b/ai/Squidex.AI/Implementation/OpenAI/OpenAIChatOptions.cs
index a703e40..1d2e8cf 100644
--- a/ai/Squidex.AI/Implementation/OpenAI/OpenAIChatOptions.cs
+++ b/ai/Squidex.AI/Implementation/OpenAI/OpenAIChatOptions.cs
@@ -5,12 +5,12 @@
// All rights reserved. Licensed under the MIT license.
// ==========================================================================
-using OpenAI;
-using OpenAI.ObjectModels;
+using Betalgo.Ranul.OpenAI;
+using Betalgo.Ranul.OpenAI.ObjectModels;
namespace Squidex.AI.Implementation.OpenAI;
-public sealed class OpenAIChatOptions : OpenAiOptions
+public sealed class OpenAIChatOptions : OpenAIOptions
{
public string Model { get; set; } = Models.Gpt_4o;
diff --git a/ai/Squidex.AI/Implementation/OpenAI/OpenAIChatProvider.cs b/ai/Squidex.AI/Implementation/OpenAI/OpenAIChatProvider.cs
index 018df10..187921d 100644
--- a/ai/Squidex.AI/Implementation/OpenAI/OpenAIChatProvider.cs
+++ b/ai/Squidex.AI/Implementation/OpenAI/OpenAIChatProvider.cs
@@ -7,25 +7,18 @@
using System.Globalization;
using System.Reactive.Linq;
+using Betalgo.Ranul.OpenAI.Managers;
+using Betalgo.Ranul.OpenAI.ObjectModels.RequestModels;
using Microsoft.Extensions.Options;
-using OpenAI.Managers;
-using OpenAI.ObjectModels.RequestModels;
-using OpenAIMessage = OpenAI.ObjectModels.RequestModels.ChatMessage;
+using OpenAIMessage = Betalgo.Ranul.OpenAI.ObjectModels.RequestModels.ChatMessage;
namespace Squidex.AI.Implementation.OpenAI;
-public sealed class OpenAIChatProvider : IChatProvider
+public sealed class OpenAIChatProvider(IOptions options) : IChatProvider
{
private readonly StreamOptions streamOptions = new StreamOptions { IncludeUsage = true };
- private readonly OpenAIChatOptions options;
- private readonly OpenAIService service;
-
- public OpenAIChatProvider(IOptions options)
- {
- service = new OpenAIService(options.Value);
-
- this.options = options.Value;
- }
+ private readonly OpenAIChatOptions options = options.Value;
+ private readonly OpenAIService service = new OpenAIService(options.Value);
public IAsyncEnumerable StreamAsync(ChatProviderRequest request,
CancellationToken ct = default)
diff --git a/ai/Squidex.AI/Implementation/OpenAI/OpenAIEmbeddings.cs b/ai/Squidex.AI/Implementation/OpenAI/OpenAIEmbeddings.cs
index d1f5a0d..37f8689 100644
--- a/ai/Squidex.AI/Implementation/OpenAI/OpenAIEmbeddings.cs
+++ b/ai/Squidex.AI/Implementation/OpenAI/OpenAIEmbeddings.cs
@@ -5,23 +5,16 @@
// All rights reserved. Licensed under the MIT license.
// ==========================================================================
+using Betalgo.Ranul.OpenAI.Managers;
+using Betalgo.Ranul.OpenAI.ObjectModels.RequestModels;
using Microsoft.Extensions.Options;
-using OpenAI.Managers;
-using OpenAI.ObjectModels.RequestModels;
namespace Squidex.AI.Implementation.OpenAI;
-public sealed class OpenAIEmbeddings : IEmbeddings
+public sealed class OpenAIEmbeddings(IOptions options) : IEmbeddings
{
- private readonly OpenAIEmbeddingsOptions options;
- private readonly OpenAIService service;
-
- public OpenAIEmbeddings(IOptions options)
- {
- service = new OpenAIService(options.Value);
-
- this.options = options.Value;
- }
+ private readonly OpenAIEmbeddingsOptions options = options.Value;
+ private readonly OpenAIService service = new OpenAIService(options.Value);
public async Task> CalculateEmbeddingsAsync(string query,
CancellationToken ct)
diff --git a/ai/Squidex.AI/Implementation/OpenAI/OpenAIEmbeddingsOptions.cs b/ai/Squidex.AI/Implementation/OpenAI/OpenAIEmbeddingsOptions.cs
index e88c363..3111d75 100644
--- a/ai/Squidex.AI/Implementation/OpenAI/OpenAIEmbeddingsOptions.cs
+++ b/ai/Squidex.AI/Implementation/OpenAI/OpenAIEmbeddingsOptions.cs
@@ -5,12 +5,12 @@
// All rights reserved. Licensed under the MIT license.
// ==========================================================================
-using OpenAI;
-using OpenAI.ObjectModels;
+using Betalgo.Ranul.OpenAI;
+using Betalgo.Ranul.OpenAI.ObjectModels;
namespace Squidex.AI.Implementation.OpenAI;
-public sealed class OpenAIEmbeddingsOptions : OpenAiOptions
+public sealed class OpenAIEmbeddingsOptions : OpenAIOptions
{
public string ModelName { get; set; } = Models.TextEmbeddingV3Large;
}
diff --git a/ai/Squidex.AI/Implementation/Pinecone/PineconeTool.cs b/ai/Squidex.AI/Implementation/Pinecone/PineconeTool.cs
index e90c24e..55a66a4 100644
--- a/ai/Squidex.AI/Implementation/Pinecone/PineconeTool.cs
+++ b/ai/Squidex.AI/Implementation/Pinecone/PineconeTool.cs
@@ -49,7 +49,7 @@ public PineconeTool(IEmbeddings embeddings, IOptions options)
public async Task InitializeAsync(
CancellationToken ct)
{
- index = await client.GetIndex(options.IndexName, ct);
+ index = await client.GetIndex(options.IndexName, ct);
}
public async Task ExecuteAsync(ToolContext toolContext,
diff --git a/ai/Squidex.AI/Implementation/SingleChatToolProvider.cs b/ai/Squidex.AI/Implementation/SingleChatToolProvider.cs
index 59a29fd..f9d6d91 100644
--- a/ai/Squidex.AI/Implementation/SingleChatToolProvider.cs
+++ b/ai/Squidex.AI/Implementation/SingleChatToolProvider.cs
@@ -7,15 +7,8 @@
namespace Squidex.AI.Implementation;
-public sealed class SingleChatToolProvider : IChatToolProvider where T : IChatTool
+public sealed class SingleChatToolProvider(T tool) : IChatToolProvider where T : IChatTool
{
- private readonly T tool;
-
- public SingleChatToolProvider(T tool)
- {
- this.tool = tool;
- }
-
public IAsyncEnumerable GetToolsAsync(ChatContext chatContext,
CancellationToken ct)
{
diff --git a/ai/Squidex.AI/Squidex.AI.csproj b/ai/Squidex.AI/Squidex.AI.csproj
index fb4820e..0af1390 100644
--- a/ai/Squidex.AI/Squidex.AI.csproj
+++ b/ai/Squidex.AI/Squidex.AI.csproj
@@ -12,23 +12,23 @@
-
-
+
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
-
+
+
-
+
diff --git a/assets/Benchmarks/Benchmarks.csproj b/assets/Benchmarks/Benchmarks.csproj
index 45566df..2aa47ea 100644
--- a/assets/Benchmarks/Benchmarks.csproj
+++ b/assets/Benchmarks/Benchmarks.csproj
@@ -11,7 +11,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/assets/Squidex.Assets.Azure/AzureBlobAssetStore.cs b/assets/Squidex.Assets.Azure/AzureBlobAssetStore.cs
index dc17cbc..7f32810 100644
--- a/assets/Squidex.Assets.Azure/AzureBlobAssetStore.cs
+++ b/assets/Squidex.Assets.Azure/AzureBlobAssetStore.cs
@@ -13,7 +13,7 @@
namespace Squidex.Assets;
-public class AzureBlobAssetStore : IAssetStore, IInitializable
+public class AzureBlobAssetStore(IOptions options) : IAssetStore, IInitializable
{
private static readonly BlobUploadOptions NoOverwriteUpload = new BlobUploadOptions
{
@@ -29,15 +29,10 @@ public class AzureBlobAssetStore : IAssetStore, IInitializable
IfNoneMatch = new ETag("*")
}
};
- private readonly AzureBlobAssetOptions options;
+ private readonly AzureBlobAssetOptions options = options.Value;
private BlobContainerClient blobContainer;
private BlobContainerProperties blobContainerProperties;
- public AzureBlobAssetStore(IOptions options)
- {
- this.options = options.Value;
- }
-
public async Task InitializeAsync(
CancellationToken ct)
{
diff --git a/assets/Squidex.Assets.Azure/Squidex.Assets.Azure.csproj b/assets/Squidex.Assets.Azure/Squidex.Assets.Azure.csproj
index 1f29618..d030377 100644
--- a/assets/Squidex.Assets.Azure/Squidex.Assets.Azure.csproj
+++ b/assets/Squidex.Assets.Azure/Squidex.Assets.Azure.csproj
@@ -13,8 +13,8 @@
-
-
+
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/assets/Squidex.Assets.FTP/FTPAssetStore.cs b/assets/Squidex.Assets.FTP/FTPAssetStore.cs
index 600967a..4af3eb4 100644
--- a/assets/Squidex.Assets.FTP/FTPAssetStore.cs
+++ b/assets/Squidex.Assets.FTP/FTPAssetStore.cs
@@ -15,25 +15,15 @@
namespace Squidex.Assets;
[ExcludeFromCodeCoverage]
-public sealed class FTPAssetStore : IAssetStore, IInitializable
+public sealed class FTPAssetStore(IOptions options, ILogger log) : IAssetStore, IInitializable
{
- private readonly ILogger log;
- private readonly FTPClientPool pool;
- private readonly FTPAssetOptions options;
-
- public FTPAssetStore(IOptions options, ILogger log)
- {
- this.options = options.Value;
-
- this.log = log;
-
- pool = new FTPClientPool(
+ private readonly FTPClientPool pool = new FTPClientPool(
() => new AsyncFtpClient(
options.Value.ServerHost,
options.Value.Username,
options.Value.Password,
options.Value.ServerPort), 1);
- }
+ private readonly FTPAssetOptions options = options.Value;
public async Task InitializeAsync(
CancellationToken ct)
diff --git a/assets/Squidex.Assets.FTP/FTPClientPool.cs b/assets/Squidex.Assets.FTP/FTPClientPool.cs
index a6a446c..61f2844 100644
--- a/assets/Squidex.Assets.FTP/FTPClientPool.cs
+++ b/assets/Squidex.Assets.FTP/FTPClientPool.cs
@@ -9,20 +9,12 @@
namespace Squidex.Assets;
-internal sealed class FTPClientPool
+internal sealed class FTPClientPool(Func clientFactory, int clientsLimit)
{
private readonly Queue> queue = new Queue>();
private readonly Queue pool = new Queue();
- private readonly Func clientFactory;
- private readonly int clientsLimit;
private int created;
- public FTPClientPool(Func clientFactory, int clientsLimit)
- {
- this.clientFactory = clientFactory;
- this.clientsLimit = clientsLimit;
- }
-
public async Task<(IAsyncFtpClient, bool IsNew)> GetClientAsync(
CancellationToken ct)
{
diff --git a/assets/Squidex.Assets.FTP/Squidex.Assets.FTP.csproj b/assets/Squidex.Assets.FTP/Squidex.Assets.FTP.csproj
index eb58548..5297ba5 100644
--- a/assets/Squidex.Assets.FTP/Squidex.Assets.FTP.csproj
+++ b/assets/Squidex.Assets.FTP/Squidex.Assets.FTP.csproj
@@ -13,8 +13,8 @@
-
-
+
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/assets/Squidex.Assets.GoogleCloud/GoogleCloudAssetStore.cs b/assets/Squidex.Assets.GoogleCloud/GoogleCloudAssetStore.cs
index 666edf9..aa22c4e 100644
--- a/assets/Squidex.Assets.GoogleCloud/GoogleCloudAssetStore.cs
+++ b/assets/Squidex.Assets.GoogleCloud/GoogleCloudAssetStore.cs
@@ -14,18 +14,13 @@
namespace Squidex.Assets;
-public sealed class GoogleCloudAssetStore : IAssetStore, IInitializable
+public sealed class GoogleCloudAssetStore(IOptions options) : IAssetStore, IInitializable
{
private static readonly UploadObjectOptions IfNotExists = new UploadObjectOptions { IfGenerationMatch = 0 };
private static readonly CopyObjectOptions IfNotExistsCopy = new CopyObjectOptions { IfGenerationMatch = 0 };
- private readonly string bucketName;
+ private readonly string bucketName = options.Value.Bucket;
private StorageClient storageClient;
- public GoogleCloudAssetStore(IOptions options)
- {
- bucketName = options.Value.Bucket;
- }
-
public async Task InitializeAsync(
CancellationToken ct)
{
diff --git a/assets/Squidex.Assets.GoogleCloud/Squidex.Assets.GoogleCloud.csproj b/assets/Squidex.Assets.GoogleCloud/Squidex.Assets.GoogleCloud.csproj
index c3f609f..efe37bc 100644
--- a/assets/Squidex.Assets.GoogleCloud/Squidex.Assets.GoogleCloud.csproj
+++ b/assets/Squidex.Assets.GoogleCloud/Squidex.Assets.GoogleCloud.csproj
@@ -14,7 +14,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/assets/Squidex.Assets.ImageMagick/ImageMagickThumbnailGenerator.cs b/assets/Squidex.Assets.ImageMagick/ImageMagickThumbnailGenerator.cs
index ad6ac4f..7a24277 100644
--- a/assets/Squidex.Assets.ImageMagick/ImageMagickThumbnailGenerator.cs
+++ b/assets/Squidex.Assets.ImageMagick/ImageMagickThumbnailGenerator.cs
@@ -60,16 +60,21 @@ protected override async Task CreateThumbnailCoreAsync(Stream source, string mim
var resizeMode = GetResizeMode(options, w, h, image);
var resizeAnchor = GetResizeAnchor(options);
- var (size, pad) = ResizeHelper.CalculateTargetLocationAndBounds(resizeMode, new Size(image.Width, image.Height), w, h, resizeAnchor);
-
- var sourceRectangle = new MagickGeometry(pad.Width, pad.Height)
+ var (size, pad) = ResizeHelper.CalculateTargetLocationAndBounds(
+ resizeMode,
+ new Size((int)image.Width, (int)image.Height),
+ w,
+ h,
+ resizeAnchor);
+
+ var sourceRectangle = new MagickGeometry((uint)pad.Width, (uint)pad.Height)
{
IgnoreAspectRatio = true
};
clone.Resize(sourceRectangle);
- image.Extent(size.Width, size.Height);
+ image.Extent((uint)size.Width, (uint)size.Height);
image.CompositeClear(color);
image.Composite(clone, pad.X, pad.Y, CompositeOperator.Over);
}
@@ -83,7 +88,7 @@ protected override async Task CreateThumbnailCoreAsync(Stream source, string mim
if (options.Quality.HasValue)
{
- image.Quality = options.Quality.Value;
+ image.Quality = (uint)options.Quality.Value;
}
}
@@ -134,8 +139,8 @@ protected override async Task FixCoreAsync(Stream source, string mimeType, Strea
return Task.FromResult(new ImageInfo(
image.Format.ToImageFormat(),
- image.Width,
- image.Height,
+ (int)image.Width,
+ (int)image.Height,
image.Orientation.GetOrientation(),
hasSensitiveMetadata));
}
diff --git a/assets/Squidex.Assets.ImageMagick/Internal/Extensions.cs b/assets/Squidex.Assets.ImageMagick/Internal/Extensions.cs
index f599b93..92ae5af 100644
--- a/assets/Squidex.Assets.ImageMagick/Internal/Extensions.cs
+++ b/assets/Squidex.Assets.ImageMagick/Internal/Extensions.cs
@@ -58,11 +58,11 @@ public static void CompositeClear(this IMagickImage image, MagickColor col
var w = Math.Min(BufferSize, image.Width - x);
var h = Math.Min(BufferSize, image.Height - y);
- var bufferLength = w * h * colorChannels;
+ var bufferLength = (int)(w * h * colorChannels);
var actualBuffer = buffer.AsSpan()[..bufferLength];
- pixels.SetArea(x, y, w, h, actualBuffer);
+ pixels.SetArea(x, y, (uint)w, (uint)h, actualBuffer);
}
}
}
diff --git a/assets/Squidex.Assets.ImageMagick/Internal/StreamFileAbstraction.cs b/assets/Squidex.Assets.ImageMagick/Internal/StreamFileAbstraction.cs
index 37849bb..272e056 100644
--- a/assets/Squidex.Assets.ImageMagick/Internal/StreamFileAbstraction.cs
+++ b/assets/Squidex.Assets.ImageMagick/Internal/StreamFileAbstraction.cs
@@ -11,23 +11,14 @@
namespace Squidex.Assets.Internal;
-internal sealed class StreamFileAbstraction : IFileAbstraction
+internal sealed class StreamFileAbstraction(Stream stream, string extension) : IFileAbstraction
{
- private readonly Stream stream;
- private readonly string extension;
-
public string Name => $"image.{extension}";
public Stream ReadStream => stream;
public Stream WriteStream => throw new NotSupportedException();
- public StreamFileAbstraction(Stream stream, string extension)
- {
- this.stream = stream;
- this.extension = extension;
- }
-
public void CloseStream(Stream stream)
{
}
diff --git a/assets/Squidex.Assets.ImageMagick/Squidex.Assets.ImageMagick.csproj b/assets/Squidex.Assets.ImageMagick/Squidex.Assets.ImageMagick.csproj
index 041005d..99b53cd 100644
--- a/assets/Squidex.Assets.ImageMagick/Squidex.Assets.ImageMagick.csproj
+++ b/assets/Squidex.Assets.ImageMagick/Squidex.Assets.ImageMagick.csproj
@@ -12,9 +12,9 @@
-
-
-
+
+
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/assets/Squidex.Assets.ImageSharp/ImageSharpThumbnailGenerator.cs b/assets/Squidex.Assets.ImageSharp/ImageSharpThumbnailGenerator.cs
index 15edd9d..c6f93a0 100644
--- a/assets/Squidex.Assets.ImageSharp/ImageSharpThumbnailGenerator.cs
+++ b/assets/Squidex.Assets.ImageSharp/ImageSharpThumbnailGenerator.cs
@@ -30,17 +30,9 @@
namespace Squidex.Assets;
-public sealed class ImageSharpThumbnailGenerator : AssetThumbnailGeneratorBase
+public sealed class ImageSharpThumbnailGenerator(IHttpClientFactory httpClientFactory) : AssetThumbnailGeneratorBase
{
- private readonly HashSet mimeTypes;
- private readonly IHttpClientFactory httpClientFactory;
-
- public ImageSharpThumbnailGenerator(IHttpClientFactory httpClientFactory)
- {
- this.httpClientFactory = httpClientFactory;
-
- mimeTypes = Configuration.Default.ImageFormatsManager.ImageFormats.SelectMany(x => x.MimeTypes).ToHashSet();
- }
+ private readonly HashSet mimeTypes = Configuration.Default.ImageFormatsManager.ImageFormats.SelectMany(x => x.MimeTypes).ToHashSet();
public override bool CanReadAndWrite(string mimeType)
{
diff --git a/assets/Squidex.Assets.ImageSharp/Squidex.Assets.ImageSharp.csproj b/assets/Squidex.Assets.ImageSharp/Squidex.Assets.ImageSharp.csproj
index c66577f..d974dd3 100644
--- a/assets/Squidex.Assets.ImageSharp/Squidex.Assets.ImageSharp.csproj
+++ b/assets/Squidex.Assets.ImageSharp/Squidex.Assets.ImageSharp.csproj
@@ -12,8 +12,8 @@
-
-
+
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/assets/Squidex.Assets.Mongo/MongoGridFsAssetStore.cs b/assets/Squidex.Assets.Mongo/MongoGridFsAssetStore.cs
index c4d3a6b..1f09528 100644
--- a/assets/Squidex.Assets.Mongo/MongoGridFsAssetStore.cs
+++ b/assets/Squidex.Assets.Mongo/MongoGridFsAssetStore.cs
@@ -12,17 +12,11 @@
namespace Squidex.Assets;
-public sealed class MongoGridFsAssetStore : IAssetStore, IInitializable
+public sealed class MongoGridFsAssetStore(IGridFSBucket bucket) : IAssetStore, IInitializable
{
private static readonly FilterDefinitionBuilder> Filters = Builders>.Filter;
private static readonly GridFSDownloadOptions DownloadDefault = new GridFSDownloadOptions();
private static readonly GridFSDownloadOptions DownloadSeekable = new GridFSDownloadOptions { Seekable = true };
- private readonly IGridFSBucket bucket;
-
- public MongoGridFsAssetStore(IGridFSBucket bucket)
- {
- this.bucket = bucket;
- }
public async Task InitializeAsync(
CancellationToken ct)
diff --git a/assets/Squidex.Assets.Mongo/Squidex.Assets.Mongo.csproj b/assets/Squidex.Assets.Mongo/Squidex.Assets.Mongo.csproj
index f8e8aaf..795903f 100644
--- a/assets/Squidex.Assets.Mongo/Squidex.Assets.Mongo.csproj
+++ b/assets/Squidex.Assets.Mongo/Squidex.Assets.Mongo.csproj
@@ -13,7 +13,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
@@ -21,7 +21,7 @@
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
diff --git a/assets/Squidex.Assets.ResizeService/ImageResizer.cs b/assets/Squidex.Assets.ResizeService/ImageResizer.cs
index 0fcb629..a6d4ef2 100644
--- a/assets/Squidex.Assets.ResizeService/ImageResizer.cs
+++ b/assets/Squidex.Assets.ResizeService/ImageResizer.cs
@@ -9,15 +9,8 @@
namespace Squidex.Assets.ResizeService;
-public sealed class ImageResizer
+public sealed class ImageResizer(IAssetThumbnailGenerator assetThumbnailGenerator)
{
- private readonly IAssetThumbnailGenerator assetThumbnailGenerator;
-
- public ImageResizer(IAssetThumbnailGenerator assetThumbnailGenerator)
- {
- this.assetThumbnailGenerator = assetThumbnailGenerator;
- }
-
public void Map(IEndpointRouteBuilder endpoints)
{
endpoints.MapPost("/blur", BlurAsync);
diff --git a/assets/Squidex.Assets.ResizeService/Squidex.Assets.ResizeService.csproj b/assets/Squidex.Assets.ResizeService/Squidex.Assets.ResizeService.csproj
index d12cdfb..5797a51 100644
--- a/assets/Squidex.Assets.ResizeService/Squidex.Assets.ResizeService.csproj
+++ b/assets/Squidex.Assets.ResizeService/Squidex.Assets.ResizeService.csproj
@@ -9,7 +9,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/assets/Squidex.Assets.ResizeService/Startup.cs b/assets/Squidex.Assets.ResizeService/Startup.cs
index 22efe0c..a1f8730 100644
--- a/assets/Squidex.Assets.ResizeService/Startup.cs
+++ b/assets/Squidex.Assets.ResizeService/Startup.cs
@@ -9,15 +9,8 @@
namespace Squidex.Assets.ResizeService;
-public sealed class Startup
+public sealed class Startup(IConfiguration configuration)
{
- private readonly IConfiguration configuration;
-
- public Startup(IConfiguration configuration)
- {
- this.configuration = configuration;
- }
-
public void ConfigureServices(IServiceCollection services)
{
var options = configuration.GetSection("images").Get()!;
diff --git a/assets/Squidex.Assets.S3/AmazonS3AssetStore.cs b/assets/Squidex.Assets.S3/AmazonS3AssetStore.cs
index 2325de8..0f295be 100644
--- a/assets/Squidex.Assets.S3/AmazonS3AssetStore.cs
+++ b/assets/Squidex.Assets.S3/AmazonS3AssetStore.cs
@@ -16,19 +16,14 @@
namespace Squidex.Assets;
-public sealed class AmazonS3AssetStore : IAssetStore, IInitializable
+public sealed class AmazonS3AssetStore(IOptions options) : IAssetStore, IInitializable
{
private const int BufferSize = 81920;
- private readonly AmazonS3AssetOptions options;
+ private readonly AmazonS3AssetOptions options = options.Value;
private TransferUtility s3Transfer;
private AmazonS3Client s3Client;
private bool canCopy = true;
- public AmazonS3AssetStore(IOptions options)
- {
- this.options = options.Value;
- }
-
public Task ReleaseAsync(
CancellationToken ct)
{
diff --git a/assets/Squidex.Assets.S3/Squidex.Assets.S3.csproj b/assets/Squidex.Assets.S3/Squidex.Assets.S3.csproj
index 28cd126..a83dcb3 100644
--- a/assets/Squidex.Assets.S3/Squidex.Assets.S3.csproj
+++ b/assets/Squidex.Assets.S3/Squidex.Assets.S3.csproj
@@ -13,8 +13,8 @@
-
-
+
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/assets/Squidex.Assets.Tests/AmazonS3AssetStoreTests.cs b/assets/Squidex.Assets.Tests/AmazonS3AssetStoreTests.cs
index a051a7e..0147038 100644
--- a/assets/Squidex.Assets.Tests/AmazonS3AssetStoreTests.cs
+++ b/assets/Squidex.Assets.Tests/AmazonS3AssetStoreTests.cs
@@ -13,14 +13,9 @@
namespace Squidex.Assets;
[Trait("Category", "Dependencies")]
-public class AmazonS3AssetStoreTests : AssetStoreTests, IClassFixture
+public class AmazonS3AssetStoreTests(AmazonS3AssetStoreFixture fixture) : AssetStoreTests, IClassFixture
{
- public AmazonS3AssetStoreFixture _ { get; }
-
- public AmazonS3AssetStoreTests(AmazonS3AssetStoreFixture fixture)
- {
- _ = fixture;
- }
+ public AmazonS3AssetStoreFixture _ { get; } = fixture;
public override AmazonS3AssetStore CreateStore()
{
diff --git a/assets/Squidex.Assets.Tests/AzureBlobAssetStoreTests.cs b/assets/Squidex.Assets.Tests/AzureBlobAssetStoreTests.cs
index 97eadfc..3371ef4 100644
--- a/assets/Squidex.Assets.Tests/AzureBlobAssetStoreTests.cs
+++ b/assets/Squidex.Assets.Tests/AzureBlobAssetStoreTests.cs
@@ -12,14 +12,9 @@
namespace Squidex.Assets;
[Trait("Category", "Dependencies")]
-public class AzureBlobAssetStoreTests : AssetStoreTests, IClassFixture
+public class AzureBlobAssetStoreTests(AzureBlobAssetStoreFixture fixture) : AssetStoreTests, IClassFixture
{
- public AzureBlobAssetStoreFixture _ { get; }
-
- public AzureBlobAssetStoreTests(AzureBlobAssetStoreFixture fixture)
- {
- _ = fixture;
- }
+ public AzureBlobAssetStoreFixture _ { get; } = fixture;
public override AzureBlobAssetStore CreateStore()
{
diff --git a/assets/Squidex.Assets.Tests/CloudflareR2Tests.cs b/assets/Squidex.Assets.Tests/CloudflareR2Tests.cs
index 30b344c..01c409d 100644
--- a/assets/Squidex.Assets.Tests/CloudflareR2Tests.cs
+++ b/assets/Squidex.Assets.Tests/CloudflareR2Tests.cs
@@ -13,14 +13,9 @@
namespace Squidex.Assets;
[Trait("Category", "Dependencies")]
-public class CloudflareR2Tests : AssetStoreTests, IClassFixture
+public class CloudflareR2Tests(CloudflareR2Fixture fixture) : AssetStoreTests, IClassFixture
{
- public CloudflareR2Fixture _ { get; }
-
- public CloudflareR2Tests(CloudflareR2Fixture fixture)
- {
- _ = fixture;
- }
+ public CloudflareR2Fixture _ { get; } = fixture;
public override AmazonS3AssetStore CreateStore()
{
diff --git a/assets/Squidex.Assets.Tests/FTPAssetStoreTests.cs b/assets/Squidex.Assets.Tests/FTPAssetStoreTests.cs
index ce70abb..d25f831 100644
--- a/assets/Squidex.Assets.Tests/FTPAssetStoreTests.cs
+++ b/assets/Squidex.Assets.Tests/FTPAssetStoreTests.cs
@@ -12,19 +12,14 @@
namespace Squidex.Assets;
[Trait("Category", "Dependencies")]
-public class FTPAssetStoreTests : AssetStoreTests, IClassFixture
+public class FTPAssetStoreTests(FTPAssetStoreFixture fixture) : AssetStoreTests, IClassFixture
{
- public FTPAssetStoreFixture _ { get; }
+ public FTPAssetStoreFixture _ { get; } = fixture;
protected override bool CanUploadStreamsWithoutLength => false;
protected override bool CanDeleteAssetsWithPrefix => false;
- public FTPAssetStoreTests(FTPAssetStoreFixture fixture)
- {
- _ = fixture;
- }
-
public override FTPAssetStore CreateStore()
{
return _.AssetStore;
diff --git a/assets/Squidex.Assets.Tests/FolderAssetStoreTests.cs b/assets/Squidex.Assets.Tests/FolderAssetStoreTests.cs
index 19bef61..a94793d 100644
--- a/assets/Squidex.Assets.Tests/FolderAssetStoreTests.cs
+++ b/assets/Squidex.Assets.Tests/FolderAssetStoreTests.cs
@@ -13,14 +13,9 @@
namespace Squidex.Assets;
-public class FolderAssetStoreTests : AssetStoreTests, IClassFixture
+public class FolderAssetStoreTests(FolderAssetStoreFixture fixture) : AssetStoreTests, IClassFixture
{
- public FolderAssetStoreFixture _ { get; }
-
- public FolderAssetStoreTests(FolderAssetStoreFixture fixture)
- {
- _ = fixture;
- }
+ public FolderAssetStoreFixture _ { get; } = fixture;
public override FolderAssetStore CreateStore()
{
diff --git a/assets/Squidex.Assets.Tests/GoogleCloudAssetStoreTests.cs b/assets/Squidex.Assets.Tests/GoogleCloudAssetStoreTests.cs
index f5c03f5..926983b 100644
--- a/assets/Squidex.Assets.Tests/GoogleCloudAssetStoreTests.cs
+++ b/assets/Squidex.Assets.Tests/GoogleCloudAssetStoreTests.cs
@@ -12,14 +12,9 @@
namespace Squidex.Assets;
[Trait("Category", "Dependencies")]
-public class GoogleCloudAssetStoreTests : AssetStoreTests, IClassFixture
+public class GoogleCloudAssetStoreTests(GoogleCloudAssetStoreFixture fixture) : AssetStoreTests, IClassFixture
{
- public GoogleCloudAssetStoreFixture _ { get; }
-
- public GoogleCloudAssetStoreTests(GoogleCloudAssetStoreFixture fixture)
- {
- _ = fixture;
- }
+ public GoogleCloudAssetStoreFixture _ { get; } = fixture;
public override GoogleCloudAssetStore CreateStore()
{
diff --git a/assets/Squidex.Assets.Tests/MongoGridFsAssetStoreTests.cs b/assets/Squidex.Assets.Tests/MongoGridFsAssetStoreTests.cs
index 6b8390d..3059243 100644
--- a/assets/Squidex.Assets.Tests/MongoGridFsAssetStoreTests.cs
+++ b/assets/Squidex.Assets.Tests/MongoGridFsAssetStoreTests.cs
@@ -12,14 +12,9 @@
namespace Squidex.Assets;
[Trait("Category", "Dependencies")]
-public class MongoGridFsAssetStoreTests : AssetStoreTests, IClassFixture
+public class MongoGridFsAssetStoreTests(MongoGridFSAssetStoreFixture fixture) : AssetStoreTests, IClassFixture
{
- public MongoGridFSAssetStoreFixture _ { get; }
-
- public MongoGridFsAssetStoreTests(MongoGridFSAssetStoreFixture fixture)
- {
- _ = fixture;
- }
+ public MongoGridFSAssetStoreFixture _ { get; } = fixture;
public override MongoGridFsAssetStore CreateStore()
{
diff --git a/assets/Squidex.Assets.Tests/PauseStream.cs b/assets/Squidex.Assets.Tests/PauseStream.cs
index 095ea11..9d64bf1 100644
--- a/assets/Squidex.Assets.Tests/PauseStream.cs
+++ b/assets/Squidex.Assets.Tests/PauseStream.cs
@@ -7,31 +7,25 @@
namespace Squidex.Assets;
-public class PauseStream : DelegateStream
+public class PauseStream(Stream innerStream, double pauseAfter) : DelegateStream(innerStream)
{
- private double pauseAfter = 1;
+ private double pauseTime = pauseAfter;
private int totalRead;
- public PauseStream(Stream innerStream, double pauseAfter)
- : base(innerStream)
- {
- this.pauseAfter = pauseAfter;
- }
-
public void Reset(double? newPauseAfter = null)
{
totalRead = 0;
if (newPauseAfter.HasValue)
{
- pauseAfter = newPauseAfter.Value;
+ pauseTime = newPauseAfter.Value;
}
}
public override async ValueTask ReadAsync(Memory buffer,
CancellationToken cancellationToken = default)
{
- if (totalRead >= Length * pauseAfter)
+ if (totalRead >= Length * pauseTime)
{
return 0;
}
diff --git a/assets/Squidex.Assets.Tests/Squidex.Assets.Tests.csproj b/assets/Squidex.Assets.Tests/Squidex.Assets.Tests.csproj
index 48c4a61..a32bcb7 100644
--- a/assets/Squidex.Assets.Tests/Squidex.Assets.Tests.csproj
+++ b/assets/Squidex.Assets.Tests/Squidex.Assets.Tests.csproj
@@ -31,15 +31,15 @@
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/assets/Squidex.Assets.Tests/TusController.cs b/assets/Squidex.Assets.Tests/TusController.cs
index 457c99e..8e5ea30 100644
--- a/assets/Squidex.Assets.Tests/TusController.cs
+++ b/assets/Squidex.Assets.Tests/TusController.cs
@@ -9,15 +9,8 @@
namespace Squidex.Assets;
-public class TusController : Controller
+public class TusController(AssetTusRunner runner) : Controller
{
- private readonly AssetTusRunner runner;
-
- public TusController(AssetTusRunner runner)
- {
- this.runner = runner;
- }
-
#pragma warning disable ASP0018 // Unused route parameter
[Route("files/controller/{**catchAll}")]
#pragma warning restore ASP0018 // Unused route parameter
diff --git a/assets/Squidex.Assets.TusAdapter/AssetTusFile.cs b/assets/Squidex.Assets.TusAdapter/AssetTusFile.cs
index 7279856..4598247 100644
--- a/assets/Squidex.Assets.TusAdapter/AssetTusFile.cs
+++ b/assets/Squidex.Assets.TusAdapter/AssetTusFile.cs
@@ -12,24 +12,28 @@
namespace Squidex.Assets;
-public sealed class AssetTusFile : IAssetFile, ITusFile, IAsyncDisposable, IDisposable
+public sealed class AssetTusFile(
+ string id,
+ TusMetadata tusMetadata,
+ Dictionary metadata,
+ Dictionary metadataRaw,
+ Stream stream,
+ Action disposed) : IAssetFile, ITusFile, IAsyncDisposable, IDisposable
{
- private readonly Stream stream;
- private readonly Action disposed;
- public string Id { get; }
+ public string Id { get; } = id;
- public string FileName { get; }
+ public string FileName { get; } = GetFileName(metadata);
- public string MimeType { get; }
+ public string MimeType { get; } = GetMimeType(metadata);
- public long FileSize { get; }
+ public long FileSize { get; } = stream.Length;
- public Dictionary Metadata { get; }
+ public Dictionary Metadata { get; } = metadata;
- public Dictionary MetadataRaw { get; }
+ public Dictionary MetadataRaw { get; } = metadataRaw;
- internal TusMetadata TusMetadata { get; }
+ internal TusMetadata TusMetadata { get; } = tusMetadata;
public static AssetTusFile Create(string id, TusMetadata tusMetadata, Stream stream, Action disposed)
{
@@ -45,29 +49,6 @@ public static AssetTusFile Create(string id, TusMetadata tusMetadata, Stream str
return new AssetTusFile(id, tusMetadata, metadata, metadataRaw, stream, disposed);
}
- public AssetTusFile(
- string id,
- TusMetadata tusMetadata,
- Dictionary metadata,
- Dictionary metadataRaw,
- Stream stream,
- Action disposed)
- {
- Id = id;
-
- this.stream = stream;
-
- FileSize = stream.Length;
- FileName = GetFileName(metadata);
- MimeType = GetMimeType(metadata);
-
- Metadata = metadata;
- MetadataRaw = metadataRaw;
- TusMetadata = tusMetadata;
-
- this.disposed = disposed;
- }
-
private static string GetFileName(Dictionary metadata)
{
var result = metadata.FirstOrDefault(x => string.Equals(x.Key, "fileName", StringComparison.OrdinalIgnoreCase)).Value;
diff --git a/assets/Squidex.Assets.TusAdapter/AssetTusStore.cs b/assets/Squidex.Assets.TusAdapter/AssetTusStore.cs
index 54ccbf2..9819317 100644
--- a/assets/Squidex.Assets.TusAdapter/AssetTusStore.cs
+++ b/assets/Squidex.Assets.TusAdapter/AssetTusStore.cs
@@ -14,7 +14,7 @@
namespace Squidex.Assets;
-public sealed class AssetTusStore :
+public sealed class AssetTusStore(IAssetStore assetStore, IAssetKeyValueStore keyValueStore) :
ITusExpirationStore,
ITusCreationDeferLengthStore,
ITusCreationStore,
@@ -24,14 +24,6 @@ public sealed class AssetTusStore :
{
private static readonly TimeSpan DefaultExpiration = TimeSpan.FromDays(2);
private readonly ConcurrentDictionary> files = new ConcurrentDictionary>();
- private readonly IAssetStore assetStore;
- private readonly IAssetKeyValueStore assetKeyValueStore;
-
- public AssetTusStore(IAssetStore assetStore, IAssetKeyValueStore keyValueStore)
- {
- this.assetStore = assetStore;
- this.assetKeyValueStore = keyValueStore;
- }
public async Task CreateFileAsync(long uploadLength, string metadata,
CancellationToken cancellationToken)
@@ -174,7 +166,7 @@ public async Task> GetExpiredFilesAsync(
{
var result = new List();
- var expirations = assetKeyValueStore.GetExpiredEntriesAsync(DateTimeOffset.UtcNow, cancellationToken);
+ var expirations = keyValueStore.GetExpiredEntriesAsync(DateTimeOffset.UtcNow, cancellationToken);
await foreach (var (_, value) in expirations.WithCancellation(cancellationToken))
{
@@ -221,7 +213,7 @@ public async Task GetUploadOffsetAsync(string fileId,
{
var key = Key(fileId);
- return await assetKeyValueStore.GetAsync(key, ct);
+ return await keyValueStore.GetAsync(key, ct);
}
public async Task RemoveExpiredFilesAsync(
@@ -229,7 +221,7 @@ public async Task RemoveExpiredFilesAsync(
{
var deletionCount = 0;
- var expirations = assetKeyValueStore.GetExpiredEntriesAsync(DateTimeOffset.UtcNow, cancellationToken);
+ var expirations = keyValueStore.GetExpiredEntriesAsync(DateTimeOffset.UtcNow, cancellationToken);
await foreach (var (_, expiration) in expirations.WithCancellation(cancellationToken))
{
@@ -260,7 +252,7 @@ private async Task CleanupAsync(TusMetadata metadata,
await assetStore.DeleteAsync(PartName(metadata.Id, i), cancellationToken);
}
- await assetKeyValueStore.DeleteAsync(Key(metadata.Id), cancellationToken);
+ await keyValueStore.DeleteAsync(Key(metadata.Id), cancellationToken);
}
private Task SetMetadataAsync(string fileId, TusMetadata metadata,
@@ -275,7 +267,7 @@ private Task SetMetadataAsync(string fileId, TusMetadata metadata,
metadata.Expires = DateTimeOffset.UtcNow.Add(DefaultExpiration);
}
- return assetKeyValueStore.SetAsync(key, metadata, metadata.Expires!.Value, ct);
+ return keyValueStore.SetAsync(key, metadata, metadata.Expires!.Value, ct);
}
private static string PartName(string fileId, int index)
diff --git a/assets/Squidex.Assets.TusAdapter/Internal/AssetFileLock.cs b/assets/Squidex.Assets.TusAdapter/Internal/AssetFileLock.cs
index c7b0099..e8f6a91 100644
--- a/assets/Squidex.Assets.TusAdapter/Internal/AssetFileLock.cs
+++ b/assets/Squidex.Assets.TusAdapter/Internal/AssetFileLock.cs
@@ -10,17 +10,9 @@
namespace Squidex.Assets.Internal;
-internal sealed class AssetFileLock : ITusFileLock
+internal sealed class AssetFileLock(IAssetStore assetStore, string fileId) : ITusFileLock
{
- private readonly IAssetStore assetStore;
- private readonly string filePath;
-
- public AssetFileLock(IAssetStore assetStore, string fileId)
- {
- this.assetStore = assetStore;
-
- filePath = $"locks/{fileId}.lock";
- }
+ private readonly string filePath = $"locks/{fileId}.lock";
public async Task Lock()
{
diff --git a/assets/Squidex.Assets.TusAdapter/Internal/AssetFileLockProvider.cs b/assets/Squidex.Assets.TusAdapter/Internal/AssetFileLockProvider.cs
index d928407..090bb96 100644
--- a/assets/Squidex.Assets.TusAdapter/Internal/AssetFileLockProvider.cs
+++ b/assets/Squidex.Assets.TusAdapter/Internal/AssetFileLockProvider.cs
@@ -9,15 +9,8 @@
namespace Squidex.Assets.Internal;
-public sealed class AssetFileLockProvider : ITusFileLockProvider
+public sealed class AssetFileLockProvider(IAssetStore assetStore) : ITusFileLockProvider
{
- private readonly IAssetStore assetStore;
-
- public AssetFileLockProvider(IAssetStore assetStore)
- {
- this.assetStore = assetStore;
- }
-
public Task AquireLock(string fileId)
{
return Task.FromResult(new AssetFileLock(assetStore, fileId));
diff --git a/assets/Squidex.Assets.TusAdapter/Internal/CancellableStream.cs b/assets/Squidex.Assets.TusAdapter/Internal/CancellableStream.cs
index 01a2ab5..77c0ad5 100644
--- a/assets/Squidex.Assets.TusAdapter/Internal/CancellableStream.cs
+++ b/assets/Squidex.Assets.TusAdapter/Internal/CancellableStream.cs
@@ -9,10 +9,9 @@
namespace Squidex.Assets.Internal;
-internal sealed class CancellableStream : DelegateStream
+internal sealed class CancellableStream(Stream innerStream,
+ CancellationToken cancellationToken) : DelegateStream(innerStream)
{
- private readonly CancellationToken cancellationToken;
-
public override long Length
{
get => throw new NotSupportedException();
@@ -23,13 +22,6 @@ public override bool CanWrite
get => false;
}
- public CancellableStream(Stream innerStream,
- CancellationToken cancellationToken)
- : base(innerStream)
- {
- this.cancellationToken = cancellationToken;
- }
-
public override int Read(byte[] buffer, int offset, int count)
{
if (cancellationToken.IsCancellationRequested)
diff --git a/assets/Squidex.Assets.TusAdapter/Squidex.Assets.TusAdapter.csproj b/assets/Squidex.Assets.TusAdapter/Squidex.Assets.TusAdapter.csproj
index e36bd4f..cb7dce6 100644
--- a/assets/Squidex.Assets.TusAdapter/Squidex.Assets.TusAdapter.csproj
+++ b/assets/Squidex.Assets.TusAdapter/Squidex.Assets.TusAdapter.csproj
@@ -13,7 +13,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/assets/Squidex.Assets.TusAdapter/TusActionResult.cs b/assets/Squidex.Assets.TusAdapter/TusActionResult.cs
index 3b30550..d33662b 100644
--- a/assets/Squidex.Assets.TusAdapter/TusActionResult.cs
+++ b/assets/Squidex.Assets.TusAdapter/TusActionResult.cs
@@ -10,21 +10,14 @@
namespace Squidex.Assets;
-internal sealed class TusActionResult : IActionResult
+internal sealed class TusActionResult(HttpResponse response) : IActionResult
{
- private readonly HttpResponse response;
-
public int StatusCode => response.StatusCode;
public IHeaderDictionary Headers => response.Headers;
public Stream Body => response.Body;
- public TusActionResult(HttpResponse response)
- {
- this.response = response;
- }
-
public void ApplyHeaders(HttpContext context)
{
foreach (var (key, value) in Headers)
diff --git a/assets/Squidex.Assets.TusClient/IProgressHandler.cs b/assets/Squidex.Assets.TusClient/IProgressHandler.cs
index 0ee8c5d..0a13065 100644
--- a/assets/Squidex.Assets.TusClient/IProgressHandler.cs
+++ b/assets/Squidex.Assets.TusClient/IProgressHandler.cs
@@ -9,65 +9,34 @@
namespace Squidex.Assets;
-public abstract class UploadEvent
+public abstract class UploadEvent(string fileId)
{
- public string FileId { get; }
-
- protected UploadEvent(string fileId)
- {
- FileId = fileId;
- }
+ public string FileId { get; } = fileId;
}
-public sealed class UploadProgressEvent : UploadEvent
+public sealed class UploadProgressEvent(string fileId, int progress, long bytesWritten, long bytesTotal) : UploadEvent(fileId)
{
- public int Progress { get; }
-
- public long BytesWritten { get; }
+ public int Progress { get; } = progress;
- public long BytesTotal { get; }
+ public long BytesWritten { get; } = bytesWritten;
- public UploadProgressEvent(string fileId, int progress, long bytesWritten, long bytesTotal)
- : base(fileId)
- {
- Progress = progress;
- BytesWritten = bytesWritten;
- BytesTotal = bytesTotal;
- }
+ public long BytesTotal { get; } = bytesTotal;
}
-public sealed class UploadCompletedEvent : UploadEvent
+public sealed class UploadCompletedEvent(string fileId, HttpResponseMessage response) : UploadEvent(fileId)
{
- public HttpResponseMessage Response { get; }
-
- public UploadCompletedEvent(string fileId, HttpResponseMessage response)
- : base(fileId)
- {
- Response = response;
- }
+ public HttpResponseMessage Response { get; } = response;
}
-public sealed class UploadCreatedEvent : UploadEvent
+public sealed class UploadCreatedEvent(string fileId) : UploadEvent(fileId)
{
- public UploadCreatedEvent(string fileId)
- : base(fileId)
- {
- }
}
-public sealed class UploadExceptionEvent : UploadEvent
+public sealed class UploadExceptionEvent(string fileId, Exception exception, HttpResponseMessage? response) : UploadEvent(fileId)
{
- public HttpResponseMessage? Response { get; }
-
- public Exception Exception { get; }
-
- public UploadExceptionEvent(string fileId, Exception exception, HttpResponseMessage? response)
- : base(fileId)
- {
- Exception = exception;
+ public HttpResponseMessage? Response { get; } = response;
- Response = response;
- }
+ public Exception Exception { get; } = exception;
}
public interface IProgressHandler
diff --git a/assets/Squidex.Assets.TusClient/Internal/ProgressableStreamContent.cs b/assets/Squidex.Assets.TusClient/Internal/ProgressableStreamContent.cs
index 5ae42c5..770fdc6 100644
--- a/assets/Squidex.Assets.TusClient/Internal/ProgressableStreamContent.cs
+++ b/assets/Squidex.Assets.TusClient/Internal/ProgressableStreamContent.cs
@@ -9,27 +9,15 @@
namespace Squidex.Assets.Internal;
-internal sealed class ProgressableStreamContent : HttpContent
+internal sealed class ProgressableStreamContent(Stream content, int uploadBufferSize, Func uploadProgress) : HttpContent
{
- private readonly Stream content;
- private readonly int uploadBufferSize;
- private readonly long uploadLength;
- private readonly Func uploadProgress;
+ private readonly long uploadLength = content.Length - content.Position;
public ProgressableStreamContent(Stream content, Func uploadProgress)
: this(content, 4096, uploadProgress)
{
}
- public ProgressableStreamContent(Stream content, int uploadBufferSize, Func uploadProgress)
- {
- this.content = content;
- this.uploadBufferSize = uploadBufferSize;
- this.uploadProgress = uploadProgress;
-
- uploadLength = content.Length - content.Position;
- }
-
protected override Task SerializeToStreamAsync(Stream stream, TransportContext? context)
{
return SerializeToStreamAsync(stream, default);
diff --git a/assets/Squidex.Assets.TusClient/Squidex.Assets.TusClient.csproj b/assets/Squidex.Assets.TusClient/Squidex.Assets.TusClient.csproj
index 7efee4c..767bac5 100644
--- a/assets/Squidex.Assets.TusClient/Squidex.Assets.TusClient.csproj
+++ b/assets/Squidex.Assets.TusClient/Squidex.Assets.TusClient.csproj
@@ -13,7 +13,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/assets/Squidex.Assets.TusClient/UploadFile.cs b/assets/Squidex.Assets.TusClient/UploadFile.cs
index f8f6183..4af74db 100644
--- a/assets/Squidex.Assets.TusClient/UploadFile.cs
+++ b/assets/Squidex.Assets.TusClient/UploadFile.cs
@@ -9,23 +9,15 @@
namespace Squidex.Assets;
-public sealed class UploadFile
+public sealed class UploadFile(Stream stream, string fileName, string contentType, long contentLength)
{
- public Stream Stream { get; }
+ public Stream Stream { get; } = stream;
- public string FileName { get; }
+ public string FileName { get; } = fileName;
- public string ContentType { get; }
+ public string ContentType { get; } = contentType;
- public long ContentLength { get; }
-
- public UploadFile(Stream stream, string fileName, string contentType, long contentLength)
- {
- Stream = stream;
- FileName = fileName;
- ContentType = contentType;
- ContentLength = contentLength;
- }
+ public long ContentLength { get; } = contentLength;
public static UploadFile FromFile(FileInfo fileInfo, string? mimeType = null)
{
diff --git a/assets/Squidex.Assets/AssetAlreadyExistsException.cs b/assets/Squidex.Assets/AssetAlreadyExistsException.cs
index 721d0bc..bed8b53 100644
--- a/assets/Squidex.Assets/AssetAlreadyExistsException.cs
+++ b/assets/Squidex.Assets/AssetAlreadyExistsException.cs
@@ -8,13 +8,8 @@
namespace Squidex.Assets;
[Serializable]
-public class AssetAlreadyExistsException : Exception
+public class AssetAlreadyExistsException(string fileName, Exception? inner = null) : Exception(FormatMessage(fileName), inner)
{
- public AssetAlreadyExistsException(string fileName, Exception? inner = null)
- : base(FormatMessage(fileName), inner)
- {
- }
-
private static string FormatMessage(string fileName)
{
ArgumentException.ThrowIfNullOrWhiteSpace(fileName);
diff --git a/assets/Squidex.Assets/AssetNotFoundException.cs b/assets/Squidex.Assets/AssetNotFoundException.cs
index 024651c..f3a33ff 100644
--- a/assets/Squidex.Assets/AssetNotFoundException.cs
+++ b/assets/Squidex.Assets/AssetNotFoundException.cs
@@ -8,13 +8,8 @@
namespace Squidex.Assets;
[Serializable]
-public class AssetNotFoundException : Exception
+public class AssetNotFoundException(string fileName, Exception? inner = null) : Exception(FormatMessage(fileName), inner)
{
- public AssetNotFoundException(string fileName, Exception? inner = null)
- : base(FormatMessage(fileName), inner)
- {
- }
-
private static string FormatMessage(string fileName)
{
ArgumentException.ThrowIfNullOrWhiteSpace(fileName);
diff --git a/assets/Squidex.Assets/BytesRange.cs b/assets/Squidex.Assets/BytesRange.cs
index 9129bf0..5c0af9c 100644
--- a/assets/Squidex.Assets/BytesRange.cs
+++ b/assets/Squidex.Assets/BytesRange.cs
@@ -7,11 +7,11 @@
namespace Squidex.Assets;
-public readonly struct BytesRange
+public readonly struct BytesRange(long? from, long? to)
{
- public readonly long? From;
+ public readonly long? From = from;
- public readonly long? To;
+ public readonly long? To = to;
public long Length
{
@@ -38,13 +38,6 @@ public bool IsDefined
get { return (From >= 0 || To >= 0) && Length > 0; }
}
- public BytesRange(long? from, long? to)
- {
- From = from;
-
- To = to;
- }
-
public override string? ToString()
{
if (Length == 0)
diff --git a/assets/Squidex.Assets/FolderAssetStore.cs b/assets/Squidex.Assets/FolderAssetStore.cs
index d910697..0ebacfe 100644
--- a/assets/Squidex.Assets/FolderAssetStore.cs
+++ b/assets/Squidex.Assets/FolderAssetStore.cs
@@ -11,18 +11,10 @@
namespace Squidex.Assets;
-public sealed class FolderAssetStore : IAssetStore, IInitializable
+public sealed class FolderAssetStore(IOptions options, ILogger log) : IAssetStore, IInitializable
{
private const int BufferSize = 81920;
- private readonly ILogger log;
- private readonly DirectoryInfo directory;
-
- public FolderAssetStore(IOptions options, ILogger log)
- {
- this.log = log;
-
- directory = new DirectoryInfo(options.Value.Path);
- }
+ private readonly DirectoryInfo directory = new DirectoryInfo(options.Value.Path);
public Task InitializeAsync(
CancellationToken ct)
diff --git a/assets/Squidex.Assets/Remote/RemoteThumbnailGenerator.cs b/assets/Squidex.Assets/Remote/RemoteThumbnailGenerator.cs
index ef46eb2..574c959 100644
--- a/assets/Squidex.Assets/Remote/RemoteThumbnailGenerator.cs
+++ b/assets/Squidex.Assets/Remote/RemoteThumbnailGenerator.cs
@@ -11,18 +11,8 @@
namespace Squidex.Assets.Remote;
-public sealed class RemoteThumbnailGenerator : AssetThumbnailGeneratorBase
+public sealed class RemoteThumbnailGenerator(IHttpClientFactory httpClientFactory, IAssetThumbnailGenerator inner) : AssetThumbnailGeneratorBase
{
- private readonly IHttpClientFactory httpClientFactory;
- private readonly IAssetThumbnailGenerator inner;
-
- public RemoteThumbnailGenerator(IHttpClientFactory httpClientFactory, IAssetThumbnailGenerator inner)
- {
- this.httpClientFactory = httpClientFactory;
-
- this.inner = inner;
- }
-
public override bool CanReadAndWrite(string mimeType)
{
return inner.CanReadAndWrite(mimeType);
diff --git a/assets/Squidex.Assets/Squidex.Assets.csproj b/assets/Squidex.Assets/Squidex.Assets.csproj
index 69ac9a3..079d806 100644
--- a/assets/Squidex.Assets/Squidex.Assets.csproj
+++ b/assets/Squidex.Assets/Squidex.Assets.csproj
@@ -12,19 +12,19 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
diff --git a/assets/TusTestServer/Controller/TusController.cs b/assets/TusTestServer/Controller/TusController.cs
index 999637a..ada8145 100644
--- a/assets/TusTestServer/Controller/TusController.cs
+++ b/assets/TusTestServer/Controller/TusController.cs
@@ -10,16 +10,10 @@
namespace TusTestServer.Controller;
-public class TusController : ControllerBase
+public class TusController(AssetTusRunner runner) : ControllerBase
{
- private readonly AssetTusRunner runner;
private readonly Uri uploadUri = new Uri("http://localhost:4000/files/controller");
- public TusController(AssetTusRunner runner)
- {
- this.runner = runner;
- }
-
[Route("/upload")]
public async Task UploadAsync()
{
@@ -136,11 +130,11 @@ public Task OnFailedAsync(UploadExceptionEvent @event,
}
}
- public class PauseStream : DelegateStream
+ public class PauseStream(Stream innerStream, double pauseAfter) : DelegateStream(innerStream)
{
- private readonly int maxLength;
+ private readonly int maxLength = (int)Math.Floor(innerStream.Length * pauseAfter) + 1;
private long totalRead;
- private long totalRemaining;
+ private long totalRemaining = innerStream.Length;
private long seekStart;
public override long Length
@@ -154,14 +148,6 @@ public override long Position
set => throw new NotSupportedException();
}
- public PauseStream(Stream innerStream, double pauseAfter)
- : base(innerStream)
- {
- maxLength = (int)Math.Floor(innerStream.Length * pauseAfter) + 1;
-
- totalRemaining = innerStream.Length;
- }
-
public override long Seek(long offset, SeekOrigin origin)
{
var position = seekStart = base.Seek(offset, origin);
diff --git a/assets/TusTestServer/TusTestServer.csproj b/assets/TusTestServer/TusTestServer.csproj
index 441ffd0..96478ea 100644
--- a/assets/TusTestServer/TusTestServer.csproj
+++ b/assets/TusTestServer/TusTestServer.csproj
@@ -9,11 +9,11 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
diff --git a/caching/Squidex.Caching.Tests/Squidex.Caching.Tests.csproj b/caching/Squidex.Caching.Tests/Squidex.Caching.Tests.csproj
index 8c089b8..a90556e 100644
--- a/caching/Squidex.Caching.Tests/Squidex.Caching.Tests.csproj
+++ b/caching/Squidex.Caching.Tests/Squidex.Caching.Tests.csproj
@@ -11,13 +11,13 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
-
-
+
+
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/caching/Squidex.Caching/AsyncLocalCleaner.cs b/caching/Squidex.Caching/AsyncLocalCleaner.cs
index ef69252..aee29eb 100644
--- a/caching/Squidex.Caching/AsyncLocalCleaner.cs
+++ b/caching/Squidex.Caching/AsyncLocalCleaner.cs
@@ -7,15 +7,8 @@
namespace Squidex.Caching;
-internal sealed class AsyncLocalCleaner : IDisposable
+internal sealed class AsyncLocalCleaner(AsyncLocal asyncLocal) : IDisposable
{
- private readonly AsyncLocal asyncLocal;
-
- public AsyncLocalCleaner(AsyncLocal asyncLocal)
- {
- this.asyncLocal = asyncLocal;
- }
-
public void Dispose()
{
asyncLocal.Value = default!;
diff --git a/caching/Squidex.Caching/BackgroundCache.cs b/caching/Squidex.Caching/BackgroundCache.cs
index a64e4a6..8caf0fe 100644
--- a/caching/Squidex.Caching/BackgroundCache.cs
+++ b/caching/Squidex.Caching/BackgroundCache.cs
@@ -17,18 +17,11 @@ public sealed class BackgroundCache : IBackgroundCache
private readonly ConcurrentDictionary
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
-
-
+
+
all
diff --git a/hosting/Squidex.Hosting.Abstractions/Configuration/ConfigurationException.cs b/hosting/Squidex.Hosting.Abstractions/Configuration/ConfigurationException.cs
index efebe71..bf63f60 100644
--- a/hosting/Squidex.Hosting.Abstractions/Configuration/ConfigurationException.cs
+++ b/hosting/Squidex.Hosting.Abstractions/Configuration/ConfigurationException.cs
@@ -10,21 +10,15 @@
namespace Squidex.Hosting.Configuration;
[Serializable]
-public class ConfigurationException : Exception
+public class ConfigurationException(IReadOnlyList errors, Exception? inner = null) : Exception(FormatMessage(errors), inner)
{
- public IReadOnlyList Errors { get; }
+ public IReadOnlyList Errors { get; } = errors;
public ConfigurationException(ConfigurationError error, Exception? inner = null)
: this([error], inner)
{
}
- public ConfigurationException(IReadOnlyList errors, Exception? inner = null)
- : base(FormatMessage(errors), inner)
- {
- Errors = errors;
- }
-
private static string FormatMessage(IReadOnlyList errors)
{
ArgumentNullException.ThrowIfNull(errors);
diff --git a/hosting/Squidex.Hosting.Abstractions/Configuration/OptionsErrorProvider.cs b/hosting/Squidex.Hosting.Abstractions/Configuration/OptionsErrorProvider.cs
index 36c2a6f..ba244b5 100644
--- a/hosting/Squidex.Hosting.Abstractions/Configuration/OptionsErrorProvider.cs
+++ b/hosting/Squidex.Hosting.Abstractions/Configuration/OptionsErrorProvider.cs
@@ -10,17 +10,8 @@
namespace Squidex.Hosting.Configuration;
-public sealed class OptionsErrorProvider : IErrorProvider, IValidateOptions where T : class, IValidatableOptions
+public sealed class OptionsErrorProvider(IOptions options, string prefix) : IErrorProvider, IValidateOptions where T : class, IValidatableOptions
{
- private readonly IOptions options;
- private readonly string prefix;
-
- public OptionsErrorProvider(IOptions options, string prefix)
- {
- this.options = options;
- this.prefix = prefix;
- }
-
public IEnumerable GetErrors()
{
return GetErrors(options.Value);
diff --git a/hosting/Squidex.Hosting.Abstractions/Configuration/ValidationInitializer.cs b/hosting/Squidex.Hosting.Abstractions/Configuration/ValidationInitializer.cs
index 3501674..7e42bec 100644
--- a/hosting/Squidex.Hosting.Abstractions/Configuration/ValidationInitializer.cs
+++ b/hosting/Squidex.Hosting.Abstractions/Configuration/ValidationInitializer.cs
@@ -7,17 +7,10 @@
namespace Squidex.Hosting.Configuration;
-public sealed class ValidationInitializer : IInitializable
+public sealed class ValidationInitializer(IEnumerable errorProviders) : IInitializable
{
- private readonly IEnumerable errorProviders;
-
public int Order => int.MinValue;
- public ValidationInitializer(IEnumerable errorProviders)
- {
- this.errorProviders = errorProviders;
- }
-
public Task InitializeAsync(
CancellationToken ct)
{
diff --git a/hosting/Squidex.Hosting.Abstractions/Squidex.Hosting.Abstractions.csproj b/hosting/Squidex.Hosting.Abstractions/Squidex.Hosting.Abstractions.csproj
index 3438633..351314c 100644
--- a/hosting/Squidex.Hosting.Abstractions/Squidex.Hosting.Abstractions.csproj
+++ b/hosting/Squidex.Hosting.Abstractions/Squidex.Hosting.Abstractions.csproj
@@ -13,13 +13,13 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
diff --git a/hosting/Squidex.Hosting.TestRunner/EmbedMiddleware.cs b/hosting/Squidex.Hosting.TestRunner/EmbedMiddleware.cs
index 68a3594..836bb39 100644
--- a/hosting/Squidex.Hosting.TestRunner/EmbedMiddleware.cs
+++ b/hosting/Squidex.Hosting.TestRunner/EmbedMiddleware.cs
@@ -7,15 +7,8 @@
namespace Squidex.Hosting;
-public sealed class EmbedMiddleware
+public sealed class EmbedMiddleware(RequestDelegate next)
{
- private readonly RequestDelegate next;
-
- public EmbedMiddleware(RequestDelegate next)
- {
- this.next = next;
- }
-
public Task InvokeAsync(HttpContext context)
{
var request = context.Request;
diff --git a/hosting/Squidex.Hosting.TestRunner/Squidex.Hosting.TestRunner.csproj b/hosting/Squidex.Hosting.TestRunner/Squidex.Hosting.TestRunner.csproj
index 1213edf..632f540 100644
--- a/hosting/Squidex.Hosting.TestRunner/Squidex.Hosting.TestRunner.csproj
+++ b/hosting/Squidex.Hosting.TestRunner/Squidex.Hosting.TestRunner.csproj
@@ -8,7 +8,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/hosting/Squidex.Hosting.TestRunner/Startup.cs b/hosting/Squidex.Hosting.TestRunner/Startup.cs
index c3cf13b..bb11d83 100644
--- a/hosting/Squidex.Hosting.TestRunner/Startup.cs
+++ b/hosting/Squidex.Hosting.TestRunner/Startup.cs
@@ -11,15 +11,8 @@
namespace Squidex.Hosting;
-public sealed class Startup
+public sealed class Startup(IConfiguration configuration)
{
- private readonly IConfiguration configuration;
-
- public Startup(IConfiguration configuration)
- {
- this.configuration = configuration;
- }
-
public void ConfigureServices(IServiceCollection services)
{
services.AddSingletonAs(_ => JsonLogWriterFactory.Readable())
diff --git a/hosting/Squidex.Hosting.Tests/ServiceRegistrationTests.cs b/hosting/Squidex.Hosting.Tests/ServiceRegistrationTests.cs
index 2f1ca0d..e1558b3 100644
--- a/hosting/Squidex.Hosting.Tests/ServiceRegistrationTests.cs
+++ b/hosting/Squidex.Hosting.Tests/ServiceRegistrationTests.cs
@@ -30,14 +30,9 @@ private sealed class ServiceWrapped : IWrapped, IInterface1, IInterface2
public IWrapped? Inner => null;
}
- private sealed class ServiceWrapper : IWrapped
+ private sealed class ServiceWrapper(ServiceRegistrationTests.IWrapped inner) : IWrapped
{
- public IWrapped? Inner { get; }
-
- public ServiceWrapper(IWrapped inner)
- {
- Inner = inner;
- }
+ public IWrapped? Inner { get; } = inner;
}
[Fact]
diff --git a/hosting/Squidex.Hosting.Tests/Squidex.Hosting.Tests.csproj b/hosting/Squidex.Hosting.Tests/Squidex.Hosting.Tests.csproj
index 44d5f5c..492d36f 100644
--- a/hosting/Squidex.Hosting.Tests/Squidex.Hosting.Tests.csproj
+++ b/hosting/Squidex.Hosting.Tests/Squidex.Hosting.Tests.csproj
@@ -14,17 +14,17 @@
runtime; build; native; contentfiles; analyzers; buildtransitive
all
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
runtime; build; native; contentfiles; analyzers; buildtransitive
all
diff --git a/hosting/Squidex.Hosting/BackgroundHost.cs b/hosting/Squidex.Hosting/BackgroundHost.cs
index 89b75cc..f48fbbe 100644
--- a/hosting/Squidex.Hosting/BackgroundHost.cs
+++ b/hosting/Squidex.Hosting/BackgroundHost.cs
@@ -10,13 +10,8 @@
namespace Squidex.Hosting;
-public sealed class BackgroundHost : SystemHost, IHostedService
+public sealed class BackgroundHost(ISemanticLog log, IEnumerable systems) : SystemHost(log, systems), IHostedService
{
- public BackgroundHost(ISemanticLog log, IEnumerable systems)
- : base(log, systems)
- {
- }
-
public async Task StartAsync(
CancellationToken cancellationToken)
{
diff --git a/hosting/Squidex.Hosting/DelegateInitializer.cs b/hosting/Squidex.Hosting/DelegateInitializer.cs
index 88e24c3..d728570 100644
--- a/hosting/Squidex.Hosting/DelegateInitializer.cs
+++ b/hosting/Squidex.Hosting/DelegateInitializer.cs
@@ -7,25 +7,12 @@
namespace Squidex.Hosting;
-public sealed class DelegateInitializer : IInitializable
+public sealed class DelegateInitializer(IServiceProvider serviceProvider, string name, int order, Func action) : IInitializable
{
- private readonly IServiceProvider serviceProvider;
- private readonly string name;
- private readonly int order;
- private readonly Func action;
-
public string Name => name;
public int Order => order;
- public DelegateInitializer(IServiceProvider serviceProvider, string name, int order, Func action)
- {
- this.serviceProvider = serviceProvider;
- this.name = name;
- this.order = order;
- this.action = action;
- }
-
public Task InitializeAsync(
CancellationToken ct)
{
diff --git a/hosting/Squidex.Hosting/DelegateInitializer{T}.cs b/hosting/Squidex.Hosting/DelegateInitializer{T}.cs
index eb300dc..431e110 100644
--- a/hosting/Squidex.Hosting/DelegateInitializer{T}.cs
+++ b/hosting/Squidex.Hosting/DelegateInitializer{T}.cs
@@ -9,25 +9,12 @@
namespace Squidex.Hosting;
-public sealed class DelegateInitializer : IInitializable where T : class
+public sealed class DelegateInitializer(IServiceProvider serviceProvider, string name, int order, Func action) : IInitializable where T : class
{
- private readonly IServiceProvider serviceProvider;
- private readonly string name;
- private readonly int order;
- private readonly Func action;
-
public string Name => name;
public int Order => order;
- public DelegateInitializer(IServiceProvider serviceProvider, string name, int order, Func action)
- {
- this.serviceProvider = serviceProvider;
- this.name = name;
- this.order = order;
- this.action = action;
- }
-
public Task InitializeAsync(
CancellationToken ct)
{
diff --git a/hosting/Squidex.Hosting/InitializerHost.cs b/hosting/Squidex.Hosting/InitializerHost.cs
index 1d5bdd9..5be72d4 100644
--- a/hosting/Squidex.Hosting/InitializerHost.cs
+++ b/hosting/Squidex.Hosting/InitializerHost.cs
@@ -10,13 +10,8 @@
namespace Squidex.Hosting;
-public sealed class InitializerHost : SystemHost, IHostedService
+public sealed class InitializerHost(ISemanticLog log, IEnumerable systems) : SystemHost(log, systems), IHostedService
{
- public InitializerHost(ISemanticLog log, IEnumerable systems)
- : base(log, systems)
- {
- }
-
public async Task StartAsync(
CancellationToken cancellationToken)
{
diff --git a/hosting/Squidex.Hosting/Squidex.Hosting.csproj b/hosting/Squidex.Hosting/Squidex.Hosting.csproj
index 73efc6f..5f30a2f 100644
--- a/hosting/Squidex.Hosting/Squidex.Hosting.csproj
+++ b/hosting/Squidex.Hosting/Squidex.Hosting.csproj
@@ -16,7 +16,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/hosting/Squidex.Hosting/SystemHost.cs b/hosting/Squidex.Hosting/SystemHost.cs
index 713dcfd..ccc2f38 100644
--- a/hosting/Squidex.Hosting/SystemHost.cs
+++ b/hosting/Squidex.Hosting/SystemHost.cs
@@ -9,23 +9,16 @@
namespace Squidex.Hosting;
-public abstract class SystemHost where T : ISystem
+public abstract class SystemHost(ISemanticLog log, IEnumerable systems) where T : ISystem
{
- protected IReadOnlyList<(T System, string Name)> Systems { get; }
-
- protected ISemanticLog Log { get; }
-
- protected SystemHost(ISemanticLog log, IEnumerable systems)
- {
- Log = log;
-
- Systems =
+ protected IReadOnlyList<(T System, string Name)> Systems { get; } =
systems.Distinct()
.Select(x => (System: x, Name: GetName(x)))
.OrderBy(x => x.System.Order)
.ThenBy(x => x.Name)
.ToList();
- }
+
+ protected ISemanticLog Log { get; } = log;
private static string GetName(T system)
{
diff --git a/hosting/Squidex.Hosting/Web/CleanupHostMiddleware.cs b/hosting/Squidex.Hosting/Web/CleanupHostMiddleware.cs
index 81165c5..eedab3d 100644
--- a/hosting/Squidex.Hosting/Web/CleanupHostMiddleware.cs
+++ b/hosting/Squidex.Hosting/Web/CleanupHostMiddleware.cs
@@ -9,15 +9,8 @@
namespace Squidex.Hosting.Web;
-public sealed class CleanupHostMiddleware
+public sealed class CleanupHostMiddleware(RequestDelegate next)
{
- private readonly RequestDelegate next;
-
- public CleanupHostMiddleware(RequestDelegate next)
- {
- this.next = next;
- }
-
public Task InvokeAsync(HttpContext context)
{
var request = context.Request;
diff --git a/hosting/Squidex.Hosting/Web/ConfigureForwardedHeaders.cs b/hosting/Squidex.Hosting/Web/ConfigureForwardedHeaders.cs
index 5919945..8396df8 100644
--- a/hosting/Squidex.Hosting/Web/ConfigureForwardedHeaders.cs
+++ b/hosting/Squidex.Hosting/Web/ConfigureForwardedHeaders.cs
@@ -12,16 +12,9 @@
namespace Squidex.Hosting.Web;
-public sealed class ConfigureForwardedHeaders : IConfigureOptions
+public sealed class ConfigureForwardedHeaders(IOptions urlOptions, IUrlGenerator urlGenerator) : IConfigureOptions
{
- private readonly UrlOptions urlOptions;
- private readonly IUrlGenerator urlGenerator;
-
- public ConfigureForwardedHeaders(IOptions urlOptions, IUrlGenerator urlGenerator)
- {
- this.urlOptions = urlOptions.Value;
- this.urlGenerator = urlGenerator;
- }
+ private readonly UrlOptions urlOptions = urlOptions.Value;
public void Configure(ForwardedHeadersOptions options)
{
diff --git a/hosting/Squidex.Hosting/Web/ConfigureHttpsRedirection.cs b/hosting/Squidex.Hosting/Web/ConfigureHttpsRedirection.cs
index 7ae05ed..0d47142 100644
--- a/hosting/Squidex.Hosting/Web/ConfigureHttpsRedirection.cs
+++ b/hosting/Squidex.Hosting/Web/ConfigureHttpsRedirection.cs
@@ -10,14 +10,9 @@
namespace Squidex.Hosting.Web;
-public sealed class ConfigureHttpsRedirection : IConfigureOptions
+public sealed class ConfigureHttpsRedirection(IOptions urlOptions) : IConfigureOptions
{
- private readonly UrlOptions urlOptions;
-
- public ConfigureHttpsRedirection(IOptions urlOptions)
- {
- this.urlOptions = urlOptions.Value;
- }
+ private readonly UrlOptions urlOptions = urlOptions.Value;
public void Configure(HttpsRedirectionOptions options)
{
diff --git a/hosting/Squidex.Hosting/Web/HtmlTransformMiddleware.cs b/hosting/Squidex.Hosting/Web/HtmlTransformMiddleware.cs
index 001bc52..5a13b37 100644
--- a/hosting/Squidex.Hosting/Web/HtmlTransformMiddleware.cs
+++ b/hosting/Squidex.Hosting/Web/HtmlTransformMiddleware.cs
@@ -11,22 +11,12 @@
namespace Squidex.Hosting.Web;
-public sealed class HtmlTransformMiddleware
+public sealed class HtmlTransformMiddleware(HtmlTransformOptions options, RequestDelegate next)
{
- private readonly HtmlTransformOptions options;
- private readonly RequestDelegate next;
-
- public HtmlTransformMiddleware(HtmlTransformOptions options, RequestDelegate next)
- {
- this.options = options;
- this.next = next;
- }
-
- private sealed class BufferStream : Stream
+ private sealed class BufferStream(HttpContext context) : Stream
{
private static readonly RecyclableMemoryStreamManager Buffers = new RecyclableMemoryStreamManager();
- private readonly Stream originalBody;
- private readonly HttpContext context;
+ private readonly Stream originalBody = context.Response.Body;
private bool writingStarted;
private MemoryStream? memoryStream;
@@ -45,14 +35,6 @@ private Stream ActualStream
get => memoryStream ?? originalBody;
}
- public BufferStream(HttpContext context)
- {
- this.context = context;
-
- // Keep an instance of the original body, because the body will be replaced later.
- this.originalBody = context.Response.Body;
- }
-
public async Task CompleteAsync(HtmlTransformOptions options)
{
if (memoryStream == null || memoryStream.Length == 0)
@@ -85,7 +67,7 @@ public async Task CompleteAsync(HtmlTransformOptions options)
}
finally
{
- this.context.Response.Body = originalBody;
+ context.Response.Body = originalBody;
}
}
diff --git a/log/Squidex.Log.Tests/Squidex.Log.Tests.csproj b/log/Squidex.Log.Tests/Squidex.Log.Tests.csproj
index ba9f3bd..d77c008 100644
--- a/log/Squidex.Log.Tests/Squidex.Log.Tests.csproj
+++ b/log/Squidex.Log.Tests/Squidex.Log.Tests.csproj
@@ -15,14 +15,14 @@
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/log/Squidex.Log/Adapter/CategoryNameAppender.cs b/log/Squidex.Log/Adapter/CategoryNameAppender.cs
index a870102..f00e57a 100644
--- a/log/Squidex.Log/Adapter/CategoryNameAppender.cs
+++ b/log/Squidex.Log/Adapter/CategoryNameAppender.cs
@@ -7,15 +7,8 @@
namespace Squidex.Log.Adapter;
-public sealed class CategoryNameAppender : ILogAppender
+public sealed class CategoryNameAppender(string category) : ILogAppender
{
- private readonly string category;
-
- public CategoryNameAppender(string category)
- {
- this.category = category;
- }
-
public void Append(IObjectWriter writer, SemanticLogLevel logLevel, Exception? exception)
{
writer.WriteProperty(nameof(category), category);
diff --git a/log/Squidex.Log/Adapter/SemanticLogLogger.cs b/log/Squidex.Log/Adapter/SemanticLogLogger.cs
index 6fe585c..b911390 100644
--- a/log/Squidex.Log/Adapter/SemanticLogLogger.cs
+++ b/log/Squidex.Log/Adapter/SemanticLogLogger.cs
@@ -10,15 +10,8 @@
namespace Squidex.Log.Adapter;
-internal sealed class SemanticLogLogger : ILogger
+internal sealed class SemanticLogLogger(ISemanticLog semanticLog) : ILogger
{
- private readonly ISemanticLog semanticLog;
-
- public SemanticLogLogger(ISemanticLog semanticLog)
- {
- this.semanticLog = semanticLog;
- }
-
public void Log(LogLevel logLevel, EventId eventId, TState state, Exception? exception, Func formatter)
{
SemanticLogLevel semanticLogLevel;
diff --git a/log/Squidex.Log/ConsoleLogChannel.cs b/log/Squidex.Log/ConsoleLogChannel.cs
index 771b660..0466d28 100644
--- a/log/Squidex.Log/ConsoleLogChannel.cs
+++ b/log/Squidex.Log/ConsoleLogChannel.cs
@@ -9,15 +9,9 @@
namespace Squidex.Log;
-public sealed class ConsoleLogChannel : ILogChannel, IDisposable
+public sealed class ConsoleLogChannel(bool useColors = false) : ILogChannel, IDisposable
{
private readonly ConsoleLogProcessor processor = new ConsoleLogProcessor();
- private readonly bool useColors;
-
- public ConsoleLogChannel(bool useColors = false)
- {
- this.useColors = useColors;
- }
public void Dispose()
{
diff --git a/log/Squidex.Log/Internal/AnsiLogConsole.cs b/log/Squidex.Log/Internal/AnsiLogConsole.cs
index b6638b2..3ccb7d8 100644
--- a/log/Squidex.Log/Internal/AnsiLogConsole.cs
+++ b/log/Squidex.Log/Internal/AnsiLogConsole.cs
@@ -10,15 +10,8 @@
namespace Squidex.Log.Internal;
[ExcludeFromCodeCoverage]
-public sealed class AnsiLogConsole : IConsole
+public sealed class AnsiLogConsole(bool logToStdError) : IConsole
{
- private readonly bool logToStdError;
-
- public AnsiLogConsole(bool logToStdError)
- {
- this.logToStdError = logToStdError;
- }
-
public void Reset()
{
}
diff --git a/log/Squidex.Log/Internal/WindowsLogConsole.cs b/log/Squidex.Log/Internal/WindowsLogConsole.cs
index 06d4509..d1948fb 100644
--- a/log/Squidex.Log/Internal/WindowsLogConsole.cs
+++ b/log/Squidex.Log/Internal/WindowsLogConsole.cs
@@ -10,15 +10,8 @@
namespace Squidex.Log.Internal;
[ExcludeFromCodeCoverage]
-public sealed class WindowsLogConsole : IConsole
+public sealed class WindowsLogConsole(bool logToStdError) : IConsole
{
- private readonly bool logToStdError;
-
- public WindowsLogConsole(bool logToStdError)
- {
- this.logToStdError = logToStdError;
- }
-
public void Reset()
{
Console.ResetColor();
diff --git a/log/Squidex.Log/JsonLogWriterFactory.cs b/log/Squidex.Log/JsonLogWriterFactory.cs
index 8294c8c..05e78d9 100644
--- a/log/Squidex.Log/JsonLogWriterFactory.cs
+++ b/log/Squidex.Log/JsonLogWriterFactory.cs
@@ -10,9 +10,9 @@
namespace Squidex.Log;
-public sealed class JsonLogWriterFactory : IRootWriterFactory
+public sealed class JsonLogWriterFactory(bool indended = false, bool formatLine = false) : IRootWriterFactory
{
- private readonly ObjectPool writerPool;
+ private readonly ObjectPool writerPool = new DefaultObjectPoolProvider().Create(new JsonLogWriterPolicy(indended, formatLine));
internal sealed class JsonLogWriterPolicy : PooledObjectPolicy
{
@@ -45,11 +45,6 @@ public override bool Return(JsonLogWriter obj)
}
}
- public JsonLogWriterFactory(bool indended = false, bool formatLine = false)
- {
- writerPool = new DefaultObjectPoolProvider().Create(new JsonLogWriterPolicy(indended, formatLine));
- }
-
public static JsonLogWriterFactory Default()
{
return new JsonLogWriterFactory();
diff --git a/log/Squidex.Log/Squidex.Log.csproj b/log/Squidex.Log/Squidex.Log.csproj
index 7d0769f..80b2e50 100644
--- a/log/Squidex.Log/Squidex.Log.csproj
+++ b/log/Squidex.Log/Squidex.Log.csproj
@@ -12,12 +12,12 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
-
+
+
all
diff --git a/log/Squidex.Log/TimestampLogAppender.cs b/log/Squidex.Log/TimestampLogAppender.cs
index 4734421..4bc3761 100644
--- a/log/Squidex.Log/TimestampLogAppender.cs
+++ b/log/Squidex.Log/TimestampLogAppender.cs
@@ -7,20 +7,15 @@
namespace Squidex.Log;
-public sealed class TimestampLogAppender : ILogAppender
+public sealed class TimestampLogAppender(Func? clock = null) : ILogAppender
{
- private readonly Func clock;
+ private readonly Func clock = clock ?? (() => DateTime.UtcNow);
public TimestampLogAppender()
: this(null)
{
}
- public TimestampLogAppender(Func? clock = null)
- {
- this.clock = clock ?? (() => DateTime.UtcNow);
- }
-
public void Append(IObjectWriter writer, SemanticLogLevel logLevel, Exception? exception)
{
writer.WriteProperty("timestamp", clock());
diff --git a/log/Squidex.Log/ValueStopwatch.cs b/log/Squidex.Log/ValueStopwatch.cs
index b630335..2e585f7 100644
--- a/log/Squidex.Log/ValueStopwatch.cs
+++ b/log/Squidex.Log/ValueStopwatch.cs
@@ -9,15 +9,13 @@
namespace Squidex.Log;
-internal readonly struct ValueStopwatch
+internal readonly struct ValueStopwatch(long startTime)
{
private const long TicksPerMillisecond = 10000;
private const long TicksPerSecond = TicksPerMillisecond * 1000;
private static readonly double TickFrequency;
- private readonly long startTime;
-
static ValueStopwatch()
{
if (Stopwatch.IsHighResolution)
@@ -26,11 +24,6 @@ static ValueStopwatch()
}
}
- public ValueStopwatch(long startTime)
- {
- this.startTime = startTime;
- }
-
public static ValueStopwatch StartNew()
{
return new ValueStopwatch(Stopwatch.GetTimestamp());
diff --git a/messaging/Squidex.Messaging.All/Squidex.Messaging.All.csproj b/messaging/Squidex.Messaging.All/Squidex.Messaging.All.csproj
index f4d3e55..64b9362 100644
--- a/messaging/Squidex.Messaging.All/Squidex.Messaging.All.csproj
+++ b/messaging/Squidex.Messaging.All/Squidex.Messaging.All.csproj
@@ -12,7 +12,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/messaging/Squidex.Messaging.GoogleCloud/GooglePubSubTransport.cs b/messaging/Squidex.Messaging.GoogleCloud/GooglePubSubTransport.cs
index 11498a1..68f0aa4 100644
--- a/messaging/Squidex.Messaging.GoogleCloud/GooglePubSubTransport.cs
+++ b/messaging/Squidex.Messaging.GoogleCloud/GooglePubSubTransport.cs
@@ -16,22 +16,14 @@
namespace Squidex.Messaging.GoogleCloud;
-public sealed class GooglePubSubTransport : IMessagingTransport
+public sealed class GooglePubSubTransport(IOptions options,
+ ILogger log) : IMessagingTransport
{
private readonly Dictionary> publishers = [];
- private readonly GooglePubSubTransportOptions options;
+ private readonly GooglePubSubTransportOptions options = options.Value;
private readonly GooglePushConfig pushConfig = new GooglePushConfig();
private readonly HashSet createdSubcriptions = [];
private readonly HashSet createdTopics = [];
- private readonly ILogger log;
-
- public GooglePubSubTransport(IOptions options,
- ILogger log)
- {
- this.options = options.Value;
-
- this.log = log;
- }
public Task InitializeAsync(
CancellationToken ct)
diff --git a/messaging/Squidex.Messaging.GoogleCloud/Squidex.Messaging.GoogleCloud.csproj b/messaging/Squidex.Messaging.GoogleCloud/Squidex.Messaging.GoogleCloud.csproj
index 6e5f0a9..93b8f5e 100644
--- a/messaging/Squidex.Messaging.GoogleCloud/Squidex.Messaging.GoogleCloud.csproj
+++ b/messaging/Squidex.Messaging.GoogleCloud/Squidex.Messaging.GoogleCloud.csproj
@@ -12,8 +12,8 @@
-
-
+
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/messaging/Squidex.Messaging.Kafka/KafkaOwner.cs b/messaging/Squidex.Messaging.Kafka/KafkaOwner.cs
index e89e982..d58c0c5 100644
--- a/messaging/Squidex.Messaging.Kafka/KafkaOwner.cs
+++ b/messaging/Squidex.Messaging.Kafka/KafkaOwner.cs
@@ -11,26 +11,19 @@
namespace Squidex.Messaging.Kafka;
-public sealed class KafkaOwner
+public sealed class KafkaOwner(IOptions options,
+ ILogger log)
{
- private readonly IProducer producer;
-
- public Handle Handle => producer.Handle;
-
- public KafkaTransportOptions Options { get; }
-
- public KafkaOwner(IOptions options,
- ILogger log)
- {
- Options = options.Value;
-
- producer =
+ private readonly IProducer producer =
new ProducerBuilder(options.Value)
.SetLogHandler(KafkaLogFactory.ProducerLog(log))
.SetErrorHandler(KafkaLogFactory.ProducerError(log))
.SetStatisticsHandler(KafkaLogFactory.ProducerStats(log))
.Build();
- }
+
+ public Handle Handle => producer.Handle;
+
+ public KafkaTransportOptions Options { get; } = options.Value;
public void Dispose()
{
diff --git a/messaging/Squidex.Messaging.Kafka/KafkaTransport.cs b/messaging/Squidex.Messaging.Kafka/KafkaTransport.cs
index fa1480e..1a4858a 100644
--- a/messaging/Squidex.Messaging.Kafka/KafkaTransport.cs
+++ b/messaging/Squidex.Messaging.Kafka/KafkaTransport.cs
@@ -12,20 +12,11 @@
namespace Squidex.Messaging.Kafka;
-public sealed class KafkaTransport : IMessagingTransport
+public sealed class KafkaTransport(KafkaOwner owner,
+ ILogger log) : IMessagingTransport
{
- private readonly KafkaOwner owner;
- private readonly ILogger log;
private IProducer? producer;
- public KafkaTransport(KafkaOwner owner,
- ILogger log)
- {
- this.owner = owner;
-
- this.log = log;
- }
-
public Task InitializeAsync(
CancellationToken ct)
{
diff --git a/messaging/Squidex.Messaging.Kafka/Squidex.Messaging.Kafka.csproj b/messaging/Squidex.Messaging.Kafka/Squidex.Messaging.Kafka.csproj
index 60b6ecc..a2a4ecd 100644
--- a/messaging/Squidex.Messaging.Kafka/Squidex.Messaging.Kafka.csproj
+++ b/messaging/Squidex.Messaging.Kafka/Squidex.Messaging.Kafka.csproj
@@ -12,8 +12,8 @@
-
-
+
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/messaging/Squidex.Messaging.Mongo/MongoMessagingDataStore.cs b/messaging/Squidex.Messaging.Mongo/MongoMessagingDataStore.cs
index c907fbb..e924ca4 100644
--- a/messaging/Squidex.Messaging.Mongo/MongoMessagingDataStore.cs
+++ b/messaging/Squidex.Messaging.Mongo/MongoMessagingDataStore.cs
@@ -11,9 +11,9 @@
namespace Squidex.Messaging.Mongo;
-public sealed class MongoMessagingDataStore : IMessagingDataStore, IInitializable
+public sealed class MongoMessagingDataStore(IMongoDatabase database, IOptions options) : IMessagingDataStore, IInitializable
{
- private readonly IMongoCollection collection;
+ private readonly IMongoCollection collection = database.GetCollection(options.Value.CollectionName);
private sealed class Entity
{
@@ -32,11 +32,6 @@ private sealed class Entity
public DateTime Expiration { get; set; }
}
- public MongoMessagingDataStore(IMongoDatabase database, IOptions options)
- {
- collection = database.GetCollection(options.Value.CollectionName);
- }
-
public Task InitializeAsync(
CancellationToken ct)
{
diff --git a/messaging/Squidex.Messaging.Mongo/MongoTransport.cs b/messaging/Squidex.Messaging.Mongo/MongoTransport.cs
index f5386f1..3071a2a 100644
--- a/messaging/Squidex.Messaging.Mongo/MongoTransport.cs
+++ b/messaging/Squidex.Messaging.Mongo/MongoTransport.cs
@@ -13,28 +13,15 @@
namespace Squidex.Messaging.Mongo;
-public sealed class MongoTransport : IMessagingTransport
+public sealed class MongoTransport(
+ IMongoDatabase database,
+ IMessagingDataProvider messagingDataProvider,
+ IOptions options,
+ TimeProvider timeProvider,
+ ILogger log) : IMessagingTransport
{
private readonly Dictionary>> collections = [];
- private readonly MongoTransportOptions options;
- private readonly IMongoDatabase database;
- private readonly IMessagingDataProvider messagingDataProvider;
- private readonly TimeProvider timeProvider;
- private readonly ILogger log;
-
- public MongoTransport(
- IMongoDatabase database,
- IMessagingDataProvider messagingDataProvider,
- IOptions options,
- TimeProvider timeProvider,
- ILogger log)
- {
- this.options = options.Value;
- this.database = database;
- this.messagingDataProvider = messagingDataProvider;
- this.timeProvider = timeProvider;
- this.log = log;
- }
+ private readonly MongoTransportOptions options = options.Value;
public Task InitializeAsync(
CancellationToken ct)
diff --git a/messaging/Squidex.Messaging.Mongo/MongoTransportCleaner.cs b/messaging/Squidex.Messaging.Mongo/MongoTransportCleaner.cs
index 07332c5..64efbff 100644
--- a/messaging/Squidex.Messaging.Mongo/MongoTransportCleaner.cs
+++ b/messaging/Squidex.Messaging.Mongo/MongoTransportCleaner.cs
@@ -11,18 +11,14 @@
namespace Squidex.Messaging.Mongo;
-internal sealed class MongoTransportCleaner : IAsyncDisposable
+internal sealed class MongoTransportCleaner(IMongoCollection collection, string collectionName,
+ TimeSpan timeout,
+ TimeSpan expires,
+ TimeSpan updateInterval,
+ ILogger log,
+ TimeProvider timeProvider) : IAsyncDisposable
{
- private readonly SimpleTimer timer;
-
- public MongoTransportCleaner(IMongoCollection collection, string collectionName,
- TimeSpan timeout,
- TimeSpan expires,
- TimeSpan updateInterval,
- ILogger log,
- TimeProvider timeProvider)
- {
- timer = new SimpleTimer(async ct =>
+ private readonly SimpleTimer timer = new SimpleTimer(async ct =>
{
var now = timeProvider.GetUtcNow().UtcDateTime;
@@ -40,7 +36,6 @@ public MongoTransportCleaner(IMongoCollection collection, string c
log.LogInformation("{collectionName}: Items reset: {count}.", collectionName, update.ModifiedCount);
}
}, updateInterval, log);
- }
public ValueTask DisposeAsync()
{
diff --git a/messaging/Squidex.Messaging.Mongo/Squidex.Messaging.Mongo.csproj b/messaging/Squidex.Messaging.Mongo/Squidex.Messaging.Mongo.csproj
index d9e092c..fb50b59 100644
--- a/messaging/Squidex.Messaging.Mongo/Squidex.Messaging.Mongo.csproj
+++ b/messaging/Squidex.Messaging.Mongo/Squidex.Messaging.Mongo.csproj
@@ -12,7 +12,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
@@ -20,7 +20,7 @@
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
diff --git a/messaging/Squidex.Messaging.RabbitMq/RabbitMqOwner.cs b/messaging/Squidex.Messaging.RabbitMq/RabbitMqOwner.cs
index b552241..ab4333f 100644
--- a/messaging/Squidex.Messaging.RabbitMq/RabbitMqOwner.cs
+++ b/messaging/Squidex.Messaging.RabbitMq/RabbitMqOwner.cs
@@ -12,7 +12,7 @@ namespace Squidex.Messaging.RabbitMq;
public sealed class RabbitMqOwner
{
- public IConnection Connection { get; }
+ public Task Connection { get; }
public RabbitMqTransportOptions Options { get; }
@@ -23,11 +23,16 @@ public RabbitMqOwner(IOptions options)
var connectionFactory = new ConnectionFactory
{
Uri = options.Value.Uri,
-
- // Of course we want an asynchronous behavior.
- DispatchConsumersAsync = true
};
- Connection = connectionFactory.CreateConnection();
+ Connection = connectionFactory.CreateConnectionAsync();
+ }
+
+ public async Task CreateChannelAsync(
+ CancellationToken ct)
+ {
+ var connection = await Connection;
+
+ return await connection.CreateChannelAsync(cancellationToken: ct);
}
}
diff --git a/messaging/Squidex.Messaging.RabbitMq/RabbitMqSubscription.cs b/messaging/Squidex.Messaging.RabbitMq/RabbitMqSubscription.cs
index 34aa64c..229281d 100644
--- a/messaging/Squidex.Messaging.RabbitMq/RabbitMqSubscription.cs
+++ b/messaging/Squidex.Messaging.RabbitMq/RabbitMqSubscription.cs
@@ -15,35 +15,56 @@ namespace Squidex.Messaging.RabbitMq;
internal sealed class RabbitMqSubscription : IMessageAck, IAsyncDisposable
{
private readonly CancellationTokenSource stopToken = new CancellationTokenSource();
- private readonly IModel model;
private readonly string queueName;
- private readonly string consumerTag;
+ private readonly IChannel channel;
private readonly ILogger log;
+ private string consumerTag;
- public RabbitMqSubscription(string queueName, RabbitMqOwner factory,
- MessageTransportCallback callback, ILogger log)
+ private RabbitMqSubscription(string queueName, IChannel channel, ILogger log)
{
this.queueName = queueName;
+ this.channel = channel;
+ this.log = log;
+ }
+
+ public static async Task OpenAsync(
+ string queueName, RabbitMqOwner
+ factory,
+ MessageTransportCallback callback,
+ ILogger log,
+ CancellationToken ct)
+ {
+ var rabbitMqChannel = await factory.CreateChannelAsync(ct);
+ var rabbitMqSubscription = new RabbitMqSubscription(queueName, rabbitMqChannel, log);
- model = factory.Connection.CreateModel();
+ await rabbitMqSubscription.StartAsync(callback, ct);
- var eventConsumer = new AsyncEventingBasicConsumer(model);
+ return rabbitMqSubscription;
+ }
- eventConsumer.Received += async (_, @event) =>
+ internal async Task StartAsync(MessageTransportCallback callback,
+ CancellationToken ct)
+ {
+ var eventConsumer = new AsyncEventingBasicConsumer(channel);
+
+ eventConsumer.ReceivedAsync += async (_, @event) =>
{
try
{
var headers = new TransportHeaders();
- foreach (var (key, value) in @event.BasicProperties.Headers)
+ if (@event.BasicProperties.Headers != null)
{
- if (value is byte[] bytes)
- {
- headers[key] = Encoding.UTF8.GetString(bytes);
- }
- else if (value is string text)
+ foreach (var (key, value) in @event.BasicProperties.Headers)
{
- headers[key] = text;
+ if (value is byte[] bytes)
+ {
+ headers[key] = Encoding.UTF8.GetString(bytes);
+ }
+ else if (value is string text)
+ {
+ headers[key] = text;
+ }
}
}
@@ -58,68 +79,67 @@ public RabbitMqSubscription(string queueName, RabbitMqOwner factory,
}
};
- consumerTag = model.BasicConsume(queueName, false, eventConsumer);
-
- this.log = log;
+ consumerTag = await channel.BasicConsumeAsync(queueName, false, eventConsumer, ct);
}
public async ValueTask DisposeAsync()
{
await stopToken.CancelAsync();
-
- model.BasicCancel(consumerTag);
- model.Dispose();
+ try
+ {
+ await channel.BasicCancelAsync(consumerTag, cancellationToken: default);
+ }
+ finally
+ {
+ channel.Dispose();
+ }
}
- public Task OnErrorAsync(TransportResult result,
+ public async Task OnErrorAsync(TransportResult result,
CancellationToken ct)
{
if (stopToken.IsCancellationRequested)
{
- return Task.CompletedTask;
+ return;
}
if (result.Data is not ulong deliverTag)
{
log.LogWarning("Transport message has no RabbitMq delivery tag.");
- return Task.CompletedTask;
+ return;
}
try
{
- model.BasicReject(deliverTag, false);
+ await channel.BasicRejectAsync(deliverTag, false, ct);
}
catch (Exception ex)
{
log.LogError(ex, "Failed to acknowledge message from queue {queue}.", queueName);
}
-
- return Task.CompletedTask;
}
- public Task OnSuccessAsync(TransportResult result,
+ public async Task OnSuccessAsync(TransportResult result,
CancellationToken ct)
{
if (stopToken.IsCancellationRequested)
{
- return Task.CompletedTask;
+ return;
}
if (result.Data is not ulong deliverTag)
{
log.LogWarning("Transport message has no RabbitMq delivery tag.");
- return Task.CompletedTask;
+ return;
}
try
{
- model.BasicAck(deliverTag, false);
+ await channel.BasicAckAsync(deliverTag, false, ct);
}
catch (Exception ex)
{
log.LogError(ex, "Failed to reject message from queue {queue}.", queueName);
}
-
- return Task.CompletedTask;
}
}
diff --git a/messaging/Squidex.Messaging.RabbitMq/RabbitMqTransport.cs b/messaging/Squidex.Messaging.RabbitMq/RabbitMqTransport.cs
index ca2d245..960fe0a 100644
--- a/messaging/Squidex.Messaging.RabbitMq/RabbitMqTransport.cs
+++ b/messaging/Squidex.Messaging.RabbitMq/RabbitMqTransport.cs
@@ -11,88 +11,84 @@
namespace Squidex.Messaging.RabbitMq;
-public sealed class RabbitMqTransport : IMessagingTransport
+public sealed class RabbitMqTransport(RabbitMqOwner owner,
+ ILogger log) : IMessagingTransport
{
- private readonly RabbitMqOwner owner;
- private readonly ILogger log;
private readonly HashSet createdQueues = [];
- private IModel? model;
+ private readonly SemaphoreSlim semaphoreSlim = new SemaphoreSlim(1);
+ private IChannel? channelModel;
- public RabbitMqTransport(RabbitMqOwner owner,
- ILogger log)
- {
- this.owner = owner;
-
- this.log = log;
- }
-
- public Task InitializeAsync(
+ public async Task InitializeAsync(
CancellationToken ct)
{
- if (model != null)
+ if (channelModel != null)
{
- return Task.CompletedTask;
+ return;
}
- model = owner.Connection.CreateModel();
-
- return Task.CompletedTask;
+ channelModel = await owner.CreateChannelAsync(ct);
}
public Task ReleaseAsync(
CancellationToken ct)
{
- if (model == null)
+ if (channelModel == null)
{
return Task.CompletedTask;
}
- model.Dispose();
- model = null;
+ channelModel.Dispose();
+ channelModel = null;
return Task.CompletedTask;
}
- public Task CreateChannelAsync(ChannelName channel, string instanceName, bool consume, ProducerOptions producerOptions,
+ public async Task CreateChannelAsync(ChannelName channel, string instanceName, bool consume, ProducerOptions producerOptions,
CancellationToken ct)
{
- if (model == null)
+ if (channelModel == null)
{
ThrowHelper.InvalidOperationException("Transport not initialized yet.");
- return Task.FromResult(null);
+ return null;
}
- lock (model)
+ await semaphoreSlim.WaitAsync(ct);
+ try
{
if (channel.Type == ChannelType.Queue)
{
- model.QueueDeclare(channel.Name, true, false, false, null);
+ await channelModel.QueueDeclareAsync(channel.Name, true, false, false, null, cancellationToken: ct);
}
else
{
- model.ExchangeDeclare(channel.Name, "fanout", true, false, null);
+ await channelModel.ExchangeDeclareAsync(channel.Name, "fanout", true, false, null, cancellationToken: ct);
}
}
+ finally
+ {
+ semaphoreSlim.Release();
+ }
- return Task.FromResult(null);
+ return null;
}
- public Task ProduceAsync(ChannelName channel, string instanceName, TransportMessage transportMessage,
+ public async Task ProduceAsync(ChannelName channel, string instanceName, TransportMessage transportMessage,
CancellationToken ct)
{
- if (model == null)
+ if (channelModel == null)
{
ThrowHelper.InvalidOperationException("Transport not initialized yet.");
- return Task.CompletedTask;
+ return;
}
- lock (model)
+ await semaphoreSlim.WaitAsync(ct);
+ try
{
- var properties = model.CreateBasicProperties();
+ var properties = new BasicProperties();
if (transportMessage.Headers.Count > 0)
{
- properties.Headers = new Dictionary();
+ properties.Headers = new Dictionary();
foreach (var (key, value) in transportMessage.Headers)
{
@@ -102,26 +98,23 @@ public Task ProduceAsync(ChannelName channel, string instanceName, TransportMess
if (channel.Type == ChannelType.Queue)
{
- model.BasicPublish(string.Empty, channel.Name, properties, transportMessage.Data);
+ await channelModel.BasicPublishAsync(string.Empty, channel.Name, false, properties, transportMessage.Data, ct);
}
else
{
- model.BasicPublish(channel.Name, "*", properties, transportMessage.Data);
+ await channelModel.BasicPublishAsync(channel.Name, "*", false, properties, transportMessage.Data, ct);
}
}
-
- return Task.CompletedTask;
+ finally
+ {
+ semaphoreSlim.Release();
+ }
}
- public Task SubscribeAsync(ChannelName channel, string instanceName, MessageTransportCallback callback,
+ public async Task SubscribeAsync(ChannelName channel, string instanceName, MessageTransportCallback callback,
CancellationToken ct)
{
- return Task.FromResult(SubscribeCore(channel, instanceName, callback));
- }
-
- private RabbitMqSubscription SubscribeCore(ChannelName channel, string instanceName, MessageTransportCallback callback)
- {
- if (model == null)
+ if (channelModel == null)
{
ThrowHelper.InvalidOperationException("Transport not initialized yet.");
return null!;
@@ -131,13 +124,14 @@ private RabbitMqSubscription SubscribeCore(ChannelName channel, string instanceN
if (channel.Type == ChannelType.Topic)
{
- queueName = CreateTemporaryQueue(channel, instanceName);
+ queueName = await CreateTemporaryQueueAsync(channel, instanceName, ct);
}
- return new RabbitMqSubscription(queueName, owner, callback, log);
+ return await RabbitMqSubscription.OpenAsync(queueName, owner, callback, log, ct);
}
- private string CreateTemporaryQueue(ChannelName channel, string instanceName)
+ private async Task CreateTemporaryQueueAsync(ChannelName channel, string instanceName,
+ CancellationToken ct)
{
var queueName = $"{channel.Name}_{instanceName}";
@@ -146,13 +140,16 @@ private string CreateTemporaryQueue(ChannelName channel, string instanceName)
return queueName;
}
- lock (model!)
+ await semaphoreSlim.WaitAsync(ct);
+ try
{
// Create a queue that only lives as long as the client is connected.
- model.QueueDeclare(queueName);
-
- // Bind the queue to the exchange.
- model.QueueBind(queueName, channel.Name, "*");
+ await channelModel!.QueueDeclareAsync(queueName, cancellationToken: ct);
+ await channelModel!.QueueBindAsync(queueName, channel.Name, "*", cancellationToken: ct);
+ }
+ finally
+ {
+ semaphoreSlim.Release();
}
return queueName;
diff --git a/messaging/Squidex.Messaging.RabbitMq/Squidex.Messaging.RabbitMq.csproj b/messaging/Squidex.Messaging.RabbitMq/Squidex.Messaging.RabbitMq.csproj
index a223669..0a7a2ef 100644
--- a/messaging/Squidex.Messaging.RabbitMq/Squidex.Messaging.RabbitMq.csproj
+++ b/messaging/Squidex.Messaging.RabbitMq/Squidex.Messaging.RabbitMq.csproj
@@ -12,7 +12,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
@@ -20,7 +20,7 @@
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
diff --git a/messaging/Squidex.Messaging.Redis/LoggerTextWriter.cs b/messaging/Squidex.Messaging.Redis/LoggerTextWriter.cs
index 14305ff..462e226 100644
--- a/messaging/Squidex.Messaging.Redis/LoggerTextWriter.cs
+++ b/messaging/Squidex.Messaging.Redis/LoggerTextWriter.cs
@@ -10,15 +10,8 @@
namespace Squidex.Messaging.Redis;
-internal sealed class LoggerTextWriter : TextWriter
+internal sealed class LoggerTextWriter(ILogger log) : TextWriter
{
- private readonly ILogger log;
-
- public LoggerTextWriter(ILogger log)
- {
- this.log = log;
- }
-
public override Encoding Encoding => Encoding.UTF8;
public override void Write(char value)
diff --git a/messaging/Squidex.Messaging.Redis/RedisTransport.cs b/messaging/Squidex.Messaging.Redis/RedisTransport.cs
index 1dbc831..ef646f5 100644
--- a/messaging/Squidex.Messaging.Redis/RedisTransport.cs
+++ b/messaging/Squidex.Messaging.Redis/RedisTransport.cs
@@ -13,21 +13,13 @@
namespace Squidex.Messaging.Redis;
-public sealed class RedisTransport : IMessagingTransport
+public sealed class RedisTransport(IOptions options,
+ ILogger log) : IMessagingTransport
{
- private readonly ILogger log;
- private readonly RedisTransportOptions options;
+ private readonly RedisTransportOptions options = options.Value;
private ISubscriber? subscriber;
private IDatabase? database;
- public RedisTransport(IOptions options,
- ILogger log)
- {
- this.options = options.Value;
-
- this.log = log;
- }
-
public async Task InitializeAsync(
CancellationToken ct)
{
diff --git a/messaging/Squidex.Messaging.Redis/Squidex.Messaging.Redis.csproj b/messaging/Squidex.Messaging.Redis/Squidex.Messaging.Redis.csproj
index 8f8753f..a73d935 100644
--- a/messaging/Squidex.Messaging.Redis/Squidex.Messaging.Redis.csproj
+++ b/messaging/Squidex.Messaging.Redis/Squidex.Messaging.Redis.csproj
@@ -12,7 +12,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
@@ -21,7 +21,7 @@
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
diff --git a/messaging/Squidex.Messaging.Subscriptions/Implementation/SubscriptionService.cs b/messaging/Squidex.Messaging.Subscriptions/Implementation/SubscriptionService.cs
index eb1866f..222146f 100644
--- a/messaging/Squidex.Messaging.Subscriptions/Implementation/SubscriptionService.cs
+++ b/messaging/Squidex.Messaging.Subscriptions/Implementation/SubscriptionService.cs
@@ -15,28 +15,16 @@
namespace Squidex.Messaging.Subscriptions.Implementation;
-public sealed class SubscriptionService : ISubscriptionService, IMessageHandler
+public sealed class SubscriptionService(
+ IInstanceNameProvider instanceName,
+ IMessageBus messageBus,
+ IMessagingDataProvider messagingDataProvider,
+ IOptions options,
+ ILogger log) : ISubscriptionService, IMessageHandler
{
private readonly ConcurrentDictionary localSubscriptions = [];
- private readonly SubscriptionOptions options;
- private readonly string instanceName;
- private readonly IMessageBus messageBus;
- private readonly IMessagingDataProvider messagingDataProvider;
- private readonly ILogger log;
-
- public SubscriptionService(
- IInstanceNameProvider instanceName,
- IMessageBus messageBus,
- IMessagingDataProvider messagingDataProvider,
- IOptions options,
- ILogger log)
- {
- this.instanceName = instanceName.Name;
- this.messageBus = messageBus;
- this.messagingDataProvider = messagingDataProvider;
- this.options = options.Value;
- this.log = log;
- }
+ private readonly SubscriptionOptions options = options.Value;
+ private readonly string instanceName = instanceName.Name;
public async Task HasSubscriptionsAsync(string key,
CancellationToken ct = default)
diff --git a/messaging/Squidex.Messaging.Subscriptions/Squidex.Messaging.Subscriptions.csproj b/messaging/Squidex.Messaging.Subscriptions/Squidex.Messaging.Subscriptions.csproj
index 37de1bc..e105c4f 100644
--- a/messaging/Squidex.Messaging.Subscriptions/Squidex.Messaging.Subscriptions.csproj
+++ b/messaging/Squidex.Messaging.Subscriptions/Squidex.Messaging.Subscriptions.csproj
@@ -12,7 +12,7 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/messaging/Squidex.Messaging.Tests/Internal/Types.cs b/messaging/Squidex.Messaging.Tests/Internal/Types.cs
index cfc58e3..d2d2366 100644
--- a/messaging/Squidex.Messaging.Tests/Internal/Types.cs
+++ b/messaging/Squidex.Messaging.Tests/Internal/Types.cs
@@ -14,23 +14,12 @@ public sealed class TestValue(string value)
public string Value { get; } = value;
}
-public sealed class TestMessage : BaseMessage
+public sealed class TestMessage(Guid testId, int value) : BaseMessage(testId)
{
- public int Value { get; }
-
- public TestMessage(Guid testId, int value)
- : base(testId)
- {
- Value = value;
- }
+ public int Value { get; } = value;
}
-public abstract class BaseMessage
+public abstract class BaseMessage(Guid testId)
{
- public Guid TestId { get; }
-
- protected BaseMessage(Guid testId)
- {
- TestId = testId;
- }
+ public Guid TestId { get; } = testId;
}
diff --git a/messaging/Squidex.Messaging.Tests/MongoMessagingPrefetchTests.cs b/messaging/Squidex.Messaging.Tests/MongoMessagingPrefetchTests.cs
index 2b02466..df15be4 100644
--- a/messaging/Squidex.Messaging.Tests/MongoMessagingPrefetchTests.cs
+++ b/messaging/Squidex.Messaging.Tests/MongoMessagingPrefetchTests.cs
@@ -11,14 +11,9 @@
namespace Squidex.Messaging;
-public class MongoMessagingPrefetchTests : MessagingTestsBase, IClassFixture
+public class MongoMessagingPrefetchTests(MongoFixture fixture) : MessagingTestsBase, IClassFixture
{
- public MongoFixture _ { get; }
-
- public MongoMessagingPrefetchTests(MongoFixture fixture)
- {
- _ = fixture;
- }
+ public MongoFixture _ { get; } = fixture;
protected override void Configure(MessagingBuilder builder)
{
diff --git a/messaging/Squidex.Messaging.Tests/MongoMessagingTests.cs b/messaging/Squidex.Messaging.Tests/MongoMessagingTests.cs
index ce45ec4..1aff121 100644
--- a/messaging/Squidex.Messaging.Tests/MongoMessagingTests.cs
+++ b/messaging/Squidex.Messaging.Tests/MongoMessagingTests.cs
@@ -11,14 +11,9 @@
namespace Squidex.Messaging;
-public class MongoMessagingTests : MessagingTestsBase, IClassFixture
+public class MongoMessagingTests(MongoFixture fixture) : MessagingTestsBase, IClassFixture
{
- public MongoFixture _ { get; }
-
- public MongoMessagingTests(MongoFixture fixture)
- {
- _ = fixture;
- }
+ public MongoFixture _ { get; } = fixture;
protected override void Configure(MessagingBuilder builder)
{
diff --git a/messaging/Squidex.Messaging.Tests/MongoSubscriptionStoreTests.cs b/messaging/Squidex.Messaging.Tests/MongoSubscriptionStoreTests.cs
index cbc3a3a..d8ffbd6 100644
--- a/messaging/Squidex.Messaging.Tests/MongoSubscriptionStoreTests.cs
+++ b/messaging/Squidex.Messaging.Tests/MongoSubscriptionStoreTests.cs
@@ -12,14 +12,9 @@
namespace Squidex.Messaging;
[Trait("Category", "Dependencies")]
-public class MongoSubscriptionStoreTests : SubscriptionStoreTestsBase, IClassFixture
+public class MongoSubscriptionStoreTests(MongoFixture fixture) : SubscriptionStoreTestsBase, IClassFixture
{
- public MongoFixture _ { get; }
-
- public MongoSubscriptionStoreTests(MongoFixture fixture)
- {
- _ = fixture;
- }
+ public MongoFixture _ { get; } = fixture;
protected override void Configure(MessagingBuilder builder)
{
diff --git a/messaging/Squidex.Messaging.Tests/RedisMessagingTests.cs b/messaging/Squidex.Messaging.Tests/RedisMessagingTests.cs
index 438d7bd..180b1c3 100644
--- a/messaging/Squidex.Messaging.Tests/RedisMessagingTests.cs
+++ b/messaging/Squidex.Messaging.Tests/RedisMessagingTests.cs
@@ -12,17 +12,12 @@
namespace Squidex.Messaging;
-public class RedisMessagingTests : MessagingTestsBase, IClassFixture
+public class RedisMessagingTests(RedisFixture fixture) : MessagingTestsBase, IClassFixture
{
- public RedisFixture _ { get; }
+ public RedisFixture _ { get; } = fixture;
protected override bool CanHandleAndSimulateTimeout => false;
- public RedisMessagingTests(RedisFixture fixture)
- {
- _ = fixture;
- }
-
protected override void Configure(MessagingBuilder builder)
{
builder.AddRedisTransport(TestHelpers.Configuration, options =>
diff --git a/messaging/Squidex.Messaging.Tests/Squidex.Messaging.Tests.csproj b/messaging/Squidex.Messaging.Tests/Squidex.Messaging.Tests.csproj
index babf113..b4a5a96 100644
--- a/messaging/Squidex.Messaging.Tests/Squidex.Messaging.Tests.csproj
+++ b/messaging/Squidex.Messaging.Tests/Squidex.Messaging.Tests.csproj
@@ -15,16 +15,16 @@
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/messaging/Squidex.Messaging.Tests/SubscriptionServiceTests.cs b/messaging/Squidex.Messaging.Tests/SubscriptionServiceTests.cs
index fbd0553..9a47890 100644
--- a/messaging/Squidex.Messaging.Tests/SubscriptionServiceTests.cs
+++ b/messaging/Squidex.Messaging.Tests/SubscriptionServiceTests.cs
@@ -17,17 +17,12 @@
namespace Squidex.Messaging;
[Trait("Category", "Dependencies")]
-public class SubscriptionServiceTests : IClassFixture
+public class SubscriptionServiceTests(MongoFixture fixture) : IClassFixture
{
private readonly string groupName = $"group-{Guid.NewGuid()}";
private readonly string key = $"key-{Guid.NewGuid()}";
- public MongoFixture _ { get; }
-
- public SubscriptionServiceTests(MongoFixture fixture)
- {
- _ = fixture;
- }
+ public MongoFixture _ { get; } = fixture;
[Fact]
public async Task Should_subscribe_hot()
diff --git a/messaging/Squidex.Messaging/Implementation/CachingMessagingDataProvider.cs b/messaging/Squidex.Messaging/Implementation/CachingMessagingDataProvider.cs
index eefb51c..1df5d47 100644
--- a/messaging/Squidex.Messaging/Implementation/CachingMessagingDataProvider.cs
+++ b/messaging/Squidex.Messaging/Implementation/CachingMessagingDataProvider.cs
@@ -10,18 +10,9 @@
namespace Squidex.Messaging.Implementation;
-public sealed class CachingMessagingDataProvider : IMessagingDataProvider
+public sealed class CachingMessagingDataProvider(IMemoryCache cache, IMessagingDataProvider inner, IOptions options) : IMessagingDataProvider
{
- private readonly IMessagingDataProvider inner;
- private readonly IMemoryCache cache;
- private readonly MessagingOptions options;
-
- public CachingMessagingDataProvider(IMemoryCache cache, IMessagingDataProvider inner, IOptions options)
- {
- this.options = options.Value;
- this.cache = cache;
- this.inner = inner;
- }
+ private readonly MessagingOptions options = options.Value;
public async Task> GetEntriesAsync(string group,
CancellationToken ct = default) where T : notnull
diff --git a/messaging/Squidex.Messaging/Implementation/DefaultMessageBus.cs b/messaging/Squidex.Messaging/Implementation/DefaultMessageBus.cs
index dd9e1ff..c738bab 100644
--- a/messaging/Squidex.Messaging/Implementation/DefaultMessageBus.cs
+++ b/messaging/Squidex.Messaging/Implementation/DefaultMessageBus.cs
@@ -10,17 +10,9 @@
namespace Squidex.Messaging.Implementation;
-internal sealed class DefaultMessageBus : IMessageBus
+internal sealed class DefaultMessageBus(IInternalMessageProducer internalProducer, IOptions options) : IMessageBus
{
- private readonly IInternalMessageProducer internalProducer;
- private readonly RoutingCollection routing;
-
- public DefaultMessageBus(IInternalMessageProducer internalProducer, IOptions options)
- {
- this.internalProducer = internalProducer;
-
- routing = new RoutingCollection(options.Value.Routing);
- }
+ private readonly RoutingCollection routing = new RoutingCollection(options.Value.Routing);
public async Task PublishAsync(object message, string? key = null,
CancellationToken ct = default)
diff --git a/messaging/Squidex.Messaging/Implementation/DelegateAsyncDisposable.cs b/messaging/Squidex.Messaging/Implementation/DelegateAsyncDisposable.cs
index a1462bc..cf839f2 100644
--- a/messaging/Squidex.Messaging/Implementation/DelegateAsyncDisposable.cs
+++ b/messaging/Squidex.Messaging/Implementation/DelegateAsyncDisposable.cs
@@ -7,15 +7,8 @@
namespace Squidex.Messaging.Implementation;
-public sealed class DelegateAsyncDisposable : IAsyncDisposable
+public sealed class DelegateAsyncDisposable(Func action) : IAsyncDisposable
{
- private readonly Func action;
-
- public DelegateAsyncDisposable(Func action)
- {
- this.action = action;
- }
-
public ValueTask DisposeAsync()
{
return action();
diff --git a/messaging/Squidex.Messaging/Implementation/DelegatingProducer.cs b/messaging/Squidex.Messaging/Implementation/DelegatingProducer.cs
index 22ee0c9..b9f1408 100644
--- a/messaging/Squidex.Messaging/Implementation/DelegatingProducer.cs
+++ b/messaging/Squidex.Messaging/Implementation/DelegatingProducer.cs
@@ -11,29 +11,16 @@
namespace Squidex.Messaging.Implementation;
-public sealed class DelegatingProducer : IInternalMessageProducer
+public sealed class DelegatingProducer(
+ IInstanceNameProvider instanceName,
+ IMessagingTransports messagingTransports,
+ IMessagingSerializer messagingSerializer,
+ IOptionsMonitor channelOptions,
+ TimeProvider timeProvider) : IInternalMessageProducer
{
private readonly HashSet initializedChannels = [];
private readonly SemaphoreSlim semaphore = new SemaphoreSlim(1);
- private readonly string instanceName;
- private readonly IMessagingTransports messagingTransports;
- private readonly IMessagingSerializer messagingSerializer;
- private readonly IOptionsMonitor channelOptions;
- private readonly TimeProvider timeProvider;
-
- public DelegatingProducer(
- IInstanceNameProvider instanceName,
- IMessagingTransports messagingTransports,
- IMessagingSerializer messagingSerializer,
- IOptionsMonitor channelOptions,
- TimeProvider timeProvider)
- {
- this.channelOptions = channelOptions;
- this.instanceName = instanceName.Name;
- this.messagingTransports = messagingTransports;
- this.messagingSerializer = messagingSerializer;
- this.timeProvider = timeProvider;
- }
+ private readonly string instanceName = instanceName.Name;
public async Task ProduceAsync(ChannelName channel, object message, string? key = null,
CancellationToken ct = default)
diff --git a/messaging/Squidex.Messaging/Implementation/MessagingDataProvider.cs b/messaging/Squidex.Messaging/Implementation/MessagingDataProvider.cs
index 8fb96f5..092a521 100644
--- a/messaging/Squidex.Messaging/Implementation/MessagingDataProvider.cs
+++ b/messaging/Squidex.Messaging/Implementation/MessagingDataProvider.cs
@@ -11,30 +11,17 @@
namespace Squidex.Messaging.Implementation;
-public sealed class MessagingDataProvider : IMessagingDataProvider, IBackgroundProcess
+public sealed class MessagingDataProvider(
+ IMessagingDataStore messagingDataStore,
+ IMessagingSerializer messagingSerializer,
+ IOptions options,
+ TimeProvider timeProvider,
+ ILogger log) : IMessagingDataProvider, IBackgroundProcess
{
private readonly Dictionary<(string Group, string Key), (SerializedObject Value, TimeSpan Expires)> localData = [];
- private readonly MessagingOptions options;
- private readonly IMessagingDataStore messagingDataStore;
- private readonly IMessagingSerializer messagingSerializer;
- private readonly ILogger log;
- private readonly TimeProvider timeProvider;
+ private readonly MessagingOptions options = options.Value;
private SimpleTimer? updateTimer;
- public MessagingDataProvider(
- IMessagingDataStore messagingDataStore,
- IMessagingSerializer messagingSerializer,
- IOptions options,
- TimeProvider timeProvider,
- ILogger log)
- {
- this.options = options.Value;
- this.messagingDataStore = messagingDataStore;
- this.messagingSerializer = messagingSerializer;
- this.timeProvider = timeProvider;
- this.log = log;
- }
-
public Task StartAsync(
CancellationToken ct)
{
diff --git a/messaging/Squidex.Messaging/Internal/AggregateAsyncDisposable.cs b/messaging/Squidex.Messaging/Internal/AggregateAsyncDisposable.cs
index 3c3d347..404ab37 100644
--- a/messaging/Squidex.Messaging/Internal/AggregateAsyncDisposable.cs
+++ b/messaging/Squidex.Messaging/Internal/AggregateAsyncDisposable.cs
@@ -7,15 +7,8 @@
namespace Squidex.Messaging.Internal;
-public sealed class AggregateAsyncDisposable : IAsyncDisposable
+public sealed class AggregateAsyncDisposable(params IAsyncDisposable[] inners) : IAsyncDisposable
{
- private readonly IAsyncDisposable[] inners;
-
- public AggregateAsyncDisposable(params IAsyncDisposable[] inners)
- {
- this.inners = inners;
- }
-
public async ValueTask DisposeAsync()
{
foreach (var inner in inners)
diff --git a/messaging/Squidex.Messaging/Squidex.Messaging.csproj b/messaging/Squidex.Messaging/Squidex.Messaging.csproj
index 1982d2c..f5b8027 100644
--- a/messaging/Squidex.Messaging/Squidex.Messaging.csproj
+++ b/messaging/Squidex.Messaging/Squidex.Messaging.csproj
@@ -12,14 +12,14 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/text/Squidex.Text.Tests/Squidex.Text.Tests.csproj b/text/Squidex.Text.Tests/Squidex.Text.Tests.csproj
index 764a216..9d07ada 100644
--- a/text/Squidex.Text.Tests/Squidex.Text.Tests.csproj
+++ b/text/Squidex.Text.Tests/Squidex.Text.Tests.csproj
@@ -16,19 +16,19 @@
runtime; build; native; contentfiles; analyzers; buildtransitive
-
-
+
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
-
-
+
+
+
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
diff --git a/text/Squidex.Text/ReadOnlyMemoryCharComparer.cs b/text/Squidex.Text/ReadOnlyMemoryCharComparer.cs
index b5c41bb..eb8756e 100644
--- a/text/Squidex.Text/ReadOnlyMemoryCharComparer.cs
+++ b/text/Squidex.Text/ReadOnlyMemoryCharComparer.cs
@@ -9,7 +9,7 @@
namespace Squidex.Text;
-internal sealed class ReadOnlyMemoryCharComparer : IEqualityComparer>
+internal sealed class ReadOnlyMemoryCharComparer(StringComparison comparison) : IEqualityComparer>
{
public static readonly ReadOnlyMemoryCharComparer Ordinal
= new ReadOnlyMemoryCharComparer(StringComparison.Ordinal);
@@ -29,13 +29,6 @@ public static readonly ReadOnlyMemoryCharComparer CurrentCulture
public static readonly ReadOnlyMemoryCharComparer CurrentCultureIgnoreCase
= new ReadOnlyMemoryCharComparer(StringComparison.CurrentCultureIgnoreCase);
- private readonly StringComparison comparison;
-
- public ReadOnlyMemoryCharComparer(StringComparison comparison)
- {
- this.comparison = comparison;
- }
-
public bool Equals(ReadOnlyMemory x, ReadOnlyMemory y)
{
return x.Span.Equals(y.Span, comparison);
diff --git a/text/Squidex.Text/RichText/TextVisitor.cs b/text/Squidex.Text/RichText/TextVisitor.cs
index fb9184f..77cd235 100644
--- a/text/Squidex.Text/RichText/TextVisitor.cs
+++ b/text/Squidex.Text/RichText/TextVisitor.cs
@@ -10,18 +10,12 @@
namespace Squidex.Text.RichText;
-public sealed class TextVisitor : Visitor
+public sealed class TextVisitor(StringBuilder stringBuilder, int maxLength) : Visitor
{
- private readonly StringBuilder stringBuilder;
- private readonly int maxLength;
+ private readonly StringBuilder stringBuilder = stringBuilder;
+ private readonly int maxLength = maxLength;
private NodeType previousNodeType;
- public TextVisitor(StringBuilder stringBuilder, int maxLength)
- {
- this.stringBuilder = stringBuilder;
- this.maxLength = maxLength;
- }
-
public static void Render(INode node, StringBuilder stringBuilder, int maxLength = int.MaxValue)
{
new TextVisitor(stringBuilder, maxLength).VisitRoot(node);
diff --git a/text/Squidex.Text/RichText/Writer/IndentedWriter.cs b/text/Squidex.Text/RichText/Writer/IndentedWriter.cs
index 2954b4d..5becef5 100644
--- a/text/Squidex.Text/RichText/Writer/IndentedWriter.cs
+++ b/text/Squidex.Text/RichText/Writer/IndentedWriter.cs
@@ -9,17 +9,11 @@
namespace Squidex.Text.RichText.Writer;
-internal sealed class IndentedWriter : IWriter
+internal sealed class IndentedWriter(StringBuilder stringBuilder) : IWriter
{
- private readonly StringBuilder stringBuilder = new StringBuilder();
private readonly Stack indents = new Stack(10);
private bool previousWasLine = true;
- public IndentedWriter(StringBuilder stringBuilder)
- {
- this.stringBuilder = stringBuilder;
- }
-
public IWriter WriteLine(string text)
{
AppendIndentsCore();
diff --git a/text/Squidex.Text/RichText/Writer/PlainWriter.cs b/text/Squidex.Text/RichText/Writer/PlainWriter.cs
index b1121cc..cfc6879 100644
--- a/text/Squidex.Text/RichText/Writer/PlainWriter.cs
+++ b/text/Squidex.Text/RichText/Writer/PlainWriter.cs
@@ -9,15 +9,8 @@
namespace Squidex.Text.RichText.Writer;
-internal sealed class PlainWriter : IWriter
+internal sealed class PlainWriter(StringBuilder stringBuilder) : IWriter
{
- private readonly StringBuilder stringBuilder;
-
- public PlainWriter(StringBuilder stringBuilder)
- {
- this.stringBuilder = stringBuilder;
- }
-
public IWriter WriteLine(string text)
{
stringBuilder.Append(text);
diff --git a/text/Squidex.Text/Squidex.Text.csproj b/text/Squidex.Text/Squidex.Text.csproj
index 34f9e17..817c55d 100644
--- a/text/Squidex.Text/Squidex.Text.csproj
+++ b/text/Squidex.Text/Squidex.Text.csproj
@@ -14,21 +14,21 @@
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
+
all
runtime; build; native; contentfiles; analyzers; buildtransitive
-
-
+
+
-
+
diff --git a/text/Squidex.Text/SvgError.cs b/text/Squidex.Text/SvgError.cs
index fb9cdd9..47bf3b3 100644
--- a/text/Squidex.Text/SvgError.cs
+++ b/text/Squidex.Text/SvgError.cs
@@ -7,19 +7,11 @@
namespace Squidex.Text;
-public sealed class SvgError
+public sealed class SvgError(string error, int lineCount = -1, int linePosition = -1)
{
- public int LineCount { get; }
+ public int LineCount { get; } = lineCount;
- public int LinePosition { get; }
+ public int LinePosition { get; } = linePosition;
- public string Error { get; }
-
- public SvgError(string error, int lineCount = -1, int linePosition = -1)
- {
- Error = error;
-
- LineCount = lineCount;
- LinePosition = linePosition;
- }
+ public string Error { get; } = error;
}
diff --git a/text/Squidex.Text/Translations/DeepL/DeepLTranslationService.cs b/text/Squidex.Text/Translations/DeepL/DeepLTranslationService.cs
index ecff053..0cdf091 100644
--- a/text/Squidex.Text/Translations/DeepL/DeepLTranslationService.cs
+++ b/text/Squidex.Text/Translations/DeepL/DeepLTranslationService.cs
@@ -14,12 +14,11 @@
namespace Squidex.Text.Translations.DeepL;
[ExcludeFromCodeCoverage]
-public sealed class DeepLTranslationService : ITranslationService
+public sealed class DeepLTranslationService(IHttpClientFactory httpClientFactory, IOptions options) : ITranslationService
{
private const string UrlPaid = "https://api.deepl.com/v2/translate";
private const string UrlFree = "https://api-free.deepl.com/v2/translate";
- private readonly DeepLTranslationOptions options;
- private readonly IHttpClientFactory httpClientFactory;
+ private readonly DeepLTranslationOptions options = options.Value;
private sealed class TranslationsDto
{
@@ -36,15 +35,7 @@ private sealed class TranslationDto
public string DetectedSourceLanguage { get; set; }
}
- public bool IsConfigured { get; }
-
- public DeepLTranslationService(IHttpClientFactory httpClientFactory, IOptions options)
- {
- this.options = options.Value;
- this.httpClientFactory = httpClientFactory;
-
- IsConfigured = !string.IsNullOrWhiteSpace(options.Value.AuthKey);
- }
+ public bool IsConfigured { get; } = !string.IsNullOrWhiteSpace(options.Value.AuthKey);
public async Task> TranslateAsync(IEnumerable texts, string targetLanguage, string? sourceLanguage = null,
CancellationToken ct = default)
diff --git a/text/Squidex.Text/Translations/GoogleCloud/GoogleCloudTranslationService.cs b/text/Squidex.Text/Translations/GoogleCloud/GoogleCloudTranslationService.cs
index dad7bb7..ce69781 100644
--- a/text/Squidex.Text/Translations/GoogleCloud/GoogleCloudTranslationService.cs
+++ b/text/Squidex.Text/Translations/GoogleCloud/GoogleCloudTranslationService.cs
@@ -11,19 +11,12 @@
namespace Squidex.Text.Translations.GoogleCloud;
-public sealed class GoogleCloudTranslationService : ITranslationService
+public sealed class GoogleCloudTranslationService(IOptions options) : ITranslationService
{
- private readonly GoogleCloudTranslationOptions options;
+ private readonly GoogleCloudTranslationOptions options = options.Value;
private TranslationServiceClient service;
- public bool IsConfigured { get; }
-
- public GoogleCloudTranslationService(IOptions options)
- {
- this.options = options.Value;
-
- IsConfigured = !string.IsNullOrWhiteSpace(options.Value.ProjectId);
- }
+ public bool IsConfigured { get; } = !string.IsNullOrWhiteSpace(options.Value.ProjectId);
public async Task> TranslateAsync(IEnumerable texts, string targetLanguage, string? sourceLanguage = null,
CancellationToken ct = default)