Start Debugging

Сервер MSBuild включён по умолчанию в .NET 11 Preview 7

Preview 7 переводит сервер MSBuild из режима подключения по желанию во включённый по умолчанию, поэтому идущие подряд вызовы dotnet build и dotnet test переиспользуют прогретый рабочий процесс. Что изменилось, как отключить и как убедиться, что сервер действительно был задействован.

.NET 11 Preview 7 вышел 2026-08-11, и в разделе про SDK спрятано изменение значения по умолчанию, которое влияет на каждую вашу сборку: сервер MSBuild теперь включён, если вы явно его не отключите (dotnet/sdk#55231).

Сервер MSBuild поддерживает прогретый рабочий процесс MSBuild между вызовами CLI. Без него каждый dotnet build, dotnet test и dotnet run платит за запуск процесса MSBuild, прогрев JIT и разрешение SDK с нуля. С ним второй вызов и все последующие этого избегают. Эта возможность существовала за переключателем MSBUILDUSESERVER уже несколько релизов, и Preview 7 доводит дело до конца, делая включённое состояние значением по умолчанию.

Как отключить и какая переменная главнее

Отключить сервер можно двумя переменными окружения, и они не равнозначны:

# Either of these keeps the classic single-shot MSBuild behavior
export DOTNET_CLI_USE_MSBUILD_SERVER=false
export MSBUILDUSESERVER=0

DOTNET_CLI_USE_MSBUILD_SERVER=false теперь имеет приоритет. Она передаёт MSBUILDUSESERVER=0 дальше по стеку, поэтому сервер не может быть незаметно включён обратно файлом ответов, переменной MSBUILDFORCEMULTITHREADED=1 или передачей /mt (dotnet/sdk#55393). Если у вас есть этап CI, которому нужен гарантированно холодный процесс на каждую сборку, задавать следует именно её. Если задать только MSBUILDUSESERVER=0, остаётся возможность, что что-то ниже по стеку включит сервер снова.

Почему значение по умолчанию изменилось именно сейчас

Значение по умолчанию не изменилось само по себе. В Preview 7 сервер укрепили, потому что экспериментальный многопоточный режим сборки (-mt) считает его обязательным условием, и в том же релизе исправили несколько давних шероховатостей:

Наиболее заметен выигрыш в сборках с -mt, которые опираются на прогретый сервер ради состояния JIT и разрешения SDK. По данным панели производительности MSBuild, полная пересборка -t:Rebuild решения OrchardCore в среднем занимала на 26% меньше времени с -mt в Windows (со 146.2 с до 107.8 с) и на 23% меньше в Linux (со 118.8 с до 91.5 с).

Как убедиться, что сервер был задействован

Незаметный холодный старт выглядит точно так же, как тёплый, только медленнее. Preview 7 добавляет структурированное событие сборки MSBuildServerLifecycleEventArgs, которое сообщает, был ли сервер запущен, запущен как короткоживущий, переиспользован или не использован вовсе, вместе с идентификатором процесса сервера (dotnet/msbuild#14156). Оно журналируется с низкой важностью, поэтому попадает в двоичные журналы и в диагностический уровень подробности, не изменяя обычный вывод в консоль:

dotnet build -v:diag
# or capture it for later
dotnet build -bl

Когда нужно начать с чистого листа, например после установки нового SDK или изменения глобального свойства MSBuild, которое прогретый процесс закешировал, завершайте сервер явно, а не ищите процесс вручную:

dotnet build-server shutdown --msbuild

Команда не новая, но она становится гораздо более уместной теперь, когда прогретый сервер является значением по умолчанию. Её стоит держать в голове рядом с советом “удалить obj и bin”, когда сборка начинает вести себя странно.

Полные подробности приведены в примечаниях к выпуску SDK для .NET 11 Preview 7. Если вы разбираете остальные изменения Preview 7, поддержка ZIP-архивов, защищённых паролем заслуживает прочтения.

Comments

Sign in with GitHub to comment. Reactions and replies thread back to the comments repo.

< Назад