packaging: switch to native WiX toolchain and Windows runner (#1385)

Cross-platform msitools do not support the `Environment` directive,
which should be the proper way to update %PATH%, so we adapt
the Makefile to assume a Windows environment when building, addressing #1374.

`make dist` now runs on all platforms, but on Windows, assuming
`candle.exe`, `light.exe` and GNU `tar` are installed, it builds
all tarballs, zip and msi packages.

On other platforms it will only build the tarballs.

We also address some other issues with msitools
and change the GUID for UpgradeCode which caused
the wazero package to be mistaken for func-e
when installing/uninstalling both on the same
machine.

Signed-off-by: Edoardo Vacchi <evacchi@users.noreply.github.com>
This commit is contained in:
Edoardo Vacchi
2023-04-22 08:12:12 +02:00
committed by GitHub
parent 40341af448
commit 6f0b85a451
4 changed files with 40 additions and 112 deletions

View File

@@ -25,8 +25,8 @@ concurrency:
jobs:
pre_release:
name: Pre-release build
# This only runs on ubuntu so that we can simplify the installation of necessary toolchain to build artifacts.
runs-on: ubuntu-22.04
# This only runs on Windows so that we can simplify the installation of necessary toolchain to build artifacts.
runs-on: windows-2022
# This allows us to test in the following job regardless of the event (tag or not).
outputs:
VERSION: ${{ steps.output-version.outputs.VERSION }}
@@ -44,10 +44,12 @@ jobs:
~/go/bin
key: pre-release-check-${{ runner.os }}-go-${{ matrix.go-version }}-${{ hashFiles('**/go.sum', 'Makefile') }}
# ubuntu is missing wixl https://github.com/actions/virtual-environments/issues/3857
# ubuntu is also missing osslsigncode (no issue, yet)
- name: "Install GNOME msitools (wixl) and osslsigncode"
run: sudo apt update -qq && sudo apt install -qq -y wixl osslsigncode
# windows-2022 is missing osslsigncode (no issue, yet)
- name: "Install osslsigncode, infozip; setup wix"
run: |
choco install osslsigncode -y
choco install zip -y
echo "C:\Program Files (x86)\WiX Toolset v3.11\bin" >> $GITHUB_PATH
- name: Download Windows code signing certificate
env:
@@ -57,7 +59,8 @@ jobs:
echo $WINDOWS_CODESIGN_P12_BASE64 | base64 --decode > windows-certificate.p12
echo "WINDOWS_CODESIGN_P12=windows-certificate.p12" >> $GITHUB_ENV
fi
shell: bash
- name: Make artifacts (test)
if: github.event_name != 'push' || !contains(github.ref, 'refs/tags/')
run: | # On the fork PRs, our org secret is not visible. We unset the required env so that `make dist` uses default self-signed cert.
@@ -67,6 +70,7 @@ jobs:
VERSION=${{ github.sha }}
make dist VERSION=$VERSION
echo "VERSION=${VERSION}" >> $GITHUB_ENV
shell: bash
- name: Make artifacts
# Triggers only on tag creation.
@@ -78,10 +82,12 @@ jobs:
MSI_VERSION=${VERSION//-/.}
make dist VERSION=$VERSION MSI_VERSION=$MSI_VERSION
echo "VERSION=${VERSION}" >> $GITHUB_ENV
shell: bash
# This allows us to test in the following job regardless of the event (tag or not).
- id: output-version
run: echo "VERSION=${VERSION}" >> "$GITHUB_OUTPUT"
shell: bash
# In order to share the built artifacts in the subsequent tests, we use cache instead of actions/upload-artifacts.
# The reason is that upload-artifacts are not globally consistent and sometimes pre_release_test won't be able to
@@ -145,14 +151,6 @@ jobs:
call packaging\msi\verify_msi.cmd
shell: cmd
# This tests the manifest via yamllint because validation via winget requires too much setup.
# See https://github.com/microsoft/winget-cli/issues/754#issuecomment-896475895
- name: Test winget manifest generation
if: runner.os == 'Windows'
run: |
./packaging/msi/winget_manifest.sh ${{ needs.pre_release.outputs.VERSION }} "dist\wazero_${{ needs.pre_release.outputs.VERSION }}_windows_amd64.msi" > Tetrate.wazero.yaml
yamllint -sd '{extends: default, rules: {line-length: disable}}' Tetrate.wazero.yaml
# Triggers only on the tag creation.
release:
if: github.event_name == 'push' && contains(github.ref, 'refs/tags/')

View File

@@ -261,12 +261,11 @@ fuzz:
#### CLI release related ####
VERSION ?= dev
# Default to a dummy version 0.0.1.rc1, which is always lower than a real release.
# This must be in the form of [0-255].[0-255].[0-65535] plus optional fourth element which will be ignored.
# We use the fourth field to represent the rc portion of release tag (e.g. rc1 of 1.0.0-rc2).
# Default to a dummy version 0.0.1.1, which is always lower than a real release.
# Legal version values should look like 'x.x.x.x' where x is an integer from 0 to 65534.
# https://learn.microsoft.com/en-us/windows/win32/msi/productversion?redirectedfrom=MSDN
# https://stackoverflow.com/questions/9312221/msi-version-numbers
MSI_VERSION ?= 0.0.1.rc1
MSI_VERSION ?= 0.0.1.1
non_windows_platforms := darwin_amd64 darwin_arm64 linux_amd64 linux_arm64
non_windows_archives := $(non_windows_platforms:%=dist/wazero_$(VERSION)_%.tar.gz)
windows_platforms := windows_amd64 # TODO: add arm64 windows once we start testing on it.
@@ -288,7 +287,9 @@ build/wazero_%/wazero.exe:
dist/wazero_$(VERSION)_%.tar.gz: build/wazero_%/wazero
@echo tar.gz "tarring $@"
@mkdir -p $(@D)
@tar -C $(<D) -cpzf $@ $(<F)
# On Windows, we pass the special flag `--mode='+rx' to ensure that we set the executable flag.
# This is only supported by GNU Tar, so we set it conditionally.
@tar -C $(<D) -cpzf $@ $(if $(findstring Windows_NT,$(OS)),--mode='+rx',) $(<F)
@echo tar.gz "ok"
define go-build
@@ -325,12 +326,16 @@ define codesign
@printf "$(ansi_format_bright)" codesign "ok"
endef
# This task is only supported on Windows, where we use candle.exe (compile wxs to wixobj) and light.exe (link to msi)
dist/wazero_$(VERSION)_%.msi: build/wazero_%/wazero.exe.signed
ifeq ($(OS),Windows_NT)
@echo msi "building $@"
@mkdir -p $(@D)
@wixl -a $(call msi-arch,$@) -D Version=$(MSI_VERSION) -D Bin=$(<:.signed=) -o $@ packaging/msi/wazero.wxs
@candle -nologo -arch $(call msi-arch,$@) -dVersion=$(MSI_VERSION) -dBin=$(<:.signed=) -o build/wazero.wixobj packaging/msi/wazero.wxs
@light -nologo -o $@ build/wazero.wixobj -spdb
$(call codesign,$@)
@echo msi "ok"
endif
dist/wazero_$(VERSION)_%.zip: build/wazero_%/wazero.exe.signed
@echo zip "zipping $@"
@@ -343,4 +348,4 @@ sha256sum := $(if $(findstring darwin,$(shell go env GOOS)),shasum -a 256,sha256
$(checksum_txt):
@cd $(@D); touch $(@F); $(sha256sum) * >> $(@F)
dist: $(non_windows_archives) $(windows_archives) $(checksum_txt)
dist: $(non_windows_archives) $(if $(findstring Windows_NT,$(OS)),$(windows_archives),) $(checksum_txt)

View File

@@ -1,4 +1,4 @@
<?xml version="1.0" encoding="UTF-8"?>
<?xml version="1.0" encoding="UTF-8"?>
<!--
Copyright 2023 Tetrate
@@ -15,18 +15,15 @@
limitations under the License.
-->
<!-- This builds a minimal package of wazero. The only required variable is Version
Ex. `wixl -D Version=0.6.1`
Ex. `candle.exe -dVersion=0.6.1`
While all options used are documented, the initial version of this file was helped by:
* cloudflared - https://github.com/cloudflare/cloudflared/commit/38af26e232d6a5fd981d40981b702a1d06a3b8ee
* podmad - https://github.com/containers/podman/commit/b6b0b6e8bd0f8c75fe9411f722a43f9305c6137a
In order to allow single-host builds, we restrict to syntax that works with GNOME msitools.
Raise issues on incompatibilies here https://gitlab.gnome.org/GNOME/msitools/-/issues -->
* podman - https://github.com/containers/podman/commit/b6b0b6e8bd0f8c75fe9411f722a43f9305c6137a -->
<Wix xmlns="http://schemas.microsoft.com/wix/2006/wi">
<?ifndef var.Version?>
<?error Version must be defined. Ex. wixl -D Version=0.6.1?>
<?error Version must be defined. Ex. candle -dVersion=0.6.1?>
<?endif?>
<?ifndef var.Bin?>
@@ -36,7 +33,7 @@
<!-- UpgradeCode needs to be constant until an incompatible change occurs
See https://docs.microsoft.com/en-us/windows/win32/msi/upgrade-table -->
<?ifndef var.UpgradeCode?>
<?define UpgradeCode = "FC6C326B-1DB7-4D48-8F05-E13E79DF4D0E" ?>
<?define UpgradeCode = "bef1bfc9-a5fc-4819-988f-807e47312f57" ?>
<?endif?>
<!-- Id="*" means it will be automatically generated: TODO: Consider if we should version-correlate the Id
@@ -47,17 +44,15 @@
-->
<Product Id="*" Name="wazero" Manufacturer="Tetrate" Version="$(var.Version)" UpgradeCode="$(var.UpgradeCode)"
Language="1033" Codepage="1252">
<!-- TODO: set <Property Id="ALLUSERS"... after https://gitlab.gnome.org/GNOME/msitools/-/issues/40 -->
InstallScope="perUser" is default (Id="ALLUSERS" doesn't work on msitools 0.101) -->
<Package Id="*" Keywords="Installer" Description="wazero installer" Manufacturer="Tetrate"
InstallerVersion="310" Languages="1033" Compressed="yes" SummaryCodepage="1252"/>
InstallerVersion="310" Languages="1033" Compressed="yes" SummaryCodepage="1252" Platform="x64" />
<!-- wazero.exe is embedded inside the installer: wazero.msi
Cabinet="Wazero.cab" because light.exe fails on "wazero.cab" -->
<Media Id="1" Cabinet="Wazero.cab" EmbedCab="yes"/>
<!-- We allow the special version 0.0.1 in order to run tests. Releases will always be real versions. -->
<!-- We allow the special version 0.0.1.1 in order to run tests. Releases will always be real versions. -->
<Upgrade Id="$(var.UpgradeCode)">
<UpgradeVersion Minimum="$(var.Version)" OnlyDetect="yes" Property="NEWERVERSIONDETECTED"/>
<UpgradeVersion Minimum="0.0.0" Maximum="$(var.Version)" IncludeMinimum="yes" IncludeMaximum="no"
@@ -73,6 +68,8 @@
<Property Id="ARPNOREPAIR" Value="1"/>
<Property Id="ARPNOMODIFY" Value="1"/>
<Property Id="ALLUSERS" Secure="yes"/>
<!-- On Windows, when Id="TARGETDIR" Name="SourceDir": it will error otherwise -->
<Directory Id="TARGETDIR" Name="SourceDir">
<Directory Id="ProgramFiles64Folder">
@@ -84,6 +81,11 @@
</Component>
</Directory>
</Directory>
<Component Id="Path" Guid="{fb130dec-3828-4ebc-b253-e7368cba14e8}">
<Environment Id="PATH" Name="PATH" Value="[INSTALLDIR]" Permanent="no" Part="last" Action="set" System="no" />
</Component>
</Directory>
<!-- Use most common size 48x48 for the Add/Remove programs -->
@@ -92,17 +94,11 @@
<Feature Id="Complete" Level="1">
<ComponentRef Id="WazeroBin"/>
<ComponentRef Id="Path" />
</Feature>
<!-- Add wazero to the default PATH once installation succeeds.
Replace with <Component><Environment> after https://gitlab.gnome.org/GNOME/msitools/-/merge_requests/42 -->
<Property Id="setx" Value="setx.exe"/>
<CustomAction Id="ChangePath" ExeCommand="PATH &quot;%PATH%;[INSTALLDIR]&quot;" Property="setx"
Execute="deferred"/>
<InstallExecuteSequence>
<RemoveExistingProducts Before="InstallInitialize"/>
<!-- Add PATH remove after after https://gitlab.gnome.org/GNOME/msitools/-/merge_requests/42 -->
<Custom Action="ChangePath" After="InstallServices">NOT Installed</Custom>
</InstallExecuteSequence>
</Product>
</Wix>

View File

@@ -1,71 +0,0 @@
#!/bin/sh -ue
# Copyright 2023 Tetrate
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
# This script echos the winget manifest for a wazero Windows Installer (msi).
#
# Ex.
# msi_file=/path/to/wazero.msi
# manifest_path=./manifests/t/Tetrate/wazero/${version}/Tetrate.wazero.yaml
# mkdir -p $(dirname "${manifest_path}")
# packaging/msi/winget_manifest.sh ${version} ${msi_file} > ${manifest_path}
# winget validate --manifest ${manifest_path}
version=${1:-0.0.1}
msi_file=${2:-dist/wazero_dev_windows_amd64.msi}
case $(uname -s) in
CYGWIN* | MSYS* | MINGW*)
installer_sha256=$(certutil -hashfile "${msi_file}" SHA256 | sed -n 2p)
product_code=$(powershell -File ./packaging/msi/msi_product_code.ps1 -msi "${msi_file}")
;;
*) # notably, this gets rid of the Windows carriage return (\r), which otherwise would mess up the heredoc.
msiinfo -h export >/dev/null
# shasum -a 256, not sha256sum as https://github.com/actions/virtual-environments/issues/90
installer_sha256=$(shasum -a 256 "${msi_file}" | awk '{print toupper($1)}' 2>&-)
product_code=$(msiinfo export "${msi_file}" Property | sed -n '/ProductCode/s/\r$//p' | cut -f2)
;;
esac
cat <<EOF
# yaml-language-server: \$schema=https://aka.ms/winget-manifest.singleton.1.0.0.schema.json
---
PackageIdentifier: Tetrate.wazero
PackageVersion: ${version}
PackageName: wazero
Publisher: Tetrate
Copyright: Copyright 2023 Tetrate
License: Apache 2.0
LicenseUrl: https://github.com/tetratelabs/wazero/blob/main/LICENSE
Moniker: wazero
Commands:
- wazero
Tags:
- wazero
- webassembly
- wasm
- tetrate
ShortDescription: wazero runs WebAssembly modules
Description: wazero is a command line utility to run WebAssembly modules. Specifically, this runs .wasm files compiled with WASI or Go, and has zero platform dependencies.
PackageUrl: https://wazero.io
Installers:
- Architecture: x64
InstallerUrl: https://github.com/tetratelabs/wazero/releases/download/v${version}/wazero_${version}_windows_amd64.msi
InstallerSha256: $installer_sha256
InstallerType: msi
ProductCode: "${product_code}"
PackageLocale: en-US
ManifestType: singleton
ManifestVersion: 1.0.0
EOF