Logo

dev-resources.site

for different kinds of informations.

Getting started with .Net Aspire

Published at
11/27/2024
Categories
dotnet
aspire
visualstudio
Author
funkysi1701
Categories
3 categories in total
dotnet
open
aspire
open
visualstudio
open
Author
11 person written this
funkysi1701
open
Getting started with .Net Aspire

What is .Net Aspire?

.Net Aspire is a comprehensive set of tools, templates, and packages designed to simplify the development of cloud-native applications using .Net. It focuses on building observable, production-ready apps by providing a consistent and opinionated set of tools and patterns.

The key features of .Net Aspire:

  • Orchestration: Enhances the local development experience by simplifying the management of your appโ€™s configuration and interconnections. It helps with app composition, service discovery, and connection string management.
  • Integrations: Offers NuGet packages for commonly used services like Redis and Postgres, ensuring they connect consistently and seamlessly with your app.
  • Tooling: Comes with project templates and tooling experiences for Visual Studio, Visual Studio Code, and the .Net CLI to help you create and interact with .Net Aspire projects.

Overall, .Net Aspire aims to improve the experience of building .Net cloud-native apps by providing a robust framework for developing distributed applications.

Aspire

Getting started with .Net Aspire

I touched on .Net Aspire last week, when I talked about what was new in dotnet 9, but letโ€™s walk through an example.

Lets say you have a simple application. It has a Blazor web front end, it communicates with a .Net API and that API retrieves data from a SQL Server database. Before Aspire came along I would create a docker compose file and configure ports so the FE could call the API, and add connection strings so the API could access the database.

services:
  Api:
    image: ${DOCKER_REGISTRY-}api
    container_name: api
    ports:
      - 12345:80
      - 44338:443
    networks:
      - my-network
    build:
      context: .
      dockerfile: API/Dockerfile
    depends_on:
      - sqlserver

  Ui:
    image: ${DOCKER_REGISTRY-}ui
    container_name: ui
    ports:
      - 44330:443
    networks:
      - my-network
    build:
      context: .
      dockerfile: UI/Dockerfile
    environment:
      - APIPath=http://Api:80

  sqlserver:
    image: ${DOCKER_REGISTRY-}sql
    container_name: sql
    volumes:
      - sqlvol:/var/opt/mssql
    ports:
      - "5432:1433"
    networks:
      - my-network
    build:
      context: .
      dockerfile: Database/Dockerfile

Enter fullscreen mode Exit fullscreen mode

As you can see from this docker compose file, there is a lot of specifying ports and other plumbing to get these three parts of my system to work together.

Now in Visual Studio, right-click on the API project and select add .Net Aspire Orchestrator Support this will add two new Visual Studio projects to the solution, AppHost and ServiceDefaults.

  • AppHost is where you configure what service depends on what, you can configure all sorts of different dependencies, like databases (sql server, mysql, postgres etc), rabbitmq, redis and many others.
  • ServiceDefaults is where you configure the defaults for your services, like how opentelemetry should be configured, or how logging should work.

Now right click on the Blazor project and select the same option to get that wired up as well.

var builder = DistributedApplication.CreateBuilder(args);

builder.AddProject<Projects.UI>("ui");

builder.AddProject<Projects.API>("api");

builder.Build().Run();

Enter fullscreen mode Exit fullscreen mode

Your Program.cs file inside your AppHost project will look something like this now, with both your API and UI/Blazor projects referenced.

There is one more component we need to wire up, but we donโ€™t have a project to right click on for the database. It is fairly straightforward to do, update it to look like the following:

var builder = DistributedApplication.CreateBuilder(args);

var sqldb = builder.AddSqlServer("sql")
    .WithDataVolume("sql-data")
    .AddDatabase("Context", "Project");

var api = builder.AddProject<Projects.API>("api")
    .WaitFor(sqldb)
    .WithReference(sqldb);

builder.AddProject<Projects.UI>("ui")
    .WaitFor(api)
    .WithReference(api);

await builder.Build().RunAsync();

Enter fullscreen mode Exit fullscreen mode

You also need to install a couple of nuget packages. Aspire.Hosting.SqlServer and Aspire.Microsoft.EntityFrameworkCore.SqlServer the second one is because my project is using Entity Framework. Lets look at what we have, we are defining a SQL Server called sql, with a data volume called sql-data, and a database called Project, which we can refer to as Context. We then configure API to reference the sql server we have just configured, and wait for sql server to be ready before starting the API. Next the Blazor project depends on the API and will wait for that to be ready before starting. Pretty powerful stuff.

OK lets look at the API project, what do I need to configure in my connectionstrings? Not much, Aspire will fill all of this in for you.

  "ConnectionStrings": {
    "Context": ""
  }

Enter fullscreen mode Exit fullscreen mode

In your API project, your Program.cs will need a nuget package Aspire.Microsoft.EntityFrameworkCore.SqlServer and the following line, and no need for any pulling config and passing in connection strings.

builder.AddSqlServerDbContext<Context>("Context");

Enter fullscreen mode Exit fullscreen mode

One more clever thing we can do with Aspire is seed some data into my database before starting the project. Update the code that sets up your database in the AppHost project as follows.

var sqldb = builder.AddSqlServer("sql")
    .WithBindMount("./sqlserverconfig", "/usr/config")
    .WithBindMount("../API/data/sqlserver", "/docker-entrypoint-initdb.d")
    .WithEntrypoint("/usr/config/entrypoint.sh")
    .WithDataVolume("sql-data")
    .AddDatabase("Context", "Project")

Enter fullscreen mode Exit fullscreen mode

Add a sqlserverconfig folder inside your AppHost project and add the following two files. I have found entrypoint.sh being a bit picky with its line endings (windows vs linux)

#!/bin/bash

# Adapted from: https://github.com/microsoft/mssql-docker/blob/80e2a51d0eb1693f2de014fb26d4a414f5a5add5/linux/preview/examples/mssql-customize/entrypoint.sh

# Start the script to create the DB and user
/usr/config/configure-db.sh &

# Start SQL Server
/opt/mssql/bin/sqlservr


#!/bin/bash

# set -x

# Adapted from: https://github.com/microsoft/mssql-docker/blob/80e2a51d0eb1693f2de014fb26d4a414f5a5add5/linux/preview/examples/mssql-customize/configure-db.sh

# Wait 60 seconds for SQL Server to start up by ensuring that
# calling SQLCMD does not return an error code, which will ensure that sqlcmd is accessible
# and that system and user databases return "0" which means all databases are in an "online" state
# https://docs.microsoft.com/en-us/sql/relational-databases/system-catalog-views/sys-databases-transact-sql?view=sql-server-2017

dbstatus=1
errcode=1
start_time=$SECONDS
end_by=$((start_time + 60))

echo "Starting check for SQL Server start-up at $start_time, will end at $end_by"

while [[$SECONDS -lt $end_by && ( $errcode -ne 0 || ( -z "$dbstatus" || $dbstatus -ne 0 ) )]]; do
    dbstatus="$(/opt/mssql-tools18/bin/sqlcmd -h -1 -t 1 -U sa -P "$MSSQL_SA_PASSWORD" -C -Q "SET NOCOUNT ON; Select SUM(state) from sys.databases")"
    errcode=$?
    sleep 1
done

elapsed_time=$((SECONDS - start_time))
echo "Stopped checking for SQL Server start-up after $elapsed_time seconds (dbstatus=$dbstatus,errcode=$errcode,seconds=$SECONDS)"

if [[$dbstatus -ne 0]] || [[$errcode -ne 0]]; then
    echo "SQL Server took more than 60 seconds to start up or one or more databases are not in an ONLINE state"
    echo "dbstatus = $dbstatus"
    echo "errcode = $errcode"
    exit 1
fi

# Loop through the .sql files in the /docker-entrypoint-initdb.d and execute them with sqlcmd
for f in /docker-entrypoint-initdb.d/*.sql
do
    echo "Processing $f file..."
    /opt/mssql-tools18/bin/sqlcmd -S localhost -U sa -P "$MSSQL_SA_PASSWORD" -C -d master -i "$f"
done

Enter fullscreen mode Exit fullscreen mode

The second BindMount line mounts a folder inside your API project, so add a data folder with a subfolder called sqlserver. Inside that add a sql script called init.sql. Put all your CREATE DATABASE and CREATE TABLES sql commands inside this. And if everything works you will have a seeded DB ready to test your application with.

Conclusion

This is just a few things I have done with Aspire. Go check out the docs on MS learn or the some of the sessions from dotnet conf.

visualstudio Article's
30 articles in total
Favicon
Can Skater's Secure Depot of Private Keys be used as a tool designed for securely storing and managing private keys?
Favicon
Code Protection
Favicon
How to use OpenMP to parallelize C++ using Visual studio
Favicon
Getting started with .Net Aspire
Favicon
Integrating OpenCV with Visual Studio C++
Favicon
Version 9 of .Net is here
Favicon
EasyTdd 0.5.0: Streamlining Mocking with Incremental FluentMock
Favicon
From Legacy to .NET 8: Migrating with NDepend
Favicon
LocalDb Dev on Windows11 ARM
Favicon
How to create custom snippets in Visual Studio 2022
Favicon
Builder: Your Buddy in Test-Driven Development (TDD)
Favicon
AutoEntityGenerator โ€“ my first visual studio extension.
Favicon
C# | Visual Studio Extensions for C# Developers
Favicon
SonarQube | Working with SonarLint and SonarQube in Visual Studio
Favicon
Migrating a project from Visual studio to Rider
Favicon
How to embed your git bash into Visual Studio
Favicon
.NET Monthly Roundup - May 2024 - .NET at Build, .NET Aspire GA, and more!
Favicon
Quick Tipp: Dev Tunnels with Visual Studio
Favicon
EasyTdd 0.4.0 Release: Introducing the Incremental Builder
Favicon
Troubleshooting โ€œThe File Does Not Have an App Associated with Itโ€ Error in Visual Studio
Favicon
Help Needed: "Object reference not set to an instance of an object" Error in Visual Studio
Favicon
Debugging with Precision: Conditional Breakpoints
Favicon
Simple Way To CreateYour NuGet Package: Step-by-Step Guide
Favicon
Easy Self-Hosted Git Installation on Ubuntu Server
Favicon
Effortless Remote Debugging with Dev Tunnel in Visual Studio 2022
Favicon
How to Use GitHub Copilot in Visual Studio 2024
Favicon
How to Enable Windows 11 Developer Mode?
Favicon
Visual Studio Live Share: Complete Guide 2024
Favicon
Gitlens Tutorial - Visual Studio Extension 2024
Favicon
Top 8 Best Visual Studio Extensions in 2024

Featured ones: