diff --git a/Directory.Packages.props b/Directory.Packages.props
index d37617bbf..79222b5b3 100644
--- a/Directory.Packages.props
+++ b/Directory.Packages.props
@@ -57,7 +57,7 @@
-
+
diff --git a/src/Testcontainers/Configurations/WaitStrategies/RetryLimitExceededException.cs b/src/Testcontainers/Configurations/WaitStrategies/RetryLimitExceededException.cs
index 17b3621c0..8dd1f8420 100644
--- a/src/Testcontainers/Configurations/WaitStrategies/RetryLimitExceededException.cs
+++ b/src/Testcontainers/Configurations/WaitStrategies/RetryLimitExceededException.cs
@@ -1,4 +1,4 @@
-namespace DotNet.Testcontainers.Configurations
+namespace DotNet.Testcontainers.Configurations
{
using System;
diff --git a/src/Testcontainers/Containers/DockerContainer.cs b/src/Testcontainers/Containers/DockerContainer.cs
index d18658eec..3a6fbdffb 100644
--- a/src/Testcontainers/Containers/DockerContainer.cs
+++ b/src/Testcontainers/Containers/DockerContainer.cs
@@ -261,34 +261,34 @@ public Task GetExitCodeAsync(CancellationToken ct = default)
///
public virtual async Task StartAsync(CancellationToken ct = default)
{
- using (_ = AcquireLock())
- {
- var futureResources = Array.Empty()
- .Concat(_configuration.Mounts)
- .Concat(_configuration.Networks);
+ using var disposable = await AcquireLockAsync(ct)
+ .ConfigureAwait(false);
- await Task.WhenAll(futureResources.Select(resource => resource.CreateAsync(ct)))
- .ConfigureAwait(false);
+ var futureResources = Array.Empty()
+ .Concat(_configuration.Mounts)
+ .Concat(_configuration.Networks);
- await Task.WhenAll(_configuration.Containers.Select(resource => resource.StartAsync(ct)))
- .ConfigureAwait(false);
+ await Task.WhenAll(futureResources.Select(resource => resource.CreateAsync(ct)))
+ .ConfigureAwait(false);
- await UnsafeCreateAsync(ct)
- .ConfigureAwait(false);
+ await Task.WhenAll(_configuration.Containers.Select(resource => resource.StartAsync(ct)))
+ .ConfigureAwait(false);
- await UnsafeStartAsync(ct)
- .ConfigureAwait(false);
- }
+ await UnsafeCreateAsync(ct)
+ .ConfigureAwait(false);
+
+ await UnsafeStartAsync(ct)
+ .ConfigureAwait(false);
}
///
public virtual async Task StopAsync(CancellationToken ct = default)
{
- using (_ = AcquireLock())
- {
- await UnsafeStopAsync(ct)
- .ConfigureAwait(false);
- }
+ using var disposable = await AcquireLockAsync(ct)
+ .ConfigureAwait(false);
+
+ await UnsafeStopAsync(ct)
+ .ConfigureAwait(false);
}
///
@@ -344,7 +344,8 @@ protected override async ValueTask DisposeAsyncCore()
return;
}
- using (_ = AcquireLock())
+ using (_ = await AcquireLockAsync()
+ .ConfigureAwait(false))
{
if (Guid.Empty.Equals(_configuration.SessionId))
{
diff --git a/src/Testcontainers/Images/FutureDockerImage.cs b/src/Testcontainers/Images/FutureDockerImage.cs
index 6a48e787e..02271788b 100644
--- a/src/Testcontainers/Images/FutureDockerImage.cs
+++ b/src/Testcontainers/Images/FutureDockerImage.cs
@@ -77,21 +77,21 @@ public string GetHostname()
///
public async Task CreateAsync(CancellationToken ct = default)
{
- using (_ = AcquireLock())
- {
- await UnsafeCreateAsync(ct)
- .ConfigureAwait(false);
- }
+ using var disposable = await AcquireLockAsync(ct)
+ .ConfigureAwait(false);
+
+ await UnsafeCreateAsync(ct)
+ .ConfigureAwait(false);
}
///
public async Task DeleteAsync(CancellationToken ct = default)
{
- using (_ = AcquireLock())
- {
- await UnsafeDeleteAsync(ct)
- .ConfigureAwait(false);
- }
+ using var disposable = await AcquireLockAsync(ct)
+ .ConfigureAwait(false);
+
+ await UnsafeDeleteAsync(ct)
+ .ConfigureAwait(false);
}
///
diff --git a/src/Testcontainers/Networks/DockerNetwork.cs b/src/Testcontainers/Networks/DockerNetwork.cs
index 9c8086eaf..7db085d82 100644
--- a/src/Testcontainers/Networks/DockerNetwork.cs
+++ b/src/Testcontainers/Networks/DockerNetwork.cs
@@ -43,21 +43,21 @@ public string Name
///
public async Task CreateAsync(CancellationToken ct = default)
{
- using (_ = AcquireLock())
- {
- await UnsafeCreateAsync(ct)
- .ConfigureAwait(false);
- }
+ using var disposable = await AcquireLockAsync(ct)
+ .ConfigureAwait(false);
+
+ await UnsafeCreateAsync(ct)
+ .ConfigureAwait(false);
}
///
public async Task DeleteAsync(CancellationToken ct = default)
{
- using (_ = AcquireLock())
- {
- await UnsafeDeleteAsync(ct)
- .ConfigureAwait(false);
- }
+ using var disposable = await AcquireLockAsync(ct)
+ .ConfigureAwait(false);
+
+ await UnsafeDeleteAsync(ct)
+ .ConfigureAwait(false);
}
///
diff --git a/src/Testcontainers/Resource.cs b/src/Testcontainers/Resource.cs
index 7f5a4795b..d8d0a8c2d 100644
--- a/src/Testcontainers/Resource.cs
+++ b/src/Testcontainers/Resource.cs
@@ -60,9 +60,12 @@ protected virtual ValueTask DisposeAsyncCore()
///
/// Acquires a lock to access the resource thread-safe.
///
- /// An that releases the lock on .
- protected virtual IDisposable AcquireLock()
+ /// A that releases the lock on .
+ protected virtual async Task AcquireLockAsync(CancellationToken ct = default)
{
+ await _semaphoreSlim.WaitAsync(ct)
+ .ConfigureAwait(false);
+
return new Lock(_semaphoreSlim);
}
@@ -102,7 +105,6 @@ private sealed class Lock : IDisposable
public Lock(SemaphoreSlim semaphoreSlim)
{
_semaphoreSlim = semaphoreSlim;
- _semaphoreSlim.Wait();
}
public void Dispose()
diff --git a/src/Testcontainers/Testcontainers.csproj b/src/Testcontainers/Testcontainers.csproj
index 7280cbb10..1ee127eba 100644
--- a/src/Testcontainers/Testcontainers.csproj
+++ b/src/Testcontainers/Testcontainers.csproj
@@ -1,6 +1,7 @@
net6.0;net8.0;netstandard2.0;netstandard2.1
+ latest
Debug;Release
DotNet.Testcontainers
diff --git a/src/Testcontainers/Volumes/DockerVolume.cs b/src/Testcontainers/Volumes/DockerVolume.cs
index 2f0e44a4b..3062b44b0 100644
--- a/src/Testcontainers/Volumes/DockerVolume.cs
+++ b/src/Testcontainers/Volumes/DockerVolume.cs
@@ -43,21 +43,21 @@ public string Name
///
public async Task CreateAsync(CancellationToken ct = default)
{
- using (_ = AcquireLock())
- {
- await UnsafeCreateAsync(ct)
- .ConfigureAwait(false);
- }
+ using var disposable = await AcquireLockAsync(ct)
+ .ConfigureAwait(false);
+
+ await UnsafeCreateAsync(ct)
+ .ConfigureAwait(false);
}
///
public async Task DeleteAsync(CancellationToken ct = default)
{
- using (_ = AcquireLock())
- {
- await UnsafeDeleteAsync(ct)
- .ConfigureAwait(false);
- }
+ using var disposable = await AcquireLockAsync(ct)
+ .ConfigureAwait(false);
+
+ await UnsafeDeleteAsync(ct)
+ .ConfigureAwait(false);
}
///
diff --git a/tests/Testcontainers.Platform.Linux.Tests/WaitStrategyTest.cs b/tests/Testcontainers.Platform.Linux.Tests/WaitStrategyTest.cs
index 0bcddbb26..ad23a1cc6 100644
--- a/tests/Testcontainers.Platform.Linux.Tests/WaitStrategyTest.cs
+++ b/tests/Testcontainers.Platform.Linux.Tests/WaitStrategyTest.cs
@@ -1,4 +1,4 @@
-namespace Testcontainers.Tests;
+namespace Testcontainers.Tests;
public sealed class WaitStrategyTest
{