/flags/dotnet-cli/dotnet-build-configuration-release
dotnet build -c Release: build the Release configuration instead of Debug
- tool
- .NET CLI
- command
- dotnet build
- flag
- -c, --configuration NAME
- default
- Debug (Release for dotnet publish and dotnet pack since the .NET 8 SDK)
dotnet build -c Release (long form --configuration Release) compiles the project with the Release configuration: optimisations on, the DEBUG symbol not defined, output in bin/Release/<tfm>/. Without the flag, dotnet build, dotnet run and dotnet test use Debug. The option is shared by every build-related command (run, test, publish, pack, clean), and since the .NET 8 SDK publish and pack already default to Release.
Debug versus Release
dotnet new console -o app > /dev/null && cd app
cat > Program.cs <<'EOF'
#if DEBUG
Console.WriteLine("Debug build");
#else
Console.WriteLine("Release build");
#endif
EOF
dotnet build -v q -nologo > /dev/null
dotnet build -c Release -v q -nologo > /dev/null
ls bin
echo "--- dotnet run"
dotnet run
echo "--- dotnet run -c Release"
dotnet run -c ReleaseOutput
Debug Release --- dotnet run Debug build --- dotnet run -c Release Release build
Each configuration gets its own folder under bin (and obj), so both builds exist side by side. Code inside #if DEBUG is compiled only into the Debug build.
What changes with the configuration
| Setting | Debug | Release |
|---|---|---|
| Optimize (JIT-friendly IL) | false | true |
| DEBUG constant | defined | not defined |
| RELEASE constant | not defined | defined (SDK-style projects) |
| Output folder | bin/Debug/<tfm>/ | bin/Release/<tfm>/ |
| Debug.Assert / Debug.WriteLine | active | removed by the compiler |
| PDB symbols | portable PDB | portable PDB (still generated) |
Configuration-specific settings
<PropertyGroup Condition="'$(Configuration)' == 'Release'">
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
<DebugType>none</DebugType>
</PropertyGroup>Conditions on $(Configuration) apply settings only to one configuration. Typical uses are stricter warnings in Release CI builds or removing symbols from the shipped files.
Pitfalls
dotnet testafterdotnet build -c Release --no-buildmust use the same configuration, otherwise it looks inbin/Debugand finds nothing:dotnet test -c Release --no-build.- Benchmarks and performance measurements in Debug are meaningless; BenchmarkDotNet refuses to run non-optimised builds.
-c release(lowercase) works on Windows but creates a separatebin/releasefolder on case-sensitive file systems, and conditions comparing to'Release'do not match. Use the exact spelling.- In a folder with several projects or solutions, add the file name, otherwise the build fails with MSB1011.
Publishing a deployable app, including self-contained builds, is covered in dotnet publish --self-contained.
FAQ
Does dotnet publish use Release by default?
Since the .NET 8 SDK, yes for projects targeting .NET 8 or later: dotnet publish and dotnet pack default to Release. dotnet build, dotnet run and dotnet test still default to Debug.
Where does dotnet build -c Release put the output?
In bin/Release/<target framework>/, for example bin/Release/net10.0/. Debug builds go to bin/Debug/<target framework>/. Use -o to choose another folder.
Can I use other configuration names?
Yes. -c accepts any name, such as Staging; MSBuild sets the Configuration property and the DEBUG and RELEASE symbols only for the two standard names, so define your own symbols for custom configurations.