16
16
type : string
17
17
description : " Whether to recreate the VM"
18
18
default : " false"
19
+ simulate_scheduled_run :
20
+ required : false
21
+ type : boolean
22
+ description : " Simulate a scheduled run"
23
+ default : false
24
+ schedule :
25
+ # Run at midnight UTC every day
26
+ # Purpose: This scheduled run performs regular vulnerability scans of the codebase
27
+ # and sends notifications to Slack when new critical vulnerabilities are found.
28
+ # The scan results are used to maintain security standards and address issues promptly.
29
+ - cron : ' 0 0 * * *'
19
30
20
31
jobs :
21
32
create-runner :
36
47
cancel-in-progress : true
37
48
outputs :
38
49
is_main_branch : ${{ (github.head_ref || github.ref) == 'refs/heads/main' }}
50
+ is_scheduled_run : ${{ github.event_name == 'schedule' || inputs.simulate_scheduled_run == true }}
39
51
version : ${{ steps.branches.outputs.sanitized-branch-name }}-gha.${{github.run_number}}
40
52
preview_enable : ${{ contains( steps.pr-details.outputs.pr_body, '[x] /werft with-preview') || (steps.output.outputs.with_integration_tests != '') }}
41
53
preview_name : ${{ github.head_ref || github.ref_name }}
@@ -98,14 +110,15 @@ jobs:
98
110
name : Build previewctl
99
111
if : |
100
112
(needs.configuration.outputs.pr_no_diff_skip != 'true') &&
101
- (needs.configuration.outputs.preview_enable == 'true')
113
+ (needs.configuration.outputs.preview_enable == 'true') &&
114
+ (needs.configuration.outputs.is_scheduled_run != 'true')
102
115
needs : [ configuration, create-runner ]
103
116
concurrency :
104
117
group : ${{ github.ref == 'refs/heads/main' && github.run_id || github.sha }}-build-previewctl
105
118
cancel-in-progress : ${{ needs.configuration.outputs.is_main_branch == 'false' }}
106
119
runs-on : ${{ needs.create-runner.outputs.label }}
107
120
container :
108
- image : eu.gcr.io/gitpod-core-dev/dev/dev-environment:main-gha.32399
121
+ image : eu.gcr.io/gitpod-core-dev/dev/dev-environment:main-gha.32507
109
122
steps :
110
123
- uses : actions/checkout@v4
111
124
- name : Setup Environment
@@ -126,7 +139,8 @@ jobs:
126
139
if : |
127
140
(needs.configuration.outputs.pr_no_diff_skip != 'true') &&
128
141
(needs.configuration.outputs.preview_enable == 'true') &&
129
- (needs.configuration.outputs.is_main_branch != 'true')
142
+ (needs.configuration.outputs.is_main_branch != 'true') &&
143
+ (needs.configuration.outputs.is_scheduled_run != 'true')
130
144
runs-on : ${{ needs.create-runner.outputs.label }}
131
145
concurrency :
132
146
group : ${{ github.ref == 'refs/heads/main' && github.run_id || github.sha }}-infrastructure
@@ -154,6 +168,8 @@ jobs:
154
168
name : Build Gitpod
155
169
needs : [ configuration, create-runner ]
156
170
runs-on : ${{ needs.create-runner.outputs.label }}
171
+ outputs :
172
+ affected_packages : ${{ steps.check_vulnerabilities.outputs.affected_packages }}
157
173
concurrency :
158
174
group : ${{ github.ref == 'refs/heads/main' && github.run_id || github.sha }}-build-gitpod
159
175
cancel-in-progress : ${{ needs.configuration.outputs.is_main_branch == 'false' }}
@@ -172,7 +188,7 @@ jobs:
172
188
ports :
173
189
- 6379:6379
174
190
container :
175
- image : eu.gcr.io/gitpod-core-dev/dev/dev-environment:main-gha.32399
191
+ image : eu.gcr.io/gitpod-core-dev/dev/dev-environment:main-gha.32507
176
192
env :
177
193
DB_HOST : " mysql"
178
194
DB_PORT : " 23306"
@@ -299,7 +315,7 @@ jobs:
299
315
300
316
exit $RESULT
301
317
- name : Tag the release
302
- if : github.ref == 'refs/heads/main'
318
+ if : github.ref == 'refs/heads/main' && needs.configuration.outputs.is_scheduled_run != 'true'
303
319
run : |
304
320
git config --global user.name $GITHUB_USER
305
321
git config --global user.email $GITHUB_EMAIL
@@ -309,36 +325,83 @@ jobs:
309
325
GITHUB_USER : roboquat
310
326
311
327
VERSION : ${{ needs.configuration.outputs.version }}
312
-
313
- trivy-scan :
314
- name : " Scan Images for Vulnerabilities"
315
- needs :
316
- - configuration
317
- - build-gitpod
318
- - create-runner
319
- runs-on : ${{ needs.create-runner.outputs.label }}
320
- container :
321
- image : eu.gcr.io/gitpod-core-dev/dev/dev-environment:main-gha.32399
322
- steps :
323
- - uses : actions/checkout@v4
324
- - name : Setup Environment
325
- uses : ./.github/actions/setup-environment
326
- with :
327
- identity_provider : ${{ github.ref == 'refs/heads/main' && secrets.CORE_DEV_PROVIDER || secrets.DEV_PREVIEW_PROVIDER }}
328
- service_account : ${{ github.ref == 'refs/heads/main' && secrets.CORE_DEV_SA || secrets.DEV_PREVIEW_SA }}
329
- leeway_segment_key : ${{ secrets.LEEWAY_SEGMENT_KEY }}
330
- - name : Scan Images for Vulnerabilities
328
+ - name : Scan for Vulnerabilities
329
+ id : scan
331
330
shell : bash
332
331
env :
333
- INSTALLER_IMAGE_BASE_REPO : ${{needs.configuration.outputs.image_repo_base}}
332
+ VERSION : ${{needs.configuration.outputs.version}}
333
+ PUBLISH_TO_NPM : ${{ needs.configuration.outputs.publish_to_npm == 'true' || needs.configuration.outputs.is_main_branch == 'true' }}
334
+ PUBLISH_TO_JBPM : ${{ needs.configuration.outputs.publish_to_jbmp == 'true' || needs.configuration.outputs.is_main_branch == 'true' }}
335
+ LEEWAY_REMOTE_CACHE_BUCKET : ${{needs.configuration.outputs.leeway_cache_bucket}}
336
+ IMAGE_REPO_BASE : ${{needs.configuration.outputs.image_repo_base}}/build
337
+ run : |
338
+ [[ "$PR_NO_CACHE" = "true" ]] && CACHE="none" || CACHE="remote"
339
+ [[ "$PR_NO_TEST" = "true" ]] && TEST="--dont-test" || TEST=""
340
+ [[ "${PUBLISH_TO_NPM}" = 'true' ]] && NPM_PUBLISH_TRIGGER=$(date +%s%3N) || NPM_PUBLISH_TRIGGER="false"
341
+
342
+ sboms_dir=$(mktemp -d)
343
+ CI= leeway sbom export components:needs-vuln-scan --with-dependencies --output-dir "$sboms_dir" \
344
+ -Dversion=$VERSION \
345
+ --docker-build-options network=host \
346
+ --max-concurrent-tasks 1 \
347
+ -DlocalAppVersion=$VERSION \
348
+ -DpublishToNPM="${PUBLISH_TO_NPM}" \
349
+ -DnpmPublishTrigger="${NPM_PUBLISH_TRIGGER}" \
350
+ -DpublishToJBMarketplace="${PUBLISH_TO_JBPM}" \
351
+ -DimageRepoBase=$IMAGE_REPO_BASE
352
+
353
+ scans_dir=$(mktemp -d)
354
+ CI= leeway sbom scan components:needs-vuln-scan --with-dependencies --output-dir "$scans_dir" \
355
+ -Dversion=$VERSION \
356
+ --docker-build-options network=host \
357
+ --max-concurrent-tasks 1 \
358
+ -DlocalAppVersion=$VERSION \
359
+ -DpublishToNPM="${PUBLISH_TO_NPM}" \
360
+ -DnpmPublishTrigger="${NPM_PUBLISH_TRIGGER}" \
361
+ -DpublishToJBMarketplace="${PUBLISH_TO_JBPM}" \
362
+ -DimageRepoBase=$IMAGE_REPO_BASE || RESULT=$?
363
+
364
+ {
365
+ echo "leeway_sboms_dir=$sboms_dir"
366
+ echo "leeway_vulnerability_reports_dir=$scans_dir"
367
+ } >> $GITHUB_OUTPUT
368
+
369
+ cat "$scans_dir/vulnerability-summary.md" >> $GITHUB_STEP_SUMMARY
370
+
371
+ exit $RESULT
372
+ - name : Check for Critical Vulnerabilities
373
+ if : needs.configuration.outputs.is_scheduled_run == 'true'
374
+ id : check_vulnerabilities
375
+ shell : bash
334
376
run : |
335
- ./scripts/trivy/trivy-scan-images.sh ${{ needs.configuration.outputs.version }} CRITICAL
336
- exit $?
377
+ # Parse vulnerability-stats.json from the scans directory
378
+ CRITICAL_PACKAGES=$(jq -r '.[] | select(.critical > 0) | "\(.name): \(.critical) critical vulnerabilities"' "${{ steps.scan.outputs.leeway_vulnerability_reports_dir }}/vulnerability-stats.json")
337
379
380
+ # If there are critical packages, list them and fail the build
381
+ if [ -n "$CRITICAL_PACKAGES" ]; then
382
+ echo "::error::Critical vulnerabilities found in the following packages:"
383
+ echo "$CRITICAL_PACKAGES" | tee -a $GITHUB_STEP_SUMMARY
384
+ echo "affected_packages<<EOF" >> $GITHUB_OUTPUT
385
+ echo "$CRITICAL_PACKAGES" >> $GITHUB_OUTPUT
386
+ echo "EOF" >> $GITHUB_OUTPUT
387
+ exit 1
388
+ else
389
+ echo "No critical vulnerabilities found."
390
+ fi
391
+ - name : Upload SBOMs
392
+ uses : actions/upload-artifact@v4
393
+ with :
394
+ name : sboms
395
+ path : ${{ steps.scan.outputs.leeway_sboms_dir }}
396
+ - name : Upload vulnerability reports
397
+ uses : actions/upload-artifact@v4
398
+ with :
399
+ name : vulnerability-reports
400
+ path : ${{ steps.scan.outputs.leeway_vulnerability_reports_dir }}
338
401
install-app :
339
402
runs-on : ${{ needs.create-runner.outputs.label }}
340
- needs : [ configuration, build-gitpod, trivy-scan, create-runner ]
341
- if : ${{ needs.configuration.outputs.is_main_branch == 'true' }}
403
+ needs : [ configuration, build-gitpod, create-runner ]
404
+ if : ${{ needs.configuration.outputs.is_main_branch == 'true' && needs.configuration.outputs.is_scheduled_run != 'true' }}
342
405
strategy :
343
406
fail-fast : false
344
407
matrix :
@@ -375,9 +438,9 @@ jobs:
375
438
- configuration
376
439
- build-previewctl
377
440
- build-gitpod
378
- - trivy-scan
379
441
- infrastructure
380
442
- create-runner
443
+ if : needs.configuration.outputs.is_scheduled_run != 'true'
381
444
runs-on : ${{ needs.create-runner.outputs.label }}
382
445
concurrency :
383
446
group : ${{ github.ref == 'refs/heads/main' && github.run_id || github.sha }}-install
@@ -428,7 +491,7 @@ jobs:
428
491
name : " Install Monitoring Satellite"
429
492
needs : [ infrastructure, build-previewctl, create-runner ]
430
493
runs-on : ${{ needs.create-runner.outputs.label }}
431
- if : needs.configuration.outputs.with_monitoring == 'true'
494
+ if : needs.configuration.outputs.with_monitoring == 'true' && needs.configuration.outputs.is_scheduled_run != 'true'
432
495
concurrency :
433
496
group : ${{ github.ref == 'refs/heads/main' && github.run_id || github.sha }}-monitoring
434
497
cancel-in-progress : true
@@ -458,8 +521,8 @@ jobs:
458
521
- create-runner
459
522
runs-on : ${{ needs.create-runner.outputs.label }}
460
523
container :
461
- image : eu.gcr.io/gitpod-core-dev/dev/dev-environment:main-gha.32399
462
- if : needs.configuration.outputs.with_integration_tests != ''
524
+ image : eu.gcr.io/gitpod-core-dev/dev/dev-environment:main-gha.32507
525
+ if : needs.configuration.outputs.with_integration_tests != '' && needs.configuration.outputs.is_scheduled_run != 'true'
463
526
concurrency :
464
527
group : ${{ needs.configuration.outputs.preview_name }}-integration-test
465
528
cancel-in-progress : true
@@ -489,7 +552,7 @@ jobs:
489
552
- configuration
490
553
- build-gitpod
491
554
- create-runner
492
- if : needs.configuration.outputs.is_main_branch == 'true'
555
+ if : needs.configuration.outputs.is_main_branch == 'true' && needs.configuration.outputs.is_scheduled_run != 'true'
493
556
uses : ./.github/workflows/workspace-integration-tests.yml
494
557
with :
495
558
version : ${{ needs.configuration.outputs.version }}
@@ -501,7 +564,7 @@ jobs:
501
564
- configuration
502
565
- build-gitpod
503
566
- create-runner
504
- if : needs.configuration.outputs.is_main_branch == 'true'
567
+ if : needs.configuration.outputs.is_main_branch == 'true' && needs.configuration.outputs.is_scheduled_run != 'true'
505
568
uses : ./.github/workflows/code-updates.yml
506
569
secrets : inherit
507
570
@@ -511,10 +574,31 @@ jobs:
511
574
- configuration
512
575
- build-gitpod
513
576
- create-runner
514
- if : needs.configuration.outputs.is_main_branch == 'true'
577
+ if : needs.configuration.outputs.is_main_branch == 'true' && needs.configuration.outputs.is_scheduled_run != 'true'
515
578
uses : ./.github/workflows/jetbrains-updates.yml
516
579
secrets : inherit
517
580
581
+ notify-scheduled-failure :
582
+ name : " Notify on scheduled run failure"
583
+ if : needs.configuration.outputs.is_scheduled_run == 'true' && failure()
584
+ needs :
585
+ - configuration
586
+ - build-gitpod
587
+ - workspace-integration-tests-main
588
+ - ide-code-updates
589
+ - ide-jb-updates
590
+ runs-on : ubuntu-latest
591
+ steps :
592
+ - name : Slack Notification
593
+ uses : rtCamp/action-slack-notify@v2
594
+ env :
595
+ SLACK_WEBHOOK : ${{ secrets.WORKSPACE_SLACK_WEBHOOK }}
596
+ SLACK_ICON_EMOJI : " :x:"
597
+ SLACK_USERNAME : " Scheduled Build"
598
+ SLACK_COLOR : " danger"
599
+ SLACK_MESSAGE : " ⚠️ Security Alert: Daily vulnerability scan detected critical vulnerabilities in the following packages:\n ${{ needs.build-gitpod.outputs.affected_packages }}"
600
+ SLACK_FOOTER : " <${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }}|View Workflow Logs>"
601
+
518
602
delete-runner :
519
603
if : always()
520
604
needs :
@@ -523,11 +607,11 @@ jobs:
523
607
- build-previewctl
524
608
- infrastructure
525
609
- build-gitpod
526
- - trivy-scan
527
610
- install-app
528
611
- install
529
612
- monitoring
530
613
- integration-test
614
+ - notify-scheduled-failure
531
615
uses : gitpod-io/gce-github-runner/.github/workflows/delete-vm.yml@main
532
616
secrets :
533
617
gcp_credentials : ${{ secrets.SELF_HOSTED_GITHUB_RUNNER_GCP_CREDENTIALS }}
0 commit comments