Skip to content
Merged
Show file tree
Hide file tree
Changes from 11 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
34 changes: 34 additions & 0 deletions src/Aspire.Hosting.SqlServer/SqlServerBuilderExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -200,6 +200,40 @@ public static IResourceBuilder<SqlServerDatabaseResource> WithCreationScript(thi
return builder;
}

/// <summary>
/// TODO
/// </summary>
/// <param name="builder"></param>
/// <param name="password"></param>
/// <returns></returns>
public static IResourceBuilder<SqlServerServerResource> WithPassword(this IResourceBuilder<SqlServerServerResource> builder, IResourceBuilder<ParameterResource> password)
{
ArgumentNullException.ThrowIfNull(builder);
ArgumentNullException.ThrowIfNull(password);

var sqlserver = builder.Resource.WithPassword(password.Resource);
return builder.WithEnvironment(context =>
{
context.EnvironmentVariables["MSSQL_SA_PASSWORD"] = sqlserver.PasswordParameter;
});
}

/// <summary>
/// TODO
/// </summary>
/// <param name="builder"></param>
/// <param name="port"></param>
/// <returns></returns>
public static IResourceBuilder<SqlServerServerResource> WithHostPort(this IResourceBuilder<SqlServerServerResource> builder, int port)
{
ArgumentNullException.ThrowIfNull(builder);
return builder.WithEndpoint(SqlServerServerResource.PrimaryEndpointName, endpoint =>
{
endpoint.Port = port;
});

}

private static async Task CreateDatabaseAsync(SqlConnection sqlConnection, SqlServerDatabaseResource sqlDatabase, IServiceProvider serviceProvider, CancellationToken ct)
{
try
Expand Down
15 changes: 14 additions & 1 deletion src/Aspire.Hosting.SqlServer/SqlServerServerResource.cs
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ public SqlServerServerResource(string name, ParameterResource password) : base(n
/// <summary>
/// Gets the parameter that contains the SQL Server password.
/// </summary>
public ParameterResource PasswordParameter { get; }
public ParameterResource PasswordParameter { get; private set; }

private ReferenceExpression ConnectionString =>
ReferenceExpression.Create(
Expand Down Expand Up @@ -76,6 +76,19 @@ public ReferenceExpression ConnectionStringExpression
/// </summary>
public IReadOnlyDictionary<string, string> Databases => _databases;

/// <summary>
/// TODO
/// </summary>
/// <param name="password"></param>
/// <returns></returns>
public SqlServerServerResource WithPassword(ParameterResource password)
{
ArgumentNullException.ThrowIfNull(password);

PasswordParameter = password;
return this;
}

internal void AddDatabase(SqlServerDatabaseResource database)
{
_databases.TryAdd(database.Name, database.DatabaseName);
Expand Down
56 changes: 56 additions & 0 deletions tests/Aspire.Hosting.Azure.Tests/AzureSqlExtensionsTests.cs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.

using System.Net.Sockets;
using Aspire.Hosting.ApplicationModel;
using Aspire.Hosting.Utils;
using Xunit;
Expand Down Expand Up @@ -189,6 +190,61 @@ public async Task AddAzureSqlServerRunAsContainerProducesCorrectConnectionString
Assert.EndsWith(";TrustServerCertificate=true;Database=db2Name", db2ConnectionString);
}

[Theory]
[InlineData(true)]
[InlineData(false)]
public async Task AddAzureSqlServerRunAsContainerProducesCorrectPasswordAndPort(bool addDbBeforeRunAsContainer)
{
using var builder = TestDistributedApplicationBuilder.Create();

var sql = builder.AddAzureSqlServer("sql");
var pass = builder.AddParameter("pass", "p@ssw0rd1");
IResourceBuilder<AzureSqlDatabaseResource> db1 = null!;
IResourceBuilder<AzureSqlDatabaseResource> db2 = null!;
if (addDbBeforeRunAsContainer)
{
db1 = sql.AddDatabase("db1");
db2 = sql.AddDatabase("db2", "db2Name");

}

IResourceBuilder<SqlServerServerResource>? innerSql = null;
sql.RunAsContainer(configureContainer: c =>
{
c.WithEndpoint("tcp", e => e.AllocatedEndpoint = new AllocatedEndpoint(e, "localhost", 12455));
c.WithHostPort(12455)
.WithPassword(pass);
innerSql = c;
});

Assert.NotNull(innerSql);

if (!addDbBeforeRunAsContainer)
{
db1 = sql.AddDatabase("db1");
db2 = sql.AddDatabase("db2", "db2Name");
}

var endpoint = Assert.Single(innerSql.Resource.Annotations.OfType<EndpointAnnotation>());
Assert.Equal(1433, endpoint.TargetPort);
Assert.False(endpoint.IsExternal);
Assert.Equal("tcp", endpoint.Name);
Assert.Equal(12455, endpoint.Port);
Assert.Equal(ProtocolType.Tcp, endpoint.Protocol);
Assert.Equal("tcp", endpoint.Transport);
Assert.Equal("tcp", endpoint.UriScheme);

Assert.True(sql.Resource.IsContainer(), "The resource should now be a container resource.");
var serverConnectionString = await sql.Resource.ConnectionStringExpression.GetValueAsync(CancellationToken.None);
Assert.Equal("Server=127.0.0.1,12455;User ID=sa;Password=p@ssw0rd1;TrustServerCertificate=true", serverConnectionString);

var db1ConnectionString = await db1.Resource.ConnectionStringExpression.GetValueAsync(CancellationToken.None);
Assert.StartsWith("Server=127.0.0.1,12455;User ID=sa;Password=p@ssw0rd1;TrustServerCertificate=true;Database=db1", db1ConnectionString);

var db2ConnectionString = await db2.Resource.ConnectionStringExpression.GetValueAsync(CancellationToken.None);
Assert.StartsWith("Server=127.0.0.1,12455;User ID=sa;Password=p@ssw0rd1;TrustServerCertificate=true;Database=db2Name", db2ConnectionString);
}

[Theory]
[InlineData(true, true)]
[InlineData(true, false)]
Expand Down
Loading