Skip to content

Commit 1dd91bd

Browse files
mocsharpdependabot[bot]lillie-dae
authored
Merge release/0.2.5 into main
* Storage service extension for health check service (#46) * Add health check for MinIO * Update packages & licenses Signed-off-by: Victor Chang <vicchang@nvidia.com> * Bump codecov/codecov-action from 2 to 3 (#37) Bumps [codecov/codecov-action](https://github.com/codecov/codecov-action) from 2 to 3. - [Release notes](https://github.com/codecov/codecov-action/releases) - [Changelog](https://github.com/codecov/codecov-action/blob/master/CHANGELOG.md) - [Commits](codecov/codecov-action@v2...v3) --- updated-dependencies: - dependency-name: codecov/codecov-action dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] <support@github.com> Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> * Bump actions/setup-dotnet from 1 to 2 (#36) Bumps [actions/setup-dotnet](https://github.com/actions/setup-dotnet) from 1 to 2. - [Release notes](https://github.com/actions/setup-dotnet/releases) - [Commits](actions/setup-dotnet@v1...v2) --- updated-dependencies: - dependency-name: actions/setup-dotnet dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] <support@github.com> Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> * Bump jungwinter/split from 1 to 2 (#31) Bumps [jungwinter/split](https://github.com/jungwinter/split) from 1 to 2. - [Release notes](https://github.com/jungwinter/split/releases) - [Commits](winterjung/split@v1...v2) --- updated-dependencies: - dependency-name: jungwinter/split dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] <support@github.com> Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> * Bump gittools/actions from 0.9.11 to 0.9.13 (#33) Bumps [gittools/actions](https://github.com/gittools/actions) from 0.9.11 to 0.9.13. - [Release notes](https://github.com/gittools/actions/releases) - [Commits](GitTools/actions@v0.9.11...v0.9.13) --- updated-dependencies: - dependency-name: gittools/actions dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] <support@github.com> Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> * Bump actions/setup-java from 1 to 3 (#34) Bumps [actions/setup-java](https://github.com/actions/setup-java) from 1 to 3. - [Release notes](https://github.com/actions/setup-java/releases) - [Commits](actions/setup-java@v1...v3) --- updated-dependencies: - dependency-name: actions/setup-java dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] <support@github.com> Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> * Bump actions/checkout from 2 to 3 (#51) Bumps [actions/checkout](https://github.com/actions/checkout) from 2 to 3. - [Release notes](https://github.com/actions/checkout/releases) - [Changelog](https://github.com/actions/checkout/blob/main/CHANGELOG.md) - [Commits](actions/checkout@v2...v3) --- updated-dependencies: - dependency-name: actions/checkout dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] <support@github.com> Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> * Bump actions/download-artifact from 2 to 3 (#48) Bumps [actions/download-artifact](https://github.com/actions/download-artifact) from 2 to 3. - [Release notes](https://github.com/actions/download-artifact/releases) - [Commits](actions/download-artifact@v2...v3) --- updated-dependencies: - dependency-name: actions/download-artifact dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] <support@github.com> Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> * Bump actions/upload-artifact from 2.3.1 to 3.1.0 (#49) Bumps [actions/upload-artifact](https://github.com/actions/upload-artifact) from 2.3.1 to 3.1.0. - [Release notes](https://github.com/actions/upload-artifact/releases) - [Commits](actions/upload-artifact@v2.3.1...v3.1.0) --- updated-dependencies: - dependency-name: actions/upload-artifact dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] <support@github.com> Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> * Bump actions/cache from 2.1.7 to 3.0.8 (#50) Bumps [actions/cache](https://github.com/actions/cache) from 2.1.7 to 3.0.8. - [Release notes](https://github.com/actions/cache/releases) - [Changelog](https://github.com/actions/cache/blob/main/RELEASES.md) - [Commits](actions/cache@v2.1.7...v3.0.8) --- updated-dependencies: - dependency-name: actions/cache dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] <support@github.com> Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> * Update ci.yml * Add minio admin heath check (#55) * add minio admin health check Signed-off-by: Lillie Dae <lillie.dae@answerdigital.com> * Fix typo * Allow enable/disable service/admin health checks Signed-off-by: Victor Chang <vicchang@nvidia.com> * Correct health check services Signed-off-by: Victor Chang <vicchang@nvidia.com> * Minio admin healthcheck fix (#61) (#62) * minor fixes to admin health checks Signed-off-by: Lillie Dae <lillie.dae@answerdigital.com> Signed-off-by: Lillie Dae <lillie.dae@answerdigital.com> Signed-off-by: Victor Chang <vicchang@nvidia.com> Signed-off-by: dependabot[bot] <support@github.com> Signed-off-by: Lillie Dae <lillie.dae@answerdigital.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Lillie Dae <61380713+lillie-dae@users.noreply.github.com>
1 parent 3ad46d0 commit 1dd91bd

9 files changed

+144
-47
lines changed

src/Plugins/MinIO/ConfigurationKeys.cs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,8 @@ namespace Monai.Deploy.Storage.MinIO
1818
{
1919
internal static class ConfigurationKeys
2020
{
21-
public static readonly string StorageServiceName = "minio";
21+
public static readonly string StorageServiceName = "MinIo";
22+
public static readonly string StorageAdminServiceName = "MinIo Admin";
2223

2324
public static readonly string EndPoint = "endpoint";
2425
public static readonly string AccessKey = "accessKey";

src/Plugins/MinIO/HealthCheckBuilder.cs

Lines changed: 10 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -23,37 +23,30 @@ namespace Monai.Deploy.Storage.MinIO
2323
{
2424
public class HealthCheckBuilder : HealthCheckRegistrationBase
2525
{
26-
public override IHealthChecksBuilder Configure(
27-
IHealthChecksBuilder builder,
28-
HealthStatus? failureStatus = null,
29-
IEnumerable<string>? tags = null,
30-
TimeSpan? timeout = null)
31-
{
26+
public override IHealthChecksBuilder ConfigureAdminHealthCheck(IHealthChecksBuilder builder, HealthStatus? failureStatus = null, IEnumerable<string>? tags = null, TimeSpan? timeout = null) =>
3227
builder.Add(new HealthCheckRegistration(
33-
ConfigurationKeys.StorageServiceName,
28+
$"{ConfigurationKeys.StorageAdminServiceName}",
3429
serviceProvider =>
3530
{
36-
var logger = serviceProvider.GetRequiredService<ILogger<MinIoHealthCheck>>();
37-
var minioClientFactory = serviceProvider.GetRequiredService<IMinIoClientFactory>();
38-
return new MinIoHealthCheck(minioClientFactory, logger);
31+
var logger = serviceProvider.GetRequiredService<ILogger<MinIoAdminHealthCheck>>();
32+
var storageAdminService = serviceProvider.GetRequiredService<IStorageAdminService>();
33+
return new MinIoAdminHealthCheck(storageAdminService, logger);
3934
},
4035
failureStatus,
4136
tags,
4237
timeout));
4338

39+
public override IHealthChecksBuilder ConfigureHealthCheck(IHealthChecksBuilder builder, HealthStatus? failureStatus = null, IEnumerable<string>? tags = null, TimeSpan? timeout = null) =>
4440
builder.Add(new HealthCheckRegistration(
45-
$"{ConfigurationKeys.StorageServiceName}-admin",
41+
ConfigurationKeys.StorageServiceName,
4642
serviceProvider =>
4743
{
48-
var logger = serviceProvider.GetRequiredService<ILogger<MinIoAdminHealthCheck>>();
49-
var storageAdminService = serviceProvider.GetRequiredService<IStorageAdminService>();
50-
return new MinIoAdminHealthCheck(storageAdminService, logger);
44+
var logger = serviceProvider.GetRequiredService<ILogger<MinIoHealthCheck>>();
45+
var minioClientFactory = serviceProvider.GetRequiredService<IMinIoClientFactory>();
46+
return new MinIoHealthCheck(minioClientFactory, logger);
5147
},
5248
failureStatus,
5349
tags,
5450
timeout));
55-
56-
return builder;
57-
}
5851
}
5952
}

src/Plugins/MinIO/LoggerMethods.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -20,8 +20,8 @@ namespace Monai.Deploy.Storage.MinIO
2020
{
2121
public static partial class LoggerMethods
2222
{
23-
[LoggerMessage(EventId = 20000, Level = LogLevel.Error, Message = "Error listing objects in bucket '{bucketName}'.")]
24-
public static partial void ListObjectError(this ILogger logger, string bucketName);
23+
[LoggerMessage(EventId = 20000, Level = LogLevel.Error, Message = "Error listing objects in bucket '{bucketName}' with error: {error}")]
24+
public static partial void ListObjectError(this ILogger logger, string bucketName, string error);
2525

2626
[LoggerMessage(EventId = 20001, Level = LogLevel.Error, Message = "File '{path}' could not be found in '{bucketName}'.")]
2727
public static partial void FileNotFoundError(this ILogger logger, string bucketName, string path);

src/Plugins/MinIO/MinIoStorageService.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -339,7 +339,7 @@ private async Task<IList<VirtualFileInfo>> ListObjectsUsingClient(MinioClient cl
339339
},
340340
error =>
341341
{
342-
_logger.ListObjectError(bucketName);
342+
_logger.ListObjectError(bucketName, error.Message);
343343
},
344344
() => completedEvent.Set(), cancellationToken);
345345

src/Plugins/MinIO/StorageAdminService.cs

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -169,17 +169,13 @@ private Process CreateProcess(string cmd)
169169
public async Task<bool> HasConnectionAsync()
170170
{
171171
var result = await GetConnectionAsync().ConfigureAwait(false);
172-
return result.Any(r => r.Equals(_serviceName));
172+
return result.Any(r => r.Trim().Equals(_serviceName));
173173
}
174174

175175
public async Task<List<string>> GetConnectionAsync() => await ExecuteAsync(_get_connections_cmd).ConfigureAwait(false);
176176

177177
public async Task<bool> SetConnectionAsync()
178178
{
179-
if (await HasConnectionAsync().ConfigureAwait(false))
180-
{
181-
return true;
182-
}
183179
var result = await ExecuteAsync(_set_connection_cmd).ConfigureAwait(false);
184180
if (result.Any(r => r.Contains($"Added `{_serviceName}` successfully.")))
185181
{

src/Plugins/MinIO/Tests/ServiceRegistrationTest.cs

Lines changed: 39 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
using System.Reflection;
1919
using Microsoft.Extensions.DependencyInjection;
2020
using Microsoft.Extensions.Diagnostics.HealthChecks;
21+
using Microsoft.Extensions.Options;
2122
using Moq;
2223
using Xunit;
2324

@@ -46,32 +47,66 @@ public void AddMonaiDeployStorageService_WhenCalled_RegisterServicesOnly()
4647
var serviceCollection = new Mock<IServiceCollection>();
4748
serviceCollection.Setup(p => p.Add(It.IsAny<ServiceDescriptor>()));
4849

49-
var returnedServiceCollection = serviceCollection.Object.AddMonaiDeployStorageService(_type.AssemblyQualifiedName, _fileSystem, false);
50+
var returnedServiceCollection = serviceCollection.Object.AddMonaiDeployStorageService(_type.AssemblyQualifiedName, _fileSystem, HealthCheckOptions.None);
5051

5152
Assert.Same(serviceCollection.Object, returnedServiceCollection);
5253

5354
serviceCollection.Verify(p => p.Add(It.IsAny<ServiceDescriptor>()), Times.Exactly(4));
5455
}
5556

5657
[Fact]
57-
public void AddMonaiDeployStorageService_WhenCalled_RegisterServicesAndHealthChecks()
58+
public void AddMonaiDeployStorageService_WhenCalled_RegisterServicesAndServiceHealthCheck()
59+
{
60+
var serviceCollection = new Mock<IServiceCollection>();
61+
62+
serviceCollection.Setup(p => p.Add(It.IsAny<ServiceDescriptor>()));
63+
serviceCollection.Setup(p => p.Add(It.Is<ServiceDescriptor>(p => p.ServiceType == typeof(HealthCheckService))));
64+
65+
var returnedServiceCollection = serviceCollection.Object.AddMonaiDeployStorageService(_type.AssemblyQualifiedName, _fileSystem, HealthCheckOptions.ServiceHealthCheck);
66+
Assert.Same(serviceCollection.Object, returnedServiceCollection);
67+
68+
serviceCollection.Verify(p => p.Add(It.IsAny<ServiceDescriptor>()), Times.AtLeast(5));
69+
serviceCollection.Verify(p => p.Add(It.Is<ServiceDescriptor>(p => p.ServiceType == typeof(HealthCheckService))), Times.Once());
70+
serviceCollection.Verify(p => p.Add(It.Is<ServiceDescriptor>(p => p.ServiceType == typeof(IConfigureOptions<HealthCheckServiceOptions>))), Times.Once());
71+
}
72+
73+
[Fact]
74+
public void AddMonaiDeployStorageService_WhenCalled_RegisterServicesAndHealthCheck()
5875
{
5976
var serviceCollection = new Mock<IServiceCollection>();
77+
6078
serviceCollection.Setup(p => p.Add(It.IsAny<ServiceDescriptor>()));
79+
serviceCollection.Setup(p => p.Add(It.Is<ServiceDescriptor>(p => p.ServiceType == typeof(HealthCheckService))));
6180

62-
var returnedServiceCollection = serviceCollection.Object.AddMonaiDeployStorageService(_type.AssemblyQualifiedName, _fileSystem, true);
81+
var returnedServiceCollection = serviceCollection.Object.AddMonaiDeployStorageService(_type.AssemblyQualifiedName, _fileSystem, HealthCheckOptions.AdminServiceHealthCheck);
82+
Assert.Same(serviceCollection.Object, returnedServiceCollection);
83+
84+
serviceCollection.Verify(p => p.Add(It.IsAny<ServiceDescriptor>()), Times.AtLeast(5));
85+
serviceCollection.Verify(p => p.Add(It.Is<ServiceDescriptor>(p => p.ServiceType == typeof(HealthCheckService))), Times.Once());
86+
serviceCollection.Verify(p => p.Add(It.Is<ServiceDescriptor>(p => p.ServiceType == typeof(IConfigureOptions<HealthCheckServiceOptions>))), Times.Once());
87+
}
88+
89+
[Fact]
90+
public void AddMonaiDeployStorageService_WhenCalled_RegisterServicesAndHealthChecks()
91+
{
92+
var serviceCollection = new Mock<IServiceCollection>();
6393

94+
serviceCollection.Setup(p => p.Add(It.IsAny<ServiceDescriptor>()));
95+
serviceCollection.Setup(p => p.Add(It.Is<ServiceDescriptor>(p => p.ServiceType == typeof(HealthCheckService))));
96+
97+
var returnedServiceCollection = serviceCollection.Object.AddMonaiDeployStorageService(_type.AssemblyQualifiedName, _fileSystem, HealthCheckOptions.ServiceHealthCheck | HealthCheckOptions.AdminServiceHealthCheck);
6498
Assert.Same(serviceCollection.Object, returnedServiceCollection);
6599

66100
serviceCollection.Verify(p => p.Add(It.IsAny<ServiceDescriptor>()), Times.AtLeast(5));
67101
serviceCollection.Verify(p => p.Add(It.Is<ServiceDescriptor>(p => p.ServiceType == typeof(HealthCheckService))), Times.Once());
102+
serviceCollection.Verify(p => p.Add(It.Is<ServiceDescriptor>(p => p.ServiceType == typeof(IConfigureOptions<HealthCheckServiceOptions>))), Times.Exactly(2));
68103
}
69104

70105
private static byte[] GetAssemblyeBytes(Assembly assembly)
71106
{
72107
return File.ReadAllBytes(assembly.Location);
73108
}
74109
}
110+
}
75111

76112
#pragma warning restore CS8604 // Possible null reference argument.
77-
}

src/Storage/HealthCheckRegistrationBase.cs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,13 @@ namespace Monai.Deploy.Storage
2121
{
2222
public abstract class HealthCheckRegistrationBase
2323
{
24-
public abstract IHealthChecksBuilder Configure(
24+
public abstract IHealthChecksBuilder ConfigureHealthCheck(
25+
IHealthChecksBuilder builder,
26+
HealthStatus? failureStatus = null,
27+
IEnumerable<string>? tags = null,
28+
TimeSpan? timeout = null);
29+
30+
public abstract IHealthChecksBuilder ConfigureAdminHealthCheck(
2531
IHealthChecksBuilder builder,
2632
HealthStatus? failureStatus = null,
2733
IEnumerable<string>? tags = null,

src/Storage/IServiceCollectionExtension.cs

Lines changed: 28 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,14 @@
2424

2525
namespace Monai.Deploy.Storage
2626
{
27+
[Flags]
28+
public enum HealthCheckOptions
29+
{
30+
None = 0,
31+
ServiceHealthCheck = 1,
32+
AdminServiceHealthCheck = 2,
33+
}
34+
2735
public static class IServiceCollectionExtensions
2836
{
2937
/// <summary>
@@ -36,11 +44,11 @@ public static class IServiceCollectionExtensions
3644
public static IServiceCollection AddMonaiDeployStorageService(
3745
this IServiceCollection services,
3846
string fullyQualifiedTypeName,
39-
bool registerHealthCheck = true,
47+
HealthCheckOptions healthCheckOptions = HealthCheckOptions.ServiceHealthCheck | HealthCheckOptions.AdminServiceHealthCheck,
4048
HealthStatus? failureStatus = null,
4149
IEnumerable<string>? tags = null,
4250
TimeSpan? timeout = null)
43-
=> AddMonaiDeployStorageService(services, fullyQualifiedTypeName, new FileSystem(), registerHealthCheck, failureStatus, tags, timeout);
51+
=> AddMonaiDeployStorageService(services, fullyQualifiedTypeName, new FileSystem(), healthCheckOptions, failureStatus, tags, timeout);
4452

4553
/// <summary>
4654
/// Configures all dependencies required for the MONAI Deploy Storage Service.
@@ -54,7 +62,7 @@ public static IServiceCollection AddMonaiDeployStorageService(
5462
this IServiceCollection services,
5563
string fullyQualifiedTypeName,
5664
IFileSystem fileSystem,
57-
bool registerHealthCheck = true,
65+
HealthCheckOptions healthCheckOptions = HealthCheckOptions.ServiceHealthCheck | HealthCheckOptions.AdminServiceHealthCheck,
5866
HealthStatus? failureStatus = null,
5967
IEnumerable<string>? tags = null,
6068
TimeSpan? timeout = null)
@@ -78,23 +86,26 @@ public static IServiceCollection AddMonaiDeployStorageService(
7886

7987
RegisterServices(services, fullyQualifiedTypeName, storageServiceAssembly);
8088

81-
if (registerHealthCheck)
82-
{
83-
RegisterHealtChecks(services, fullyQualifiedTypeName, storageServiceAssembly, failureStatus, tags, timeout);
84-
}
89+
RegisterHealtChecks(healthCheckOptions, services, fullyQualifiedTypeName, storageServiceAssembly, failureStatus, tags, timeout);
8590

8691
AppDomain.CurrentDomain.AssemblyResolve -= resolveEventHandler;
8792
return services;
8893
}
8994

9095
private static void RegisterHealtChecks(
96+
HealthCheckOptions healthCheckOptions,
9197
IServiceCollection services,
9298
string fullyQualifiedTypeName,
9399
Assembly storageServiceAssembly,
94100
HealthStatus? failureStatus = null,
95101
IEnumerable<string>? tags = null,
96102
TimeSpan? timeout = null)
97103
{
104+
if (healthCheckOptions == HealthCheckOptions.None)
105+
{
106+
return;
107+
}
108+
98109
var healthCheckBase = storageServiceAssembly.GetTypes().FirstOrDefault(p => p.IsSubclassOf(typeof(HealthCheckRegistrationBase)));
99110

100111
if (healthCheckBase is null || Activator.CreateInstance(healthCheckBase) is not HealthCheckRegistrationBase healthCheckBuilderBase)
@@ -103,7 +114,16 @@ private static void RegisterHealtChecks(
103114
}
104115

105116
var healthCheckBuilder = services.AddHealthChecks();
106-
healthCheckBuilderBase.Configure(healthCheckBuilder, failureStatus, tags, timeout);
117+
118+
if (healthCheckOptions.HasFlag(HealthCheckOptions.ServiceHealthCheck))
119+
{
120+
healthCheckBuilderBase.ConfigureHealthCheck(healthCheckBuilder, failureStatus, tags, timeout);
121+
}
122+
123+
if (healthCheckOptions.HasFlag(HealthCheckOptions.AdminServiceHealthCheck))
124+
{
125+
healthCheckBuilderBase.ConfigureAdminHealthCheck(healthCheckBuilder, failureStatus, tags, timeout);
126+
}
107127
}
108128

109129
private static void RegisterServices(IServiceCollection services, string fullyQualifiedTypeName, Assembly storageServiceAssembly)

0 commit comments

Comments
 (0)