-
Notifications
You must be signed in to change notification settings - Fork 1.5k
Expand file tree
/
Copy pathaction.yml
More file actions
210 lines (190 loc) · 10 KB
/
Copy pathaction.yml
File metadata and controls
210 lines (190 loc) · 10 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
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
name: "Parse Comment Config"
description: "Parses the comment to extract run flag, pipeline list, profile list, and additional configuration fields."
inputs:
releaseVersion:
description: "Release version to test (i.e. 'latest', '0.46.0')"
required: false
default: "latest"
kafkaVersion:
description: "Kafka version. e.g. '4.0.0' or 'latest'"
required: false
default: "latest"
pipeline:
description: "Comma-separated or single pipeline name(s)"
required: false
default: "smoke"
clusterSecurityEncryption:
description: "Encryption used for the internal Kafka cluster communication ('tls' or 'none')"
required: false
default: "tls"
clusterSecurityAuthentication:
description: "Authentication used for the internal Kafka cluster communication ('mtls', 'service-account' or 'none')"
required: false
default: "mtls"
outputs:
pipelineList:
description: "Comma-separated list of pipeline names (if provided)"
value: ${{ steps.parse_comment.outputs.pipelineList }}
profileList:
description: "Comma-separated list of profile names (fallback if pipeline is not provided)"
value: ${{ steps.parse_comment.outputs.profileList }}
agent:
description: "The parsed agent value from the comment"
value: ${{ steps.parse_comment.outputs.agent }}
architecture:
description: "The parsed architecture value from the comment"
value: ${{ steps.parse_comment.outputs.architecture }}
strimzi_feature_gates:
description: "The parsed strimzi_feature_gates value"
value: ${{ steps.parse_comment.outputs.strimzi_feature_gates }}
strimzi_rbac_scope:
description: "The parsed strimzi_rbac_scope value"
value: ${{ steps.parse_comment.outputs.strimzi_rbac_scope }}
cluster_operator_install_type:
description: "The parsed cluster_operator_install_type value"
value: ${{ steps.parse_comment.outputs.cluster_operator_install_type }}
groups:
description: "JUnit5 test groups that will be executed"
value: ${{ steps.parse_comment.outputs.groups }}
tests:
description: "JUnit5 tests that will be executed"
value: ${{ steps.parse_comment.outputs.tests }}
kafkaVersion:
description: "Kafka version used for most of the tests"
value: ${{ steps.parse_comment.outputs.kafkaVersion }}
releaseVersion:
description: "Release version a.k.a docker tag of released images"
value: ${{ steps.parse_comment.outputs.releaseVersion }}
kubeVersion:
description: "Used Kubernetes version for Kind/Minikube. Note that for Kind you have to use whole image with sha digest!"
value: ${{ steps.parse_comment.outputs.kubeVersion }}
kindVersion:
description: "Version of Kind binary to install (e.g. '0.29.0'). Defaults to '0.31.0' if empty. In case you use different from default version of Kind, you should reference full image via `kindVersion` parameter to achieve supported configuration"
value: ${{ steps.parse_comment.outputs.kindVersion }}
parallel:
description: "How many tests will be executed in parallel"
value: ${{ steps.parse_comment.outputs.parallel }}
ipFamily:
description: "IP family for the Kind cluster (ipv4, ipv6, dual)"
value: ${{ steps.parse_comment.outputs.ipFamily }}
clusterSecurityEncryption:
description: "Encryption used for the internal Kafka cluster communication"
value: ${{ steps.parse_comment.outputs.clusterSecurityEncryption }}
clusterSecurityAuthentication:
description: "Authentication used for the internal Kafka cluster communication"
value: ${{ steps.parse_comment.outputs.clusterSecurityAuthentication }}
runs:
using: "composite"
steps:
- name: Build Comment
id: build_comment
uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
env:
INPUT_PIPELINE: ${{ inputs.pipeline }}
INPUT_KAFKA_VERSION: ${{ inputs.kafkaVersion }}
INPUT_CLUSTER_SECURITY_ENCRYPTION: ${{ inputs.clusterSecurityEncryption }}
INPUT_CLUSTER_SECURITY_AUTHENTICATION: ${{ inputs.clusterSecurityAuthentication }}
with:
script: |
const body = context.payload?.comment?.body ?? '';
const pipeline = process.env.INPUT_PIPELINE || 'smoke';
const fallback = `/gha run pipeline=${pipeline} kafkaVersion=${process.env.INPUT_KAFKA_VERSION}`
+ ` clusterSecurityEncryption=${process.env.INPUT_CLUSTER_SECURITY_ENCRYPTION}`
+ ` clusterSecurityAuthentication=${process.env.INPUT_CLUSTER_SECURITY_AUTHENTICATION}`;
const builtComment = (body && body.trim().length) ? body : fallback;
core.setOutput('builtComment', builtComment);
core.info(`Parsed builtComment: ${builtComment}`);
- name: Parse Comment
id: parse_comment
uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
env:
INPUT_RELEASE_VERSION: ${{ inputs.releaseVersion }}
BUILT_COMMENT: ${{ steps.build_comment.outputs.builtComment }}
with:
script: |
const comment = process.env.BUILT_COMMENT;
// Remove all backticks from the comment
const sanitized = comment.replace(/`/g, '');
// Create one-line comment in case it is multi-line
const flat = sanitized.replace(/\s+/g, ' ').trim();
// Create lower-case
const lower = flat.toLowerCase();
// Check whether the comment starts with /gha run
const starts = /^\s*\/gha\s+run\b/i.test(sanitized);
// Function for getting parameter from string
const getParameter = (key, src = flat) => {
const regex = new RegExp(`\\b${key}=("([^"]*)"|'([^']*)'|([^\\s]+))`, 'i');
const match = src.match(regex);
if (!match) {
return '';
}
return match[2] ?? match[3] ?? match[4] ?? '';
};
const DEFAULTS = {
pipelines: '',
profiles: '',
featureGate: '-UseConnectBuildWithBuildah,+UseBackgroundPodDeletion',
rbacScope: 'CLUSTER',
installType: 'yaml',
parallel: '1',
kafkaVersion: 'latest',
kubeVersion: 'latest',
kindVersion: '',
ipFamily: 'ipv4',
// Defaults used by the Cluster Operator when the `strimzi.io/internal-cluster-security` annotation is not set
clusterSecurityEncryption: 'tls',
clusterSecurityAuthentication: 'mtls',
};
let pipelineList = '', profileList = '';
if (starts) {
const pipe = getParameter('pipeline', lower);
const prof = getParameter('profile', lower);
if (pipe) {
pipelineList = pipe;
} else {
profileList = prof || DEFAULTS.profiles;
}
}
const out = {
pipelineList,
profileList,
agent: getParameter('agent', lower),
architecture: getParameter('architecture', lower),
strimzi_feature_gates: getParameter('strimzi_feature_gates', sanitized), // keep case
strimzi_rbac_scope: getParameter('strimzi_rbac_scope', sanitized), // keep case
cluster_operator_install_type: getParameter('cluster_operator_install_type', lower) || DEFAULTS.installType,
parallel: getParameter('parallel', lower) || DEFAULTS.parallel,
groups: getParameter('groups', sanitized),
tests: getParameter('tests', sanitized),
kafkaVersion: getParameter('kafkaversion', lower) || DEFAULTS.kafkaVersion,
kubeVersion: getParameter('kubeversion', lower) || DEFAULTS.kubeVersion,
kindVersion: getParameter('kindversion', lower) || DEFAULTS.kindVersion,
ipFamily: getParameter('ipfamily', lower) || DEFAULTS.ipFamily,
releaseVersion: process.env.INPUT_RELEASE_VERSION || 'latest',
clusterSecurityEncryption: getParameter('clustersecurityencryption', lower) || DEFAULTS.clusterSecurityEncryption,
clusterSecurityAuthentication: getParameter('clustersecurityauthentication', lower) || DEFAULTS.clusterSecurityAuthentication,
};
// Only the supported internal cluster security types can be used
const CLUSTER_SECURITY_ENCRYPTION_TYPES = ['tls', 'none'];
const CLUSTER_SECURITY_AUTHENTICATION_TYPES = ['mtls', 'service-account', 'none'];
if (!CLUSTER_SECURITY_ENCRYPTION_TYPES.includes(out.clusterSecurityEncryption)) {
core.setFailed(`Invalid internal cluster security configuration: clusterSecurityEncryption=${out.clusterSecurityEncryption} is not supported. Supported values are: ${CLUSTER_SECURITY_ENCRYPTION_TYPES.join(', ')}`);
return;
}
if (!CLUSTER_SECURITY_AUTHENTICATION_TYPES.includes(out.clusterSecurityAuthentication)) {
core.setFailed(`Invalid internal cluster security configuration: clusterSecurityAuthentication=${out.clusterSecurityAuthentication} is not supported. Supported values are: ${CLUSTER_SECURITY_AUTHENTICATION_TYPES.join(', ')}`);
return;
}
// mTLS authentication of the internal cluster communication can be used only with TLS encryption
if (out.clusterSecurityAuthentication === 'mtls' && out.clusterSecurityEncryption !== 'tls') {
core.setFailed(`Invalid internal cluster security configuration: clusterSecurityAuthentication=mtls can be used only with clusterSecurityEncryption=tls`);
return;
}
if (starts && !out.pipelineList && !out.profileList) {
out.profileList = DEFAULTS.profiles;
}
// Export collected data as outputs
for (const [k, v] of Object.entries(out)) {
core.setOutput(k, v);
}
core.info(`Parsed:\n${JSON.stringify(out, null, 2)}`);