forked from cachix/secretspec
-
Notifications
You must be signed in to change notification settings - Fork 0
150 lines (137 loc) · 6.08 KB
/
Copy pathruby-gems.yml
File metadata and controls
150 lines (137 loc) · 6.08 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
name: "Ruby gems"
# Builds platform-specific gems for the Ruby SDK. Each gem bundles the
# secretspec-ffi staticlib (into vendor/); at `gem install` mkmf compiles a tiny
# C glue and statically links that archive, so the resolver is embedded in the
# extension and one platform gem serves every Ruby ABI.
#
# NOTE: as with the Python wheels, the Linux gem here links the runner's glibc.
# A portable release build should use a baseline toolchain. That is the
# remaining follow-up; the build + bundling mechanism below is what is
# validated. Install requires a C compiler and Ruby headers.
#
# The Windows gem (x64-mingw-ucrt) bundles a staticlib from the
# `x86_64-pc-windows-gnu` Rust target (declared in rust-toolchain.toml):
# RubyInstaller's devkit is MinGW, whose linker cannot consume MSVC `.lib`
# archives, while the GNU target emits the same `lib<name>.a` naming the
# staging script and mkmf extension already assume. setup-ruby's MSYS2 devkit
# supplies the mingw gcc that aws-lc-sys and the other C deps compile with;
# NASM assembles aws-lc's x86_64 assembly. The SDK itself is exercised on
# every PR by the devenv-based sdks.yml; this workflow only builds the
# distributable gems.
on:
workflow_call:
workflow_dispatch:
push:
tags:
- v**
# PR runs are scoped to changes in the Ruby SDK or this workflow. Core
# resolver and FFI changes are verified on PRs by the devenv-based test.yml,
# sdks.yml, and ffi-build.yml; the full matrix here still runs on tags and
# manual dispatch.
pull_request:
paths:
- "secretspec-rb/**"
- ".github/workflows/ruby-gems.yml"
- "scripts/sync-sdk-versions.sh"
- "scripts/copy-mingw-import-libs.sh"
permissions:
contents: read
jobs:
gems:
name: ${{ matrix.target }}
runs-on: ${{ matrix.runner }}
strategy:
fail-fast: false
matrix:
include:
- { target: x86_64-linux, runner: ubuntu-latest }
- { target: aarch64-linux, runner: ubuntu-24.04-arm }
- { target: arm64-darwin, runner: macos-latest, deployment_target: "12.0" }
- { target: x64-mingw-ucrt, runner: windows-latest }
steps:
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
persist-credentials: false
- name: Sync SDK package versions
run: bash scripts/sync-sdk-versions.sh
- name: Install Rust (pinned by rust-toolchain.toml)
run: rustup toolchain install
# See the header: the Windows gem links with RubyInstaller's MinGW
# devkit, so the staticlib must come from the GNU target, not the
# runner's default MSVC one. stage-staticlib.sh reads CARGO_BUILD_TARGET
# to locate the per-target artifact.
- name: Target the GNU toolchain (Windows)
if: runner.os == 'Windows'
shell: bash
run: echo "CARGO_BUILD_TARGET=x86_64-pc-windows-gnu" >> "$GITHUB_ENV"
- name: Install NASM (aws-lc-sys assembly, Windows)
if: runner.os == 'Windows'
uses: ilammy/setup-nasm@72793074d3c8cdda771dba85f6deafe00623038b # v1.5.2
# Placed after the CARGO_BUILD_TARGET/toolchain setup so the cache key
# reflects them; keyed per matrix target (the automatic key covers only
# the job id, toolchain, and lockfile).
- name: Cache Rust builds
uses: Swatinem/rust-cache@e18b497796c12c097a38f9edb9d0641fb99eee32 # v2
with:
key: ${{ matrix.target }}
- uses: ruby/setup-ruby@95ef2b042f9d7a56d8268cba8559e2842e2ad01b # v1.321.0
with:
ruby-version: "3.3"
- name: Stage the staticlib and build the platform gem
shell: bash
env:
MACOSX_DEPLOYMENT_TARGET: ${{ matrix.deployment_target }}
EXPECTED_GEM_PLATFORM: ${{ matrix.target }}
run: |
bash secretspec-rb/scripts/stage-staticlib.sh
cd secretspec-rb
gem build secretspec.gemspec
ruby -rrubygems/package -e '
gem = Dir["secretspec-*.gem"].fetch(0)
platform = Gem::Package.new(gem).spec.platform.to_s
expected = ENV.fetch("EXPECTED_GEM_PLATFORM")
abort "expected gem platform #{expected}, got #{platform}" unless platform == expected
'
- name: Smoke test the gem
shell: bash
run: |
cd secretspec-rb
# Installing compiles the extension (spec.extensions) against the
# bundled vendor/libsecretspec_ffi.a -- no Rust toolchain needed here.
gem install --no-document --install-dir "$RUNNER_TEMP/gemhome" secretspec-*.gem
# Run outside the repo so only the installed extension satisfies require.
cd "$RUNNER_TEMP"
GEM_HOME="$RUNNER_TEMP/gemhome" GEM_PATH="$RUNNER_TEMP/gemhome" \
ruby -e 'require "secretspec"; puts "abi " + Secretspec.abi_version'
- uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
with:
name: gem-${{ matrix.target }}
path: secretspec-rb/*.gem
publish:
name: publish to RubyGems
if: github.event_name == 'push' && startsWith(github.ref, 'refs/tags/v')
needs: [gems]
runs-on: ubuntu-latest
# Must match the "Environment" configured on rubygems.org's pending
# trusted publisher for the "secretspec" gem (see RELEASE.md) -- RubyGems
# matches trusted publishers by repo + workflow filename + environment,
# no ID or role value is issued or needed.
environment: release
permissions:
id-token: write # RubyGems Trusted Publishing (OIDC), no token needed
contents: read
steps:
- uses: ruby/setup-ruby@95ef2b042f9d7a56d8268cba8559e2842e2ad01b # v1.321.0
with:
ruby-version: "3.3"
- uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8.0.1
with:
path: gems
merge-multiple: true
- name: Configure RubyGems credentials (OIDC trusted publishing)
uses: rubygems/configure-rubygems-credentials@dc5a8d8553e6ee01fc26761a49e99e733d17954a # v2.1.0
- name: gem push
run: |
for gem in gems/*.gem; do
gem push "$gem"
done