Skip to content

Commit

Permalink
Merge pull request #898 from sitkoru/tasks
Browse files Browse the repository at this point in the history
Tasks modules
  • Loading branch information
pogromistik authored Oct 18, 2023
2 parents ede3e4c + 8353b37 commit bbe0ac1
Show file tree
Hide file tree
Showing 55 changed files with 1,828 additions and 0 deletions.
60 changes: 60 additions & 0 deletions Sitko.Core.sln
Original file line number Diff line number Diff line change
Expand Up @@ -248,6 +248,14 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Sitko.Core.Repository.Grpc.
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Sitko.Core.Sentry", "src\Sitko.Core.Sentry\Sitko.Core.Sentry.csproj", "{5D438687-8576-425A-A8A9-A80B893DCE0C}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Sitko.Core.Tasks", "src\Sitko.Core.Tasks\Sitko.Core.Tasks.csproj", "{76EA307F-182B-4285-B0AD-2A8330198525}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Sitko.Core.Kafka", "src\Sitko.Core.Kafka\Sitko.Core.Kafka.csproj", "{80293122-8ABD-4CE8-945B-B88AABE87241}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Sitko.Core.Tasks.Kafka", "src\Sitko.Core.Tasks.Kafka\Sitko.Core.Tasks.Kafka.csproj", "{E1F076AD-2741-4DCC-BA44-9015ED73C875}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Sitko.Core.Tasks.Kafka.Tests", "tests\Sitko.Core.Tasks.Kafka.Tests\Sitko.Core.Tasks.Kafka.Tests.csproj", "{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Expand Down Expand Up @@ -1497,6 +1505,54 @@ Global
{5D438687-8576-425A-A8A9-A80B893DCE0C}.Release|x64.Build.0 = Release|Any CPU
{5D438687-8576-425A-A8A9-A80B893DCE0C}.Release|x86.ActiveCfg = Release|Any CPU
{5D438687-8576-425A-A8A9-A80B893DCE0C}.Release|x86.Build.0 = Release|Any CPU
{76EA307F-182B-4285-B0AD-2A8330198525}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{76EA307F-182B-4285-B0AD-2A8330198525}.Debug|Any CPU.Build.0 = Debug|Any CPU
{76EA307F-182B-4285-B0AD-2A8330198525}.Debug|x64.ActiveCfg = Debug|Any CPU
{76EA307F-182B-4285-B0AD-2A8330198525}.Debug|x64.Build.0 = Debug|Any CPU
{76EA307F-182B-4285-B0AD-2A8330198525}.Debug|x86.ActiveCfg = Debug|Any CPU
{76EA307F-182B-4285-B0AD-2A8330198525}.Debug|x86.Build.0 = Debug|Any CPU
{76EA307F-182B-4285-B0AD-2A8330198525}.Release|Any CPU.ActiveCfg = Release|Any CPU
{76EA307F-182B-4285-B0AD-2A8330198525}.Release|Any CPU.Build.0 = Release|Any CPU
{76EA307F-182B-4285-B0AD-2A8330198525}.Release|x64.ActiveCfg = Release|Any CPU
{76EA307F-182B-4285-B0AD-2A8330198525}.Release|x64.Build.0 = Release|Any CPU
{76EA307F-182B-4285-B0AD-2A8330198525}.Release|x86.ActiveCfg = Release|Any CPU
{76EA307F-182B-4285-B0AD-2A8330198525}.Release|x86.Build.0 = Release|Any CPU
{80293122-8ABD-4CE8-945B-B88AABE87241}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{80293122-8ABD-4CE8-945B-B88AABE87241}.Debug|Any CPU.Build.0 = Debug|Any CPU
{80293122-8ABD-4CE8-945B-B88AABE87241}.Debug|x64.ActiveCfg = Debug|Any CPU
{80293122-8ABD-4CE8-945B-B88AABE87241}.Debug|x64.Build.0 = Debug|Any CPU
{80293122-8ABD-4CE8-945B-B88AABE87241}.Debug|x86.ActiveCfg = Debug|Any CPU
{80293122-8ABD-4CE8-945B-B88AABE87241}.Debug|x86.Build.0 = Debug|Any CPU
{80293122-8ABD-4CE8-945B-B88AABE87241}.Release|Any CPU.ActiveCfg = Release|Any CPU
{80293122-8ABD-4CE8-945B-B88AABE87241}.Release|Any CPU.Build.0 = Release|Any CPU
{80293122-8ABD-4CE8-945B-B88AABE87241}.Release|x64.ActiveCfg = Release|Any CPU
{80293122-8ABD-4CE8-945B-B88AABE87241}.Release|x64.Build.0 = Release|Any CPU
{80293122-8ABD-4CE8-945B-B88AABE87241}.Release|x86.ActiveCfg = Release|Any CPU
{80293122-8ABD-4CE8-945B-B88AABE87241}.Release|x86.Build.0 = Release|Any CPU
{E1F076AD-2741-4DCC-BA44-9015ED73C875}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{E1F076AD-2741-4DCC-BA44-9015ED73C875}.Debug|Any CPU.Build.0 = Debug|Any CPU
{E1F076AD-2741-4DCC-BA44-9015ED73C875}.Debug|x64.ActiveCfg = Debug|Any CPU
{E1F076AD-2741-4DCC-BA44-9015ED73C875}.Debug|x64.Build.0 = Debug|Any CPU
{E1F076AD-2741-4DCC-BA44-9015ED73C875}.Debug|x86.ActiveCfg = Debug|Any CPU
{E1F076AD-2741-4DCC-BA44-9015ED73C875}.Debug|x86.Build.0 = Debug|Any CPU
{E1F076AD-2741-4DCC-BA44-9015ED73C875}.Release|Any CPU.ActiveCfg = Release|Any CPU
{E1F076AD-2741-4DCC-BA44-9015ED73C875}.Release|Any CPU.Build.0 = Release|Any CPU
{E1F076AD-2741-4DCC-BA44-9015ED73C875}.Release|x64.ActiveCfg = Release|Any CPU
{E1F076AD-2741-4DCC-BA44-9015ED73C875}.Release|x64.Build.0 = Release|Any CPU
{E1F076AD-2741-4DCC-BA44-9015ED73C875}.Release|x86.ActiveCfg = Release|Any CPU
{E1F076AD-2741-4DCC-BA44-9015ED73C875}.Release|x86.Build.0 = Release|Any CPU
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}.Debug|Any CPU.Build.0 = Debug|Any CPU
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}.Debug|x64.ActiveCfg = Debug|Any CPU
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}.Debug|x64.Build.0 = Debug|Any CPU
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}.Debug|x86.ActiveCfg = Debug|Any CPU
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}.Debug|x86.Build.0 = Debug|Any CPU
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}.Release|Any CPU.ActiveCfg = Release|Any CPU
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}.Release|Any CPU.Build.0 = Release|Any CPU
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}.Release|x64.ActiveCfg = Release|Any CPU
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}.Release|x64.Build.0 = Release|Any CPU
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}.Release|x86.ActiveCfg = Release|Any CPU
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5}.Release|x86.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(NestedProjects) = preSolution
{6677865F-C349-4D25-9E19-3DEC43E92DD5} = {109B331E-71B9-483C-8FC1-13B10C92A7F1}
Expand Down Expand Up @@ -1603,5 +1659,9 @@ Global
{910855FF-013F-4343-B4D1-27721CB65822} = {109B331E-71B9-483C-8FC1-13B10C92A7F1}
{5D54C212-07F4-46B6-B86D-EC9D7641ED19} = {10C46F0D-1B13-447E-AD22-F01DDB5A79FD}
{5D438687-8576-425A-A8A9-A80B893DCE0C} = {109B331E-71B9-483C-8FC1-13B10C92A7F1}
{76EA307F-182B-4285-B0AD-2A8330198525} = {109B331E-71B9-483C-8FC1-13B10C92A7F1}
{80293122-8ABD-4CE8-945B-B88AABE87241} = {109B331E-71B9-483C-8FC1-13B10C92A7F1}
{E1F076AD-2741-4DCC-BA44-9015ED73C875} = {109B331E-71B9-483C-8FC1-13B10C92A7F1}
{53AC3FA6-64D0-4D26-9F47-EC44A83B0DF5} = {10C46F0D-1B13-447E-AD22-F01DDB5A79FD}
EndGlobalSection
EndGlobal
11 changes: 11 additions & 0 deletions src/Directory.Packages.props
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
<ManagePackageVersionsCentrally>true</ManagePackageVersionsCentrally>
</PropertyGroup>
<ItemGroup>
<PackageVersion Include="Cronos" Version="0.7.1"/>
<PackageVersion Include="FluentValidation.DependencyInjectionExtensions" Version="11.7.1"/>
<PackageVersion Include="IL.FluentValidation.Extensions.Options" Version="11.0.2"/>
<PackageVersion Include="JetBrains.Annotations" Version="2023.2.0"/>
Expand Down Expand Up @@ -90,6 +91,16 @@
<PackageVersion Include="Microsoft.EntityFrameworkCore.InMemory" Version="7.0.10"/>
<PackageVersion Include="Npgsql.EntityFrameworkCore.PostgreSQL" Version="7.0.4"/>
</ItemGroup>
<!--Kafka libraries-->
<ItemGroup>
<PackageVersion Include="KafkaFlow" Version="2.4.1"/>
<PackageVersion Include="KafkaFlow.LogHandler.Microsoft" Version="2.4.1"/>
<PackageVersion Include="KafkaFlow.Microsoft.DependencyInjection" Version="2.4.1"/>
<PackageVersion Include="KafkaFlow.Serializer" Version="2.4.1"/>
<PackageVersion Include="KafkaFlow.Serializer.JsonCore" Version="2.4.1"/>
<PackageVersion Include="KafkaFlow.TypedHandler" Version="2.4.1"/>
<PackageVersion Include="KafkaFlow.Extensions.Hosting" Version="2.4.1"/>
</ItemGroup>
<!--Elastic libraries-->
<ItemGroup>
<PackageVersion Include="Elastic.Apm.NetCoreAll" Version="1.23.0"/>
Expand Down
5 changes: 5 additions & 0 deletions src/Sitko.Core.App/Application.cs
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,11 @@ protected void RegisterApplicationServices<TApplicationContext>(IApplicationCont
{
servicesConfigurationAction(applicationContext, services);
}

foreach (var moduleRegistration in GetEnabledModuleRegistrations(applicationContext))
{
moduleRegistration.PostConfigureServices(applicationContext, services);
}
}

protected void ConfigureConfiguration(IApplicationContext appContext, IConfigurationBuilder builder)
Expand Down
11 changes: 11 additions & 0 deletions src/Sitko.Core.App/ApplicationModuleRegistration.cs
Original file line number Diff line number Diff line change
Expand Up @@ -194,6 +194,14 @@ public override ApplicationModuleRegistration ConfigureServices(
return this;
}

public override ApplicationModuleRegistration PostConfigureServices(IApplicationContext context,
IServiceCollection services)
{
var options = CreateOptions(context, true);
instance.PostConfigureServices(context, services, options);
return this;
}

public override Task ApplicationStopped(IApplicationContext applicationContext,
IServiceProvider serviceProvider) =>
instance.ApplicationStopped(applicationContext, serviceProvider);
Expand Down Expand Up @@ -226,6 +234,9 @@ public abstract LoggerConfiguration ConfigureLogging(IApplicationContext context
public abstract ApplicationModuleRegistration ConfigureServices(IApplicationContext context,
IServiceCollection services);

public abstract ApplicationModuleRegistration PostConfigureServices(IApplicationContext context,
IServiceCollection services);

public abstract Task ApplicationStopped(IApplicationContext applicationContext,
IServiceProvider serviceProvider);

Expand Down
5 changes: 5 additions & 0 deletions src/Sitko.Core.App/BaseApplicationModule.cs
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,11 @@ public virtual void ConfigureServices(IApplicationContext applicationContext, IS
{
}

public virtual void PostConfigureServices(IApplicationContext applicationContext, IServiceCollection services,
TModuleOptions startupOptions)
{
}

public virtual Task InitAsync(IApplicationContext applicationContext, IServiceProvider serviceProvider) =>
Task.CompletedTask;

Expand Down
3 changes: 3 additions & 0 deletions src/Sitko.Core.App/IApplicationModule.cs
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,9 @@ namespace Sitko.Core.App;
void ConfigureServices(IApplicationContext applicationContext, IServiceCollection services,
TModuleOptions startupOptions);

void PostConfigureServices(IApplicationContext applicationContext, IServiceCollection services,
TModuleOptions startupOptions);

IEnumerable<Type> GetRequiredModules(IApplicationContext applicationContext, TModuleOptions options);
}

Expand Down
116 changes: 116 additions & 0 deletions src/Sitko.Core.Kafka/KafkaConfigurator.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,116 @@
using Confluent.Kafka;
using KafkaFlow;
using KafkaFlow.Configuration;
using KafkaFlow.Consumers.DistributionStrategies;

namespace Sitko.Core.Kafka;

public class KafkaConfigurator
{
private readonly Dictionary<ConsumerRegistration, Action<IConsumerConfigurationBuilder, ConsumerConfig>>
consumerActions = new();

private readonly HashSet<ConsumerRegistration> consumers = new();
private readonly string clusterName;
private readonly Dictionary<string, Action<IProducerConfigurationBuilder, ProducerConfig>> producerActions = new();
private readonly Dictionary<string, (int Partitions, short ReplicationFactor)> topics = new();
private bool ensureOffsets;

internal KafkaConfigurator(string clusterName) => this.clusterName = clusterName;

internal HashSet<ConsumerRegistration> Consumers => consumers;
internal bool NeedToEnsureOffsets => ensureOffsets;

public KafkaConfigurator AddProducer(string producerName,
Action<IProducerConfigurationBuilder, ProducerConfig> configure)
{
producerActions[producerName] = configure;
return this;
}

public KafkaConfigurator AddConsumer(string consumerName, string groupId, TopicInfo[] consumerTopics,
Action<IConsumerConfigurationBuilder, ConsumerConfig> configure)
{
var registration = new ConsumerRegistration(consumerName, groupId, consumerTopics);
consumers.Add(registration);
consumerActions[registration] = configure;
return this;
}

public KafkaConfigurator AutoCreateTopic(string topic, int partitions, short replicationFactor)
{
topics[topic] = (partitions, replicationFactor);
return this;
}

public KafkaConfigurator EnsureOffsets(bool enable = true)
{
ensureOffsets = enable;
return this;
}

public void Build(IKafkaConfigurationBuilder builder, KafkaModuleOptions options) =>
builder
.UseMicrosoftLog()
.AddCluster(clusterBuilder =>
{
clusterBuilder
.WithName(clusterName)
.WithBrokers(options.Brokers);
if (!ensureOffsets)
{
foreach (var (topic, config) in topics)
{
clusterBuilder.CreateTopicIfNotExists(topic, config.Partitions, config.ReplicationFactor);
}
}

foreach (var (producerName, configure) in producerActions)
{
clusterBuilder.AddProducer(producerName, producerBuilder =>
{
var producerConfig = new ProducerConfig
{
ClientId = producerName,
MessageTimeoutMs = (int)options.MessageTimeout.TotalMilliseconds,
MessageMaxBytes = options.MessageMaxBytes,
EnableIdempotence = options.EnableIdempotence,
SocketNagleDisable = options.SocketNagleDisable,
Acks = options.Acks
};
producerBuilder.WithProducerConfig(producerConfig);
producerBuilder.WithLingerMs(options.MaxProducingTimeout.TotalMilliseconds);
configure(producerBuilder, producerConfig);
});
}

foreach (var (registration, configureAction) in consumerActions)
{
clusterBuilder.AddConsumer(consumerBuilder =>
{
consumerBuilder.WithName(registration.Name);
consumerBuilder.Topics(registration.Topics.Select(info => info.Name));
consumerBuilder.WithGroupId(registration.GroupId);
consumerBuilder
.WithWorkDistributionStrategy<BytesSumDistributionStrategy>(); // guarantee events order
consumerBuilder.WithMaxPollIntervalMs((int)options.MaxPollInterval.TotalMilliseconds);
var consumerConfig = new ConsumerConfig
{
MaxPartitionFetchBytes = options.MaxPartitionFetchBytes,
AutoOffsetReset = options.AutoOffsetReset,
ClientId = registration.Name,
GroupInstanceId = registration.Name,
BootstrapServers = string.Join(",", options.Brokers),
SessionTimeoutMs = (int)options.SessionTimeout.TotalMilliseconds,
PartitionAssignmentStrategy = options.PartitionAssignmentStrategy
};
consumerBuilder.WithConsumerConfig(consumerConfig);
configureAction(consumerBuilder, consumerConfig);
});
}
});
}

internal record ConsumerRegistration(string Name, string GroupId, TopicInfo[] Topics);

public record TopicInfo(string Name, int PartitionsCount, short ReplicationFactor);
Loading

0 comments on commit bbe0ac1

Please sign in to comment.