[
https://issues.apache.org/jira/browse/THRIFT-6237?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel
]
Sylwester Lachiewicz updated THRIFT-6237:
-----------------------------------------
Description:
Follow-up to [THRIFT-5952|https://issues.apache.org/jira/browse/THRIFT-5952].
The MSVC CI image is still dominated by components the build does not use, and
one full rebuild of it runs close to the step timeout.
h3. Current situation
Measured on the published image
{{ghcr.io/apache/thrift-build:msvc-0e3cd7cfc101}} (compressed layer sizes from
the registry manifest) and on [MSVC Build run
34590844910|https://github.com/apache/thrift/actions/runs/34590844910] (master,
2026-09-11):
||Layer||Compressed size||Note||
|base
{{mcr.microsoft.com/dotnet/framework/sdk:4.8.1-windowsservercore-ltsc2025}} (9
layers)|4029 MiB|64% of the image. Brings VS 2026 Build Tools, the .NET
Framework 4.8.1 SDK, targeting packs and the .NET 10 SDK|
|VS 2022 Build Tools in {{C:\BuildTools}}|1080 MiB|The compiler actually used:
the CMake log prints {{The CXX compiler identification is MSVC 19.44}}|
|jdk8|377 MiB|Unused. The CMake summary prints {{Build Java library: OFF}} with
reason {{Gradle missing}}|
|Boost 1.88|293 MiB|All six library variants kept (release, debug, shared,
static, static runtime)|
|Python 3.14|134 MiB|Used ({{Build Python library: ON}})|
|Node.js|132 MiB|Used ({{Build NodeJS library: ON}})|
|OpenSSL 3.6.2|105 MiB|Used. Debug import libraries and HTML documentation
included|
|CMake, 7zip+curl, Chocolatey, libevent, zlib|about 125 MiB| |
|*Total*|*6276 MiB*| |
CI timing from the same run: pulling the image takes 12 minutes (no layer was
already present on the runner), build and test inside the container 18 minutes.
The last full image rebuild ([run
24604653145|https://github.com/apache/thrift/actions/runs/24604653145],
2026-04-18) took 53 minutes against the 60 minute step timeout.
Further observations in
[build/docker/msvc/Dockerfile|https://github.com/apache/thrift/blob/master/build/docker/msvc/Dockerfile]:
* The only thing the base image contributes is the dotnet CLI for
{{lib/netstd}}. Its VS 2026 Build Tools are not used for C++ because a separate
VS 2022 Build Tools is installed and selected by {{VsDevCmd.bat}}.
* The Chocolatey {{curl}} package is redundant: Windows Server 2025 ships
{{curl.exe}}, and the Dockerfile itself already uses it for every download.
* {{PATH}} is extended five times with user-scope {{SETX PATH "%PATH%;..."}}.
SETX re-embeds the whole expanded PATH on every call and truncates silently at
1024 characters. This is a latent risk, not an observed failure.
* The Chocolatey bootstrap and the {{python314}}, {{nodejs}}, {{winflexbison3}}
and {{7zip}} installs are unpinned, so a rebuild from an unchanged Dockerfile
can produce a different image.
*
[.github/workflows/msvc.yml|https://github.com/apache/thrift/blob/master/.github/workflows/msvc.yml]
derives the image tag from the hash of the Dockerfile alone, but the image
also {{COPY}}s {{build/appveyor/build-libevent.bat}} and
{{build/appveyor/build-zlib.bat}}. Editing either script does not change the
tag, so CI keeps using the stale image.
h3. Proposal
# Switch the base image to
{{mcr.microsoft.com/dotnet/sdk:10.0-windowsservercore-ltsc2025}} (2722 MiB
compressed). All four netstd test projects target {{net10.0}} only; the
{{net8.0}} and {{net9.0}} targets of {{Thrift.csproj}} only need reference
packs, which NuGet restores. No project under {{lib/netstd}} targets .NET
Framework and there is no {{global.json}}. The image installs dotnet to
{{C:\Program Files\dotnet}} and extends PATH with {{setx /M}}, so {{build.bat}}
keeps working unchanged.
# Remove jdk8.
# Delete the Boost variants a Release {{/MD}} build cannot use: every file in
{{lib64-msvc-14.3}} whose name contains {{-mt-gd-}}, {{-mt-s-}} or
{{-mt-sgd-}}. Both release variants (shared import library plus DLL, and
static) stay, because the log does not show which one the linker picks.
# Remove the {{curl}} package, install the remaining Chocolatey packages in one
layer and pin their versions together with the Chocolatey version. Node.js
moves from the {{nodejs}} current line to {{nodejs-lts}} (24.x), which is a
behaviour change relative to whatever the current image picked up at build time.
# Replace the user-scope {{SETX PATH}} calls with machine-scope appends through
{{[Environment]::SetEnvironmentVariable(..., 'Machine')}}, which has no 1024
character limit. This is also what both Microsoft base images do.
# Remove the OpenSSL debug import libraries ({{lib\VC\x64\MDd}},
{{lib\VC\x64\MTd}}) and the {{html}} documentation.
# In {{msvc.yml}}, hash the Dockerfile together with the two copied scripts
when computing the image tag.
Expected effect: the base swap (1307 MiB) and the jdk8 removal (377 MiB) alone
take about 1.6 GiB off the 6.3 GiB compressed image. The Boost and OpenSSL
pruning comes on top; I have not measured those directories.
Not part of this ticket, noted for later: CMake configure takes 97 s in the
container, most of it in {{try_compile}} checks that each spawn MSBuild. The
Ninja generator would cut that, but needs {{build.bat}} to drop
{{-DCMAKE_GENERATOR_PLATFORM=x64}}.
_This issue was created with AI assistance._
was:
Follow-up to [THRIFT-5952|https://issues.apache.org/jira/browse/THRIFT-5952].
The MSVC CI image is still dominated by components the build does not use, and
one full rebuild of it runs close to the step timeout.
h3. Current situation
Measured on the published image
{{ghcr.io/apache/thrift-build:msvc-0e3cd7cfc101}} (compressed layer sizes from
the registry manifest) and on [MSVC Build run
34590844910|https://github.com/apache/thrift/actions/runs/34590844910] (master,
2026-09-11):
||Layer||Compressed size||Note||
|base
{{mcr.microsoft.com/dotnet/framework/sdk:4.8.1-windowsservercore-ltsc2025}} (9
layers)|4029 MiB|64% of the image. Brings VS 2026 Build Tools, the .NET
Framework 4.8.1 SDK, targeting packs and the .NET 10 SDK|
|VS 2022 Build Tools in {{C:\BuildTools}}|1080 MiB|The compiler actually used:
the CMake log prints {{The CXX compiler identification is MSVC 19.44}}|
|jdk8|377 MiB|Unused. The CMake summary prints {{Build Java library: OFF}} with
reason {{Gradle missing}}|
|Boost 1.88|293 MiB|All six library variants kept (release, debug, shared,
static, static runtime)|
|Python 3.14|134 MiB|Used ({{Build Python library: ON}})|
|Node.js|132 MiB|Used ({{Build NodeJS library: ON}})|
|OpenSSL 3.6.2|105 MiB|Used. Debug import libraries and HTML documentation
included|
|CMake, 7zip+curl, Chocolatey, libevent, zlib|about 125 MiB| |
|*Total*|*6276 MiB*| |
CI timing from the same run: pulling the image takes 12 minutes (no layer was
already present on the runner), build and test inside the container 18 minutes.
The last full image rebuild ([run
24604653145|https://github.com/apache/thrift/actions/runs/24604653145],
2026-04-18) took 53 minutes against the 60 minute step timeout.
Further observations in
[build/docker/msvc/Dockerfile|https://github.com/apache/thrift/blob/master/build/docker/msvc/Dockerfile]:
* The only thing the base image contributes is the dotnet CLI for
{{lib/netstd}}. Its VS 2026 Build Tools are not used for C++ because a separate
VS 2022 Build Tools is installed and selected by {{VsDevCmd.bat}}.
* The Chocolatey {{curl}} package is redundant: Windows Server 2025 ships
{{curl.exe}}, and the Dockerfile itself already uses it for every download.
* {{PATH}} is extended five times with user-scope {{SETX PATH "%PATH%;..."}}.
SETX re-embeds the whole expanded PATH on every call and truncates silently at
1024 characters. This is a latent risk, not an observed failure.
* The Chocolatey bootstrap and the {{python314}}, {{nodejs}}, {{winflexbison3}}
and {{7zip}} installs are unpinned, so a rebuild from an unchanged Dockerfile
can produce a different image.
*
[.github/workflows/msvc.yml|https://github.com/apache/thrift/blob/master/.github/workflows/msvc.yml]
derives the image tag from the hash of the Dockerfile alone, but the image
also {{COPY}}s {{build/appveyor/build-libevent.bat}} and
{{build/appveyor/build-zlib.bat}}. Editing either script does not change the
tag, so CI keeps using the stale image.
h3. Proposal
# Switch the base image to
{{mcr.microsoft.com/dotnet/sdk:10.0-windowsservercore-ltsc2025}} (2722 MiB
compressed). All four netstd test projects target {{net10.0}} only; the
{{net8.0}} and {{net9.0}} targets of {{Thrift.csproj}} only need reference
packs, which NuGet restores. No project under {{lib/netstd}} targets .NET
Framework and there is no {{global.json}}. The image installs dotnet to
{{C:\Program Files\dotnet}} and extends PATH with {{setx /M}}, so {{build.bat}}
keeps working unchanged.
# Remove jdk8.
# Delete the Boost variants a Release {{/MD}} build cannot use:
{{\*-mt-gd-\*}}, {{\*-mt-s-\*}} and {{\*-mt-sgd-\*}}. Both release variants
(shared import library plus DLL, and static) stay, because the log does not
show which one the linker picks.
# Remove the {{curl}} package, install the remaining Chocolatey packages in one
layer and pin their versions together with the Chocolatey version.
# Replace the user-scope {{SETX PATH}} calls with machine-scope appends through
{{[Environment]::SetEnvironmentVariable(..., 'Machine')}}, which has no 1024
character limit. This is also what both Microsoft base images do.
# Remove the OpenSSL debug import libraries ({{lib\VC\x64\MDd}},
{{lib\VC\x64\MTd}}) and the {{html}} documentation.
# In {{msvc.yml}}, hash the Dockerfile together with the two copied scripts
when computing the image tag.
Expected effect: the base swap and the jdk8 removal alone take about 1.7 GiB
off the 6.3 GiB compressed image. The Boost and OpenSSL pruning comes on top; I
have not measured those directories.
Not part of this ticket, noted for later: CMake configure takes 97 s in the
container, most of it in {{try_compile}} checks that each spawn MSBuild. The
Ninja generator would cut that, but needs {{build.bat}} to drop
{{-DCMAKE_GENERATOR_PLATFORM=x64}}.
> Shrink the MSVC Docker image: drop the unused .NET Framework base and JDK,
> prune Boost, pin tool versions
> ---------------------------------------------------------------------------------------------------------
>
> Key: THRIFT-6237
> URL: https://issues.apache.org/jira/browse/THRIFT-6237
> Project: Thrift
> Issue Type: Improvement
> Components: Build Process
> Reporter: Sylwester Lachiewicz
> Priority: Major
>
> Follow-up to [THRIFT-5952|https://issues.apache.org/jira/browse/THRIFT-5952].
> The MSVC CI image is still dominated by components the build does not use,
> and one full rebuild of it runs close to the step timeout.
> h3. Current situation
> Measured on the published image
> {{ghcr.io/apache/thrift-build:msvc-0e3cd7cfc101}} (compressed layer sizes
> from the registry manifest) and on [MSVC Build run
> 34590844910|https://github.com/apache/thrift/actions/runs/34590844910]
> (master, 2026-09-11):
> ||Layer||Compressed size||Note||
> |base
> {{mcr.microsoft.com/dotnet/framework/sdk:4.8.1-windowsservercore-ltsc2025}}
> (9 layers)|4029 MiB|64% of the image. Brings VS 2026 Build Tools, the .NET
> Framework 4.8.1 SDK, targeting packs and the .NET 10 SDK|
> |VS 2022 Build Tools in {{C:\BuildTools}}|1080 MiB|The compiler actually
> used: the CMake log prints {{The CXX compiler identification is MSVC 19.44}}|
> |jdk8|377 MiB|Unused. The CMake summary prints {{Build Java library: OFF}}
> with reason {{Gradle missing}}|
> |Boost 1.88|293 MiB|All six library variants kept (release, debug, shared,
> static, static runtime)|
> |Python 3.14|134 MiB|Used ({{Build Python library: ON}})|
> |Node.js|132 MiB|Used ({{Build NodeJS library: ON}})|
> |OpenSSL 3.6.2|105 MiB|Used. Debug import libraries and HTML documentation
> included|
> |CMake, 7zip+curl, Chocolatey, libevent, zlib|about 125 MiB| |
> |*Total*|*6276 MiB*| |
> CI timing from the same run: pulling the image takes 12 minutes (no layer was
> already present on the runner), build and test inside the container 18
> minutes. The last full image rebuild ([run
> 24604653145|https://github.com/apache/thrift/actions/runs/24604653145],
> 2026-04-18) took 53 minutes against the 60 minute step timeout.
> Further observations in
> [build/docker/msvc/Dockerfile|https://github.com/apache/thrift/blob/master/build/docker/msvc/Dockerfile]:
> * The only thing the base image contributes is the dotnet CLI for
> {{lib/netstd}}. Its VS 2026 Build Tools are not used for C++ because a
> separate VS 2022 Build Tools is installed and selected by {{VsDevCmd.bat}}.
> * The Chocolatey {{curl}} package is redundant: Windows Server 2025 ships
> {{curl.exe}}, and the Dockerfile itself already uses it for every download.
> * {{PATH}} is extended five times with user-scope {{SETX PATH "%PATH%;..."}}.
> SETX re-embeds the whole expanded PATH on every call and truncates silently
> at 1024 characters. This is a latent risk, not an observed failure.
> * The Chocolatey bootstrap and the {{python314}}, {{nodejs}},
> {{winflexbison3}} and {{7zip}} installs are unpinned, so a rebuild from an
> unchanged Dockerfile can produce a different image.
> *
> [.github/workflows/msvc.yml|https://github.com/apache/thrift/blob/master/.github/workflows/msvc.yml]
> derives the image tag from the hash of the Dockerfile alone, but the image
> also {{COPY}}s {{build/appveyor/build-libevent.bat}} and
> {{build/appveyor/build-zlib.bat}}. Editing either script does not change the
> tag, so CI keeps using the stale image.
> h3. Proposal
> # Switch the base image to
> {{mcr.microsoft.com/dotnet/sdk:10.0-windowsservercore-ltsc2025}} (2722 MiB
> compressed). All four netstd test projects target {{net10.0}} only; the
> {{net8.0}} and {{net9.0}} targets of {{Thrift.csproj}} only need reference
> packs, which NuGet restores. No project under {{lib/netstd}} targets .NET
> Framework and there is no {{global.json}}. The image installs dotnet to
> {{C:\Program Files\dotnet}} and extends PATH with {{setx /M}}, so
> {{build.bat}} keeps working unchanged.
> # Remove jdk8.
> # Delete the Boost variants a Release {{/MD}} build cannot use: every file in
> {{lib64-msvc-14.3}} whose name contains {{-mt-gd-}}, {{-mt-s-}} or
> {{-mt-sgd-}}. Both release variants (shared import library plus DLL, and
> static) stay, because the log does not show which one the linker picks.
> # Remove the {{curl}} package, install the remaining Chocolatey packages in
> one layer and pin their versions together with the Chocolatey version.
> Node.js moves from the {{nodejs}} current line to {{nodejs-lts}} (24.x),
> which is a behaviour change relative to whatever the current image picked up
> at build time.
> # Replace the user-scope {{SETX PATH}} calls with machine-scope appends
> through {{[Environment]::SetEnvironmentVariable(..., 'Machine')}}, which has
> no 1024 character limit. This is also what both Microsoft base images do.
> # Remove the OpenSSL debug import libraries ({{lib\VC\x64\MDd}},
> {{lib\VC\x64\MTd}}) and the {{html}} documentation.
> # In {{msvc.yml}}, hash the Dockerfile together with the two copied scripts
> when computing the image tag.
> Expected effect: the base swap (1307 MiB) and the jdk8 removal (377 MiB)
> alone take about 1.6 GiB off the 6.3 GiB compressed image. The Boost and
> OpenSSL pruning comes on top; I have not measured those directories.
> Not part of this ticket, noted for later: CMake configure takes 97 s in the
> container, most of it in {{try_compile}} checks that each spawn MSBuild. The
> Ninja generator would cut that, but needs {{build.bat}} to drop
> {{-DCMAKE_GENERATOR_PLATFORM=x64}}.
> _This issue was created with AI assistance._
--
This message was sent by Atlassian Jira
(v8.20.10#820010)