-
Notifications
You must be signed in to change notification settings - Fork 38
428 lines (355 loc) · 16.4 KB
/
Copy pathcreate-sample-releases.yml
File metadata and controls
428 lines (355 loc) · 16.4 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
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
name: Build and Release Sample Artifacts
on:
push:
branches: [main]
paths:
- '*/*/release-config.yml'
- '*/**'
- '!.github/**'
- '!LICENSE'
- '.github/workflows/create-sample-releases.yml'
workflow_dispatch:
inputs:
force_rebuild:
description: 'Force rebuild all artifacts'
required: false
default: false
type: boolean
permissions:
contents: write
actions: read
jobs:
build-artifacts:
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v4
with:
fetch-depth: 0
- name: Set up Node.js
uses: actions/setup-node@v4
with:
node-version: '18'
- name: Create artifacts directory
run: mkdir -p artifacts
- name: Find and validate release configurations
run: |
echo "🔍 Finding release configurations..."
RELEASE_CONFIGS=$(find . -name "release-config.yml" -not -path "./.git/*" | sort)
if [ -z "$RELEASE_CONFIGS" ]; then
echo "❌ No release-config.yml files found!"
echo "📂 Available directories:"
find . -type d -maxdepth 3 | head -20
exit 1
fi
echo "✅ Found release configurations:"
echo "$RELEASE_CONFIGS"
# Validate each config file
for config_file in $RELEASE_CONFIGS; do
echo "📄 Validating: $config_file"
# Check if it has required fields and included: true
if grep -q "^category:" "$config_file" && grep -q "^framework:" "$config_file"; then
INCLUDED=$(grep "^included:" "$config_file" | sed 's/included: *//' | tr -d ' ')
if [ "$INCLUDED" = "true" ]; then
echo " ✅ Valid configuration (included: true)"
else
echo " ⏭️ Skipping (included: $INCLUDED)"
fi
else
echo " ❌ Missing required fields (category, framework) in $config_file"
exit 1
fi
done
- name: Check if changed files are in configured directories
run: |
echo "🔍 Checking if changes affect configured quickstarts..."
# Get list of directories with release-config.yml
CONFIG_DIRS=$(find . -name "release-config.yml" -not -path "./.git/*" -exec dirname {} \; | sort)
echo "📂 Directories with release-config.yml:"
echo "$CONFIG_DIRS"
# If this is a manual trigger, rebuild all
if [ "${{ github.event_name }}" = "workflow_dispatch" ]; then
echo "🔄 Manual trigger - will rebuild all configured samples"
echo "SHOULD_BUILD=true" >> $GITHUB_ENV
exit 0
fi
# Check if any changed files are in directories with release-config.yml
CHANGED_FILES=$(git diff --name-only HEAD~1 HEAD 2>/dev/null || echo "")
if [ -z "$CHANGED_FILES" ]; then
echo "📝 No changed files detected, building all"
echo "SHOULD_BUILD=true" >> $GITHUB_ENV
exit 0
fi
echo "📝 Changed files:"
echo "$CHANGED_FILES"
# Check if the workflow file itself was changed
if echo "$CHANGED_FILES" | grep -q "^\.github/workflows/create-sample-releases\.yml$"; then
echo "🔧 Workflow file changed - forcing rebuild of all samples"
echo "SHOULD_BUILD=true" >> $GITHUB_ENV
exit 0
fi
SHOULD_BUILD=false
for config_dir in $CONFIG_DIRS; do
# Remove leading ./
clean_dir=$(echo "$config_dir" | sed 's|^\./||')
# Check if any changed file is in this directory
if echo "$CHANGED_FILES" | grep -q "^$clean_dir/"; then
echo "✅ Changes detected in configured directory: $clean_dir"
SHOULD_BUILD=true
break
fi
done
if [ "$SHOULD_BUILD" = "true" ]; then
echo "🔄 Will rebuild artifacts (changes in configured directories)"
echo "SHOULD_BUILD=true" >> $GITHUB_ENV
else
echo "⏭️ No changes in configured directories, skipping build"
echo "SHOULD_BUILD=false" >> $GITHUB_ENV
fi
- name: Download existing release assets (if any)
if: env.SHOULD_BUILD == 'true'
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
echo "📥 Checking for existing 'latest' release assets..."
# Get changed files
CHANGED_FILES=$(git diff --name-only HEAD~1 HEAD 2>/dev/null || echo "")
# Determine if we should preserve existing assets
PRESERVE_ASSETS=true
if echo "$CHANGED_FILES" | grep -q "^\.github/workflows/create-sample-releases\.yml$"; then
echo "🔧 Workflow file changed - skipping asset preservation (full rebuild)"
PRESERVE_ASSETS=false
elif [ "${{ github.event_name }}" = "workflow_dispatch" ] && [ "${{ github.event.inputs.force_rebuild }}" = "true" ]; then
echo "🔄 Force rebuild requested - skipping asset preservation (full rebuild)"
PRESERVE_ASSETS=false
elif [ "${{ github.event_name }}" = "workflow_dispatch" ]; then
echo "🔄 Manual trigger - skipping asset preservation (full rebuild)"
PRESERVE_ASSETS=false
fi
if [ "$PRESERVE_ASSETS" = "true" ]; then
# Check if latest release exists
if gh release view latest >/dev/null 2>&1; then
echo "✅ Found existing 'latest' release"
# Download existing assets to preserve them
mkdir -p existing_assets
gh release download latest --dir existing_assets 2>/dev/null || echo "No assets to download"
# Move existing assets to artifacts directory
for existing_zip in existing_assets/*.zip; do
if [ -f "$existing_zip" ]; then
FILENAME=$(basename "$existing_zip")
echo "📦 Preserving existing: $FILENAME"
cp "$existing_zip" "artifacts/"
fi
done
rm -rf existing_assets
else
echo "ℹ️ No existing 'latest' release found"
fi
else
echo "🧹 Skipping asset preservation - will rebuild all from scratch"
fi
- name: Build quickstart packages from configs
if: env.SHOULD_BUILD == 'true'
run: |
echo "📦 Building sample packages from configurations..."
# Store the absolute path to artifacts directory
ARTIFACTS_DIR="$(pwd)/artifacts"
# Get changed files to determine which directories to rebuild
CHANGED_FILES=$(git diff --name-only HEAD~1 HEAD 2>/dev/null || echo "")
# Check if workflow file changed (rebuild all if so)
REBUILD_ALL=false
if echo "$CHANGED_FILES" | grep -q "^\.github/workflows/create-sample-releases\.yml$"; then
echo "🔧 Workflow file changed - rebuilding ALL samples"
REBUILD_ALL=true
elif [ "${{ github.event_name }}" = "workflow_dispatch" ]; then
echo "🔄 Manual trigger - rebuilding ALL samples"
REBUILD_ALL=true
elif [ "${{ github.event.inputs.force_rebuild }}" = "true" ]; then
echo "🔄 Force rebuild requested - rebuilding ALL samples"
REBUILD_ALL=true
elif [ -z "$CHANGED_FILES" ]; then
echo "📝 No changed files detected - rebuilding ALL samples"
REBUILD_ALL=true
fi
find . -name "release-config.yml" -not -path "./.git/*" | while read config_file; do
sample_dir=$(dirname "$config_file")
clean_dir=$(echo "$sample_dir" | sed 's|^\./||')
# Check if this specific directory should be rebuilt
SHOULD_REBUILD=false
if [ "$REBUILD_ALL" = "true" ]; then
SHOULD_REBUILD=true
echo "🔨 Processing: $config_file (rebuild all)"
elif echo "$CHANGED_FILES" | grep -q "^$clean_dir/"; then
SHOULD_REBUILD=true
echo "🔨 Processing: $config_file (changes detected in $clean_dir)"
else
echo "⏭️ Skipping: $config_file (no changes in $clean_dir)"
continue
fi
# Only process if this directory should be rebuilt
if [ "$SHOULD_REBUILD" = "true" ]; then
cd "$sample_dir"
# Check if this sample should be included
INCLUDED=$(grep "^included:" release-config.yml | sed 's/included: *//' | tr -d ' ')
if [ "$INCLUDED" != "true" ]; then
echo "⏭️ Skipping (included: $INCLUDED)"
cd - > /dev/null
continue
fi
# Extract configuration using basic shell parsing
CATEGORY=$(grep "^category:" release-config.yml | sed 's/category: *"//' | sed 's/"$//' | tr -d ' ')
FRAMEWORK=$(grep "^framework:" release-config.yml | sed 's/framework: *"//' | sed 's/"$//' | tr -d ' ')
if [ -z "$CATEGORY" ] || [ -z "$FRAMEWORK" ]; then
echo "❌ Missing category or framework in $config_file"
cd - > /dev/null
continue
fi
# Build zip filename from category and framework
ZIP_FILENAME="${CATEGORY}-${FRAMEWORK}-sample"
echo "📦 Building: $ZIP_FILENAME.zip"
echo "🏷️ Category: $CATEGORY, Framework: $FRAMEWORK"
echo "📁 Current directory: $(pwd)"
echo "📁 Artifacts directory: $ARTIFACTS_DIR"
# Create zip with absolute path to artifacts directory (this will overwrite existing)
zip -r "${ARTIFACTS_DIR}/${ZIP_FILENAME}.zip" . \
--exclude=".git/*" \
--exclude="node_modules/*" \
--exclude="__pycache__/*" \
--exclude="*.pyc" \
--exclude="*.pyo" \
--exclude="dist/*" \
--exclude="build/*" \
--exclude="venv/*" \
--exclude=".venv/*" \
--exclude=".pytest_cache/*" \
--exclude=".coverage" \
--exclude="coverage/*" \
--exclude="*.log" \
--exclude=".DS_Store" \
--exclude="Thumbs.db" \
--exclude=".idea/*" \
--exclude=".vscode/*" \
--exclude="temp/*" \
--exclude="tmp/*" \
--exclude="*.tmp" \
--exclude=".cache/*" \
--exclude=".next/*" \
--exclude="target/*" \
--exclude=".gradle/*" \
--exclude="bin/*" \
--exclude="obj/*" \
--exclude=".env" \
--exclude=".env.local" \
--exclude=".env.production" \
--exclude=".env.development" \
--exclude="release-config.yml"
# Add custom exclusions from config if they exist
if grep -q "^exclude_patterns:" release-config.yml; then
echo "📋 Adding custom exclusions from config..."
# Create a temporary zip with custom exclusions
TEMP_ZIP="${ARTIFACTS_DIR}/temp_${ZIP_FILENAME}.zip"
mv "${ARTIFACTS_DIR}/${ZIP_FILENAME}.zip" "$TEMP_ZIP"
# Extract and re-zip with custom exclusions
mkdir -p temp_extract
cd temp_extract
unzip -q "$TEMP_ZIP"
# Apply custom exclusions
while IFS= read -r line; do
if echo "$line" | grep -q "^ - "; then
pattern=$(echo "$line" | sed 's/^ - "//' | sed 's/"$//' | tr -d ' ')
if [ ! -z "$pattern" ]; then
echo " Excluding custom pattern: $pattern"
find . -name "$pattern" -delete 2>/dev/null || true
fi
fi
done < <(grep -A 20 "^exclude_patterns:" ../release-config.yml)
# Re-create zip with absolute path
zip -r "${ARTIFACTS_DIR}/${ZIP_FILENAME}.zip" .
cd ..
rm -rf temp_extract "$TEMP_ZIP"
fi
cd - > /dev/null
if [ -f "${ARTIFACTS_DIR}/${ZIP_FILENAME}.zip" ]; then
SIZE=$(du -h "${ARTIFACTS_DIR}/${ZIP_FILENAME}.zip" | cut -f1)
echo "✅ Created/Updated: ${ZIP_FILENAME}.zip ($SIZE)"
else
echo "❌ Failed to create: ${ZIP_FILENAME}.zip"
fi
fi
done
# Count artifacts AFTER the loop completes
ARTIFACT_COUNT=$(ls artifacts/*.zip 2>/dev/null | wc -l)
echo "ARTIFACT_COUNT=$ARTIFACT_COUNT" >> $GITHUB_ENV
echo "📊 Total artifacts for release: $ARTIFACT_COUNT"
# Debug: List what will be included in the release
echo "📦 Artifacts for release:"
ls -la artifacts/ || echo "No artifacts directory or files found"
- name: Security scan artifacts
if: env.SHOULD_BUILD == 'true'
run: |
echo "🔍 Performing security checks on artifacts..."
for zip_file in artifacts/*.zip; do
if [ -f "$zip_file" ]; then
echo "Scanning: $(basename "$zip_file")"
# Check for actual sensitive files (not config examples)
SENSITIVE_FILES=$(unzip -l "$zip_file" 2>/dev/null | grep -E "\.(key|pem|p12|pfx)$|/\.env$|\.env\.(local|production|development)$|secret\." | grep -v -E "\.(example|sample|template)" || true)
if [ ! -z "$SENSITIVE_FILES" ]; then
echo "⚠️ Warning: Potential sensitive files in $(basename "$zip_file"):"
echo "$SENSITIVE_FILES"
else
echo "✅ No sensitive files detected"
fi
fi
done
- name: Generate release notes
if: env.SHOULD_BUILD == 'true'
run: |
echo "📝 Generating release notes..."
cat > release_notes.md << EOF
# Quickstart Samples
This release contains the latest version of sample applications for various frameworks and quickstarts. See Assets below for downloadable zip files of each quickstart.
For more information, visit [auth0.com/ai/docs](https://auth0.com/ai/docs).
---
**Generated:** $(date -u '+%Y-%m-%d %H:%M:%S UTC')
EOF
- name: Delete previous 'latest' release
if: env.SHOULD_BUILD == 'true'
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
echo "🗑️ Cleaning up previous 'latest' release..."
# Delete previous latest release (ignore errors if doesn't exist)
gh release delete latest --yes 2>/dev/null || echo "No previous 'latest' release found"
git push origin :refs/tags/latest 2>/dev/null || echo "No previous 'latest' tag found"
# Also clean up local tag
git tag -d latest 2>/dev/null || echo "No local 'latest' tag found"
- name: Create 'latest' release
if: env.SHOULD_BUILD == 'true'
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
echo "🚀 Creating 'latest' release..."
if [ "$ARTIFACT_COUNT" -eq 0 ]; then
echo "❌ No artifacts to release!"
exit 1
fi
echo "📦 Releasing $ARTIFACT_COUNT artifacts"
# Create the latest release
gh release create latest \
--title "Auth0 AI Sample Artifacts - Latest" \
--notes-file release_notes.md \
--latest \
artifacts/*.zip
echo "✅ Latest release created!"
echo "🔗 Your download URLs are now active:"
for zip_file in artifacts/*.zip; do
if [ -f "$zip_file" ]; then
FILENAME=$(basename "$zip_file")
echo " https://github.com/${{ github.repository }}/releases/latest/download/$FILENAME"
fi
done
- name: Skip build notification
if: env.SHOULD_BUILD == 'false'
run: |
echo "⏭️ Build skipped - no changes in directories with release-config.yml files"
echo "💡 To force a rebuild, use the manual workflow trigger"