Set up Go apps in the AppHost
Dette indhold er ikke tilgængeligt i dit sprog endnu.
This article is the reference for the Aspire Go hosting integration. It enumerates the AppHost APIs — with examples for both AppHost.cs and apphost.mts — that you use to orchestrate Go applications in your AppHost project.
If you’re new to the Go integration, start with the Get started with the Go integration guide.
Installation
Section titled “Installation”To start building an Aspire app that uses Go, install the 📦 Aspire.Hosting.Go NuGet package:
aspire add goLearn more about aspire add in the
command reference.
Or, choose a manual installation approach:
#:package Aspire.Hosting.Go@*<PackageReference Include="Aspire.Hosting.Go" Version="*" />aspire add goLearn more about aspire add in the
command reference.
This updates your aspire.config.json with the Go hosting integration package:
{ "packages": { "Aspire.Hosting.Go": "13.4.0" }}Add Go app
Section titled “Add Go app”Use AddGoApp / addGoApp to add a Go application to your AppHost. By default, Aspire runs go run . from the application directory.
var builder = DistributedApplication.CreateBuilder(args);
var api = builder.AddGoApp("api", "./api") .WithHttpEndpoint(port: 8080, env: "PORT") .WithExternalHttpEndpoints();
builder.Build().Run();import { createBuilder } from './.aspire/modules/aspire.mjs';
const builder = await createBuilder();
const api = await builder.addGoApp('api', './api');await api.withHttpEndpoint({ port: 8080, env: 'PORT' });await api.withExternalHttpEndpoints();
await builder.build().run();The method accepts the following common parameters:
- name: The name of the resource in the Aspire dashboard.
- appDirectory: The path to the Go module root. This directory usually contains
go.modand is also the Docker build context for deployment targets that emit container build artifacts. - packagePath: The Go package to run or build relative to
appDirectory. Defaults to".".
Go applications commonly read the PORT environment variable set by WithHttpEndpoint / withHttpEndpoint:
package main
import ( "fmt" "log" "net/http" "os")
func main() { port := os.Getenv("PORT") if port == "" { port = "8080" }
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { fmt.Fprintln(w, "Hello from Go!") })
log.Printf("Listening on :%s", port) log.Fatal(http.ListenAndServe(":"+port, nil))}Configure app directory and package path
Section titled “Configure app directory and package path”Use appDirectory for the Go module root, and use packagePath when the main package is under a subdirectory such as cmd/server.
For a common layout like this:
api/|-- go.mod|-- internal/`-- cmd/ `-- server/ `-- main.goConfigure the AppHost to run go run ./cmd/server from ./api:
var builder = DistributedApplication.CreateBuilder(args);
var api = builder.AddGoApp( name: "api", appDirectory: "./api", packagePath: "./cmd/server") .WithHttpEndpoint(env: "PORT");
builder.Build().Run();import { createBuilder } from './.aspire/modules/aspire.mjs';
const builder = await createBuilder();
const api = await builder.addGoApp('api', './api', { packagePath: './cmd/server',});await api.withHttpEndpoint({ env: 'PORT' });
await builder.build().run();The same packagePath is used for local run mode, headless Delve debugging, and publish-time go build.
Configure build options
Section titled “Configure build options”Go build-time options are parameters on AddGoApp / addGoApp. Aspire passes them to go run during local development and to go build when it generates a Dockerfile for publish.
var builder = DistributedApplication.CreateBuilder(args);
var api = builder.AddGoApp( name: "api", appDirectory: "./api", packagePath: "./cmd/server", buildTags: ["netgo", "integration"], ldFlags: "-X main.version=1.2.3 -s -w", gcFlags: "all=-N -l", raceDetector: true);
builder.Build().Run();import { createBuilder } from './.aspire/modules/aspire.mjs';
const builder = await createBuilder();
const api = await builder.addGoApp('api', './api', { packagePath: './cmd/server', buildTags: ['netgo', 'integration'], ldFlags: '-X main.version=1.2.3 -s -w', gcFlags: 'all=-N -l', raceDetector: true,});
await builder.build().run();The options map to Go command-line flags:
buildTags: Adds-tags=<tag1>,<tag2>.ldFlags: Adds-ldflags=<value>.gcFlags: Adds-gcflags=<value>.raceDetector: Adds-racein local run mode. The generated Dockerfile excludes-racebecause race detection requires CGO and publish builds create a static Linux binary.
Pass app arguments
Section titled “Pass app arguments”Use WithAppArgs / withAppArgs to pass arguments to the Go program after the package path.
var builder = DistributedApplication.CreateBuilder(args);
var api = builder.AddGoApp("api", "./api") .WithAppArgs("--config", "dev.yaml") .WithHttpEndpoint(env: "PORT");
builder.Build().Run();import { createBuilder } from './.aspire/modules/aspire.mjs';
const builder = await createBuilder();
const api = await builder.addGoApp('api', './api');await api.withAppArgs(['--config', 'dev.yaml']);await api.withHttpEndpoint({ env: 'PORT' });
await builder.build().run();In normal run mode, this produces a command like go run . --config dev.yaml. In headless Delve mode, Aspire passes the app arguments after Delve’s -- separator.
Run Go module helper commands
Section titled “Run Go module helper commands”The Go integration can run common module and static analysis commands before the app starts. These helpers create setup resources in run mode and make the Go app wait for them to complete.
var builder = DistributedApplication.CreateBuilder(args);
var api = builder.AddGoApp("api", "./api") .WithModTidy() .WithModVendor() .WithModDownload() .WithVetTool() .WithHttpEndpoint(env: "PORT");
builder.Build().Run();import { createBuilder } from './.aspire/modules/aspire.mjs';
const builder = await createBuilder();
const api = await builder.addGoApp('api', './api');await api.withModTidy();await api.withModVendor();await api.withModDownload();await api.withVetTool();await api.withHttpEndpoint({ env: 'PORT' });
await builder.build().run();The helper methods run these commands:
WithModTidy/withModTidy: Runsgo mod tidy -e.WithModVendor/withModVendor: Runsgo mod vendor.WithModDownload/withModDownload: Runsgo mod download.WithVetTool/withVetTool: Runsgo vet ./....
When multiple module helpers are configured, Aspire orders them so dependency-changing steps complete before later module cache or vendor steps.
Debug Go apps
Section titled “Debug Go apps”VS Code debugging
Section titled “VS Code debugging”Go app resources automatically support VS Code debugging when the Go extension for Visual Studio Code (golang.go) is installed.
The Aspire VS Code extension detects the golang.go extension and, when you start your AppHost in debug mode, launches the Go debugger via dlv-dap. No additional configuration is required beyond AddGoApp / addGoApp. Any buildTags, ldFlags, or gcFlags configured on the resource are automatically forwarded to Delve as build flags, so the debugger compiles your program with the same flags used during normal development.
Headless Delve server
Section titled “Headless Delve server”For GoLand, VS Code attach mode, or another Delve-compatible client, use WithDelveServer / withDelveServer. This replaces the application command with a headless Delve server, such as dlv --headless=true --listen=127.0.0.1:2345 --api-version=2 debug ..
var builder = DistributedApplication.CreateBuilder(args);
var api = builder.AddGoApp("api", "./api") .WithDelveServer(port: 2345) .WithHttpEndpoint(port: 8080, env: "PORT");
builder.Build().Run();import { createBuilder } from './.aspire/modules/aspire.mjs';
const builder = await createBuilder();
const api = await builder.addGoApp('api', './api');await api.withDelveServer({ port: 2345 });await api.withHttpEndpoint({ port: 8080, env: 'PORT' });
await builder.build().run();Start your attach configuration after the Go resource is running in the Aspire dashboard. For GoLand, create a Go Remote configuration with host localhost and port 2345. For VS Code attach mode, add a launch configuration like this:
{ "name": "Attach to api", "type": "go", "request": "attach", "mode": "remote", "host": "localhost", "port": 2345}Publish Go apps
Section titled “Publish Go apps”When a publisher or deployment target emits container build artifacts for a Go app, Aspire uses the appDirectory as the Docker build context:
- If the app directory already contains a
Dockerfile, Aspire uses it. - If no
Dockerfileexists, Aspire generates a multi-stage Dockerfile. - The generated Dockerfile uses a
golang:<version>-alpinebuild image by default. Aspire detects the Go version fromgo.mod, preferring atoolchaindirective over thegodirective when both are present. - The build stage runs
go mod download, caches the module and build caches, and builds a static Linux binary withCGO_ENABLED=0andGOOS=linux. - The runtime stage uses a small runtime image, installs certificate and time zone data for Alpine-based images, creates a non-root
appuser, and starts the compiled binary. - The generated
go buildcommand uses the samepackagePath,buildTags,ldFlags, andgcFlagsconfigured on the Go app resource. It intentionally excludesraceDetectorfor publish builds.
For private modules, use WithGoPrivate / withGoPrivate to configure the generated Dockerfile with GOPRIVATE and BuildKit secret-based authentication. This setting only affects generated Dockerfiles; local run mode continues to use the developer’s local Go and Git credentials.
var builder = DistributedApplication.CreateBuilder(args);
var api = builder.AddGoApp("api", "./api") .WithGoPrivate(["github.com/myorg"], "github.com");
builder.Build().Run();import { createBuilder } from './.aspire/modules/aspire.mjs';
const builder = await createBuilder();
const api = await builder.addGoApp('api', './api');await api.withGoPrivate(['github.com/myorg'], 'github.com');
await builder.build().run();For more information about publishing Aspire apps, see Deployment overview.
Experimental Go AppHost templates
Section titled “Experimental Go AppHost templates”The Aspire.Hosting.Go integration can be used from C# and TypeScript AppHosts. Aspire also includes experimental Go AppHost and Go starter template support in the Aspire CLI. The Go AppHost templates use experimental Go AppHost APIs instead of the Aspire.Hosting.Go package. To enable Go AppHost language support for CLI templates, enable the Go polyglot feature flag:
aspire config set features:experimentalPolyglot:go true --globalAfter enabling the feature, you can create a Go starter app with:
aspire new aspire-go-starterFor more information about feature flags, see Aspire CLI
configuration.
For template command details, see aspire new.