Repository navigation
140 lines (140 loc) · 5.78 KB
/
Copy pathnative.yml
File metadata and controls
140 lines (140 loc) · 5.78 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
name: published CLI consumers
on:
pull_request:
branches: [dev]
paths-ignore:
- 'README.md'
- 'evidence/**'
- 'scripts/markdown-review/**'
- 'scripts/publish-review.ts'
- '.github/workflows/cache.yml'
- '.github/workflows/report.yml'
- 'scripts/assert-cache.mjs'
- 'scripts/prepare-registry.mjs'
workflow_dispatch:
permissions:
contents: read
concurrency:
group: native-${{ github.ref }}
cancel-in-progress: true
jobs:
native:
strategy:
fail-fast: false
matrix:
include:
- target: linux-amd64
runner: ubuntu-24.04
- target: linux-arm64
runner: ubuntu-24.04-arm
- target: darwin-amd64
runner: macos-15-intel
- target: darwin-arm64
runner: macos-15
- target: windows-amd64
runner: windows-2025
runs-on: ${{ matrix.runner }}
timeout-minutes: 10
steps:
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
persist-credentials: false
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
repository: rootform-dev/rootform
ref: 74bd643f3001a37f8b4f881c0ae33db047b6aba3
path: fixtures/rootform
sparse-checkout: |
examples/playground/shared-data-platform
policy-packs/baseline
cli/detect/testdata
persist-credentials: false
- name: Autonomous analysis and verified installation
id: analyze
uses: rootform-dev/action/analyze@cc457702223d887c9db5da52ba36099ad3e1b4e0
with:
version: 0.1.0-pr.117.1
input: fixtures/rootform/examples/playground/shared-data-platform/base/plan.json
plan-file: fixtures/rootform/examples/playground/shared-data-platform/base/plan.tfplan
artifact-name: native-${{ matrix.target }}
- name: Inspect actual analysis outputs
env:
ROOTFORM_OUTPUTS: ${{ toJSON(steps.analyze.outputs) }}
ROOTFORM_EXPECT_ARTIFACT: 'true'
run: node scripts/assert-output.mjs analyze
- name: Optional setup reuses exact verified bytes
id: setup
uses: rootform-dev/action/setup@cc457702223d887c9db5da52ba36099ad3e1b4e0
- name: Verify CLI version and executable digest
shell: bash
env:
EXPECTED_VERSION: ${{ steps.setup.outputs.version }}
EXPECTED_SHA: ${{ steps.setup.outputs.sha256 }}
run: |
set -euo pipefail
test "$(rootform version)" = "rootform $EXPECTED_VERSION"
[[ "$EXPECTED_SHA" =~ ^[0-9a-f]{64}$ ]]
- name: Record original Form digest before reuse
env:
ORIGINAL_FORM: ${{ steps.analyze.outputs.form }}
run: node -e "const fs=require('node:fs'),crypto=require('node:crypto');fs.appendFileSync(process.env.GITHUB_ENV,'ROOTFORM_PREVIOUS_SHA='+crypto.createHash('sha256').update(fs.readFileSync(process.env.ORIGINAL_FORM)).digest('hex')+'\n')"
- name: Reopen the provided Form
id: reopen
uses: rootform-dev/action/analyze@cc457702223d887c9db5da52ba36099ad3e1b4e0
with:
input: ${{ steps.analyze.outputs.form }}
upload-artifact: 'false'
summary: 'false'
- name: Check saved Form path and content reuse
env:
ROOTFORM_OUTPUTS: ${{ toJSON(steps.reopen.outputs) }}
ROOTFORM_PREVIOUS_FORM: ${{ steps.analyze.outputs.form }}
run: node scripts/assert-output.mjs analyze
- name: Compare Form with independently paired plan
id: compare
uses: rootform-dev/action/compare@cc457702223d887c9db5da52ba36099ad3e1b4e0
with:
before: ${{ steps.analyze.outputs.form }}
after: fixtures/rootform/examples/playground/shared-data-platform/head/plan.json
after-plan-file: fixtures/rootform/examples/playground/shared-data-platform/head/plan.tfplan
upload-artifact: 'false'
- name: Inspect actual comparison outputs
env:
ROOTFORM_OUTPUTS: ${{ toJSON(steps.compare.outputs) }}
run: node scripts/assert-output.mjs compare
- name: Evaluate both saved comparison sides
id: check
uses: rootform-dev/action/check@cc457702223d887c9db5da52ba36099ad3e1b4e0
with:
input: ${{ steps.compare.outputs.form }}
side: both
policy-pack: fixtures/rootform/policy-packs/baseline
upload-artifact: 'false'
- name: Inspect successful Policy outputs
env:
ROOTFORM_OUTPUTS: ${{ toJSON(steps.check.outputs) }}
run: node scripts/assert-output.mjs check 0
- name: Genuine negative verdict retains all evidence
id: negative
continue-on-error: true
uses: rootform-dev/action/check@cc457702223d887c9db5da52ba36099ad3e1b4e0
with:
input: ${{ steps.analyze.outputs.form }}
policy-pack: fixtures/negative
artifact-name: negative-${{ matrix.target }}
- name: Inspect failed gate evidence
env:
ROOTFORM_OUTPUTS: ${{ toJSON(steps.negative.outputs) }}
ROOTFORM_EXPECT_ARTIFACT: 'true'
STEP_OUTCOME: ${{ steps.negative.outcome }}
run: |
node -e "require('node:assert/strict').equal(process.env.STEP_OUTCOME,'failure')"
node scripts/assert-output.mjs check 1
- name: Download actual negative artifact
uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8.0.1
with:
artifact-ids: ${{ steps.negative.outputs.artifact-id }}
path: downloaded-negative
merge-multiple: true
- name: Check exact artifact allowlist
run: node scripts/verify-artifact.mjs downloaded-negative form.json,report.md,result.json,results.sarif