Compare commits

..

24 Commits

Author SHA1 Message Date
daz
417ae3ccd7 Prepare for v3.1.0 release 2024-02-13 13:04:08 -07:00
Daz DeBoer
8a945e8ba7 Document use of debug logging with dependency-submission 2024-02-13 09:38:01 -07:00
daz
b61dbd2545 Test no dependency-graph for failing build 2024-02-12 22:03:45 -07:00
daz
2262487821 Use v1.2.2 of dep-graph plugin 2024-02-12 21:41:04 -07:00
daz
aaf44989e3 Use v1.2.1 of dep-graph plugin 2024-02-11 18:22:33 -07:00
Daz DeBoer
09bd32c78f Improve documentation for debug logging 2024-02-11 18:18:43 -07:00
daz
4b284311c3 Disable cache debug logging for workflows
This logging can now be enabled on a case-by-case basis using
GitHub Actions debugging.
2024-02-11 18:00:40 -07:00
Daz DeBoer
5e512f6e1d Merge pull request #40 from gradle/dd/v3.1
Improvements in preparation for v3.1
2024-02-11 17:45:41 -07:00
dependabot[bot]
d31af7fbe2 Bump org.junit.jupiter:junit-jupiter
Bumps [org.junit.jupiter:junit-jupiter](https://github.com/junit-team/junit5) from 5.10.1 to 5.10.2.
- [Release notes](https://github.com/junit-team/junit5/releases)
- [Commits](https://github.com/junit-team/junit5/compare/r5.10.1...r5.10.2)

---
updated-dependencies:
- dependency-name: org.junit.jupiter:junit-jupiter
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2024-02-11 17:37:17 -07:00
daz
b6ea7d5b78 Build outputs 2024-02-11 17:35:43 -07:00
daz
9eb8242410 Improvements to debug logging
- Enable cache debugging when ACTIONS_STEP_DEBUG is on
- Replace some info messages with debug
2024-02-11 17:35:10 -07:00
hfhbd
f4f7af32dc Configure --info and --stacktrace when GitHub ACTIONS_RUNNER_DEBUG is true
Fixes #6
2024-02-11 16:56:16 -07:00
daz
79414b4f92 Add link to workflow run from PR comment
Fixes #11
2024-02-11 16:53:03 -07:00
daz
e9c65b9fc0 Attempt to make build-scan links open in new tab
GitHub currently strips the target="_blank" from the rendered HTML,
but we'll leave this in since it's the desired behaviour.
2024-02-11 16:52:22 -07:00
daz
109be5d55b Disable isolated projects in dependency-submission
The 'resolveAllDependencies' task is incompatible with project isolation.
Pending a fix to the plugin, disable this feature when running the
dependency-submission action.

Fixes #39
2024-02-11 15:56:13 -07:00
Daz DeBoer
b776693a71 Fail nicely when dependency-submission is used after setup-gradle in the same Job (#37)
Previously, this would fail with a hard-to-diagnose error message.

Fixes #14
2024-02-08 23:16:54 -07:00
daz
2f23d645f2 Warn and make Gradle Wrapper script executable
Instead of failing the build, detect a non-executable wrapper file
and set the executable bit.

Fixes #17
2024-02-08 22:26:12 -07:00
daz
dfd22334ff Use gradle properties to disable features instead of CLI args
These gradle properties will be silently ignored on older Gradle versions,
whereas unknown command-line args will cause Gradle to fail.

Fixes #15
2024-02-08 21:55:52 -07:00
daz
9c837ee543 Test dependency-submission with gradle versions 2024-02-08 21:55:52 -07:00
Goooler
bc07b88bc0 Update Gradle 8.6 rc refs to the final version
https://github.com/gradle/gradle/releases/tag/v8.6.0

Signed-off-by: Goooler <wangzongler@gmail.com>
2024-02-08 21:38:25 -07:00
Daz DeBoer
7fda81ffd5 Document auto-publish of build scans 2024-01-31 13:04:12 -07:00
Daz DeBoer
e4ee7d7f94 Document process for resolving a vulnerability (#8) 2024-01-31 12:42:07 -07:00
Daz DeBoer
a02bb79881 Introduce a top-level section for "resolving a vulnerability" 2024-01-31 12:23:08 -07:00
Daz DeBoer
52d6180f95 Add 'finding dependency source' section to docs (#7) 2024-01-31 12:17:45 -07:00
40 changed files with 739 additions and 81 deletions

View File

@@ -10,7 +10,7 @@ dependencies {
api("org.apache.commons:commons-math3:3.6.1")
implementation("com.google.guava:guava:33.0.0-jre")
testImplementation("org.junit.jupiter:junit-jupiter:5.10.1")
testImplementation("org.junit.jupiter:junit-jupiter:5.10.2")
}
tasks.test {

View File

@@ -0,0 +1 @@
// Required to keep dependabot happy

View File

@@ -0,0 +1,8 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionSha256Sum=9d926787066a081739e8200858338b4a69e837c3a821a33aca9db09dd4a41026
distributionUrl=https\://services.gradle.org/distributions/gradle-8.5-bin.zip
networkTimeout=10000
validateDistributionUrl=true
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists

View File

@@ -0,0 +1,249 @@
#!/bin/sh
#
# Copyright © 2015-2021 the original authors.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# https://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
##############################################################################
#
# Gradle start up script for POSIX generated by Gradle.
#
# Important for running:
#
# (1) You need a POSIX-compliant shell to run this script. If your /bin/sh is
# noncompliant, but you have some other compliant shell such as ksh or
# bash, then to run this script, type that shell name before the whole
# command line, like:
#
# ksh Gradle
#
# Busybox and similar reduced shells will NOT work, because this script
# requires all of these POSIX shell features:
# * functions;
# * expansions «$var», «${var}», «${var:-default}», «${var+SET}»,
# «${var#prefix}», «${var%suffix}», and «$( cmd )»;
# * compound commands having a testable exit status, especially «case»;
# * various built-in commands including «command», «set», and «ulimit».
#
# Important for patching:
#
# (2) This script targets any POSIX shell, so it avoids extensions provided
# by Bash, Ksh, etc; in particular arrays are avoided.
#
# The "traditional" practice of packing multiple parameters into a
# space-separated string is a well documented source of bugs and security
# problems, so this is (mostly) avoided, by progressively accumulating
# options in "$@", and eventually passing that to Java.
#
# Where the inherited environment variables (DEFAULT_JVM_OPTS, JAVA_OPTS,
# and GRADLE_OPTS) rely on word-splitting, this is performed explicitly;
# see the in-line comments for details.
#
# There are tweaks for specific operating systems such as AIX, CygWin,
# Darwin, MinGW, and NonStop.
#
# (3) This script is generated from the Groovy template
# https://github.com/gradle/gradle/blob/HEAD/subprojects/plugins/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt
# within the Gradle project.
#
# You can find Gradle at https://github.com/gradle/gradle/.
#
##############################################################################
# Attempt to set APP_HOME
# Resolve links: $0 may be a link
app_path=$0
# Need this for daisy-chained symlinks.
while
APP_HOME=${app_path%"${app_path##*/}"} # leaves a trailing /; empty if no leading path
[ -h "$app_path" ]
do
ls=$( ls -ld "$app_path" )
link=${ls#*' -> '}
case $link in #(
/*) app_path=$link ;; #(
*) app_path=$APP_HOME$link ;;
esac
done
# This is normally unused
# shellcheck disable=SC2034
APP_BASE_NAME=${0##*/}
# Discard cd standard output in case $CDPATH is set (https://github.com/gradle/gradle/issues/25036)
APP_HOME=$( cd "${APP_HOME:-./}" > /dev/null && pwd -P ) || exit
# Use the maximum available, or set MAX_FD != -1 to use that value.
MAX_FD=maximum
warn () {
echo "$*"
} >&2
die () {
echo
echo "$*"
echo
exit 1
} >&2
# OS specific support (must be 'true' or 'false').
cygwin=false
msys=false
darwin=false
nonstop=false
case "$( uname )" in #(
CYGWIN* ) cygwin=true ;; #(
Darwin* ) darwin=true ;; #(
MSYS* | MINGW* ) msys=true ;; #(
NONSTOP* ) nonstop=true ;;
esac
CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
# Determine the Java command to use to start the JVM.
if [ -n "$JAVA_HOME" ] ; then
if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
# IBM's JDK on AIX uses strange locations for the executables
JAVACMD=$JAVA_HOME/jre/sh/java
else
JAVACMD=$JAVA_HOME/bin/java
fi
if [ ! -x "$JAVACMD" ] ; then
die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
Please set the JAVA_HOME variable in your environment to match the
location of your Java installation."
fi
else
JAVACMD=java
if ! command -v java >/dev/null 2>&1
then
die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
Please set the JAVA_HOME variable in your environment to match the
location of your Java installation."
fi
fi
# Increase the maximum file descriptors if we can.
if ! "$cygwin" && ! "$darwin" && ! "$nonstop" ; then
case $MAX_FD in #(
max*)
# In POSIX sh, ulimit -H is undefined. That's why the result is checked to see if it worked.
# shellcheck disable=SC2039,SC3045
MAX_FD=$( ulimit -H -n ) ||
warn "Could not query maximum file descriptor limit"
esac
case $MAX_FD in #(
'' | soft) :;; #(
*)
# In POSIX sh, ulimit -n is undefined. That's why the result is checked to see if it worked.
# shellcheck disable=SC2039,SC3045
ulimit -n "$MAX_FD" ||
warn "Could not set maximum file descriptor limit to $MAX_FD"
esac
fi
# Collect all arguments for the java command, stacking in reverse order:
# * args from the command line
# * the main class name
# * -classpath
# * -D...appname settings
# * --module-path (only if needed)
# * DEFAULT_JVM_OPTS, JAVA_OPTS, and GRADLE_OPTS environment variables.
# For Cygwin or MSYS, switch paths to Windows format before running java
if "$cygwin" || "$msys" ; then
APP_HOME=$( cygpath --path --mixed "$APP_HOME" )
CLASSPATH=$( cygpath --path --mixed "$CLASSPATH" )
JAVACMD=$( cygpath --unix "$JAVACMD" )
# Now convert the arguments - kludge to limit ourselves to /bin/sh
for arg do
if
case $arg in #(
-*) false ;; # don't mess with options #(
/?*) t=${arg#/} t=/${t%%/*} # looks like a POSIX filepath
[ -e "$t" ] ;; #(
*) false ;;
esac
then
arg=$( cygpath --path --ignore --mixed "$arg" )
fi
# Roll the args list around exactly as many times as the number of
# args, so each arg winds up back in the position where it started, but
# possibly modified.
#
# NB: a `for` loop captures its iteration list before it begins, so
# changing the positional parameters here affects neither the number of
# iterations, nor the values presented in `arg`.
shift # remove old arg
set -- "$@" "$arg" # push replacement arg
done
fi
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"'
# Collect all arguments for the java command:
# * DEFAULT_JVM_OPTS, JAVA_OPTS, JAVA_OPTS, and optsEnvironmentVar are not allowed to contain shell fragments,
# and any embedded shellness will be escaped.
# * For example: A user cannot expect ${Hostname} to be expanded, as it is an environment variable and will be
# treated as '${Hostname}' itself on the command line.
set -- \
"-Dorg.gradle.appname=$APP_BASE_NAME" \
-classpath "$CLASSPATH" \
org.gradle.wrapper.GradleWrapperMain \
"$@"
# Stop when "xargs" is not available.
if ! command -v xargs >/dev/null 2>&1
then
die "xargs is not available"
fi
# Use "xargs" to parse quoted args.
#
# With -n1 it outputs one arg per line, with the quotes and backslashes removed.
#
# In Bash we could simply go:
#
# readarray ARGS < <( xargs -n1 <<<"$var" ) &&
# set -- "${ARGS[@]}" "$@"
#
# but POSIX shell has neither arrays nor command substitution, so instead we
# post-process each arg (as a line of input to sed) to backslash-escape any
# character that might be a shell metacharacter, then use eval to reverse
# that process (while maintaining the separation between arguments), and wrap
# the whole thing up as a single "set" statement.
#
# This will of course break if any of these variables contains a newline or
# an unmatched quote.
#
eval "set -- $(
printf '%s\n' "$DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS" |
xargs -n1 |
sed ' s~[^-[:alnum:]+,./:=@_]~\\&~g; ' |
tr '\n' ' '
)" '"$@"'
exec "$JAVACMD" "$@"

View File

@@ -0,0 +1,92 @@
@rem
@rem Copyright 2015 the original author or authors.
@rem
@rem Licensed under the Apache License, Version 2.0 (the "License");
@rem you may not use this file except in compliance with the License.
@rem You may obtain a copy of the License at
@rem
@rem https://www.apache.org/licenses/LICENSE-2.0
@rem
@rem Unless required by applicable law or agreed to in writing, software
@rem distributed under the License is distributed on an "AS IS" BASIS,
@rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
@rem See the License for the specific language governing permissions and
@rem limitations under the License.
@rem
@if "%DEBUG%"=="" @echo off
@rem ##########################################################################
@rem
@rem Gradle startup script for Windows
@rem
@rem ##########################################################################
@rem Set local scope for the variables with windows NT shell
if "%OS%"=="Windows_NT" setlocal
set DIRNAME=%~dp0
if "%DIRNAME%"=="" set DIRNAME=.
@rem This is normally unused
set APP_BASE_NAME=%~n0
set APP_HOME=%DIRNAME%
@rem Resolve any "." and ".." in APP_HOME to make it shorter.
for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi
@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m"
@rem Find java.exe
if defined JAVA_HOME goto findJavaFromJavaHome
set JAVA_EXE=java.exe
%JAVA_EXE% -version >NUL 2>&1
if %ERRORLEVEL% equ 0 goto execute
echo.
echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
echo.
echo Please set the JAVA_HOME variable in your environment to match the
echo location of your Java installation.
goto fail
:findJavaFromJavaHome
set JAVA_HOME=%JAVA_HOME:"=%
set JAVA_EXE=%JAVA_HOME%/bin/java.exe
if exist "%JAVA_EXE%" goto execute
echo.
echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
echo.
echo Please set the JAVA_HOME variable in your environment to match the
echo location of your Java installation.
goto fail
:execute
@rem Setup the command line
set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
@rem Execute Gradle
"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %*
:end
@rem End local scope for the variables with windows NT shell
if %ERRORLEVEL% equ 0 goto mainEnd
:fail
rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
rem the _cmd.exe /c_ return code!
set EXIT_CODE=%ERRORLEVEL%
if %EXIT_CODE% equ 0 set EXIT_CODE=1
if not ""=="%GRADLE_EXIT_CONSOLE%" exit %EXIT_CODE%
exit /b %EXIT_CODE%
:mainEnd
if "%OS%"=="Windows_NT" endlocal
:omega

View File

@@ -0,0 +1,21 @@
plugins {
id "com.gradle.enterprise" version "3.16.2"
}
gradleEnterprise {
buildScan {
termsOfServiceUrl = "https://gradle.com/terms-of-service"
termsOfServiceAgree = "yes"
publishAlways()
uploadInBackground = false
}
}
rootProject.name = 'no-wrapper'
println "Using Gradle version: ${gradle.gradleVersion}"
def gradleVersionCheck = System.properties.gradleVersionCheck
if (gradleVersionCheck && gradle.gradleVersion != gradleVersionCheck) {
throw new RuntimeException("Got the wrong version: expected ${gradleVersionCheck} but was ${gradle.gradleVersion}")
}

View File

@@ -4,9 +4,6 @@ on:
workflow_dispatch:
push:
env:
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
many-gradle-builds:
runs-on: ubuntu-latest

View File

@@ -7,9 +7,6 @@ on:
permissions:
contents: read
env:
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
dependency-submission-save:
runs-on: ubuntu-latest

View File

@@ -8,9 +8,6 @@ on:
permissions:
contents: write
env:
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
dependency-submission-submit:
runs-on: ubuntu-latest

View File

@@ -7,9 +7,6 @@ on:
permissions:
contents: write
env:
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
test-dependency-submission:
runs-on: ubuntu-latest
@@ -22,3 +19,43 @@ jobs:
build-root-directory: .github/workflow-samples/groovy-dsl
env:
GITHUB_DEPENDENCY_GRAPH_REF: 'refs/tags/v0.0.1' # Use a different ref to avoid updating the real dependency graph for the repository
test-gradle-versions:
strategy:
matrix:
gradle: [8.0.2, 7.6.4, 7.1.1, 6.9.4, 6.0.1, 5.6.4, 5.2.1]
include:
- gradle: 5.6.4
build-root-suffix: -gradle-5
- gradle: 5.2.1
build-root-suffix: -gradle-5
runs-on: ubuntu-latest
steps:
- name: Checkout sources
uses: actions/checkout@v4
- name: Generate and submit dependencies
uses: ./dependency-submission
with:
gradle-version: ${{ matrix.gradle }}
build-root-directory: .github/workflow-samples/no-wrapper${{ matrix.build-root-suffix }}
env:
GITHUB_DEPENDENCY_GRAPH_REF: 'refs/tags/v0.0.1' # Use a different ref to avoid updating the real dependency graph for the repository
test-after-setup-gradle:
runs-on: ubuntu-latest
steps:
- name: Checkout sources
uses: actions/checkout@v4
- name: Setup Gradle
uses: ./setup-gradle
- name: Generate and submit dependencies
id: dependency-submission
uses: ./dependency-submission
continue-on-error: true
with:
build-root-directory: .github/workflow-samples/groovy-dsl
- name: Assert step failure
if: steps.dependency-submission.outcome != 'failure'
run: |
echo "Dependency submission step should fail after setup-gradle"
exit 1

View File

@@ -15,7 +15,6 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: action-inputs-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
action-inputs:

View File

@@ -15,7 +15,6 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: integ-test-cache-cleanup-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
full-build:

View File

@@ -15,7 +15,6 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: action-inputs-caching-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
seed-build:

View File

@@ -15,9 +15,34 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: dependency-graph-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
failing-build:
runs-on: ubuntu-latest
steps:
- name: Checkout sources
uses: actions/checkout@v4
- name: Download distribution if required
uses: ./.github/actions/download-dist
- name: Setup Gradle for dependency-graph generate
uses: ./setup-gradle
with:
dependency-graph: generate
dependency-graph-continue-on-failure: true
- name: Run build that will fail
id: gradle-build
continue-on-error: true
run: ./gradlew build fail
working-directory: .github/workflow-samples/groovy-dsl
- name: Check no dependency graph is generated
shell: bash
run: |
if [ ! -z "$(ls -A dependency-graph-reports)" ]; then
echo "Expected no dependency graph files to be generated"
ls -l dependency-graph-reports
exit 1
fi
unsupported-gradle-version-warning:
runs-on: ubuntu-latest
steps:

View File

@@ -18,7 +18,6 @@ permissions:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: dependency-graph-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
groovy-generate:

View File

@@ -15,7 +15,6 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: detect-java-toolchain-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
# Test that pre-installed runner JDKs are detected

View File

@@ -15,7 +15,6 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: execution-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
# Tests for executing with different Gradle versions.
@@ -46,6 +45,12 @@ jobs:
gradle-version: release-candidate
build-root-directory: .github/workflow-samples/no-wrapper
arguments: help
- name: Test with non-executable wrapper
uses: ./setup-gradle
with:
gradle-version: wrapper
build-root-directory: .github/workflow-samples/non-executable-wrapper
arguments: help
gradle-versions:
strategy:

View File

@@ -18,7 +18,6 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: provision-gradle-versions-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
inject-develocity:

View File

@@ -18,7 +18,6 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: restore-configuration-cache-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
seed-build-groovy:
@@ -43,7 +42,7 @@ jobs:
with:
cache-read-only: false # For testing, allow writing cache entries on non-default branches
cache-encryption-key: ${{ secrets.GRADLE_ENCRYPTION_KEY }}
gradle-version: 8.6-rc-1
gradle-version: 8.6
- name: Groovy build with configuration-cache enabled
working-directory: .github/workflow-samples/groovy-dsl
run: gradle test --configuration-cache
@@ -71,7 +70,7 @@ jobs:
with:
cache-read-only: true
cache-encryption-key: ${{ secrets.GRADLE_ENCRYPTION_KEY }}
gradle-version: 8.6-rc-1
gradle-version: 8.6
- name: Groovy build with configuration-cache enabled
id: execute
working-directory: .github/workflow-samples/groovy-dsl
@@ -111,7 +110,7 @@ jobs:
with:
cache-read-only: true
cache-encryption-key: ${{ secrets.GRADLE_ENCRYPTION_KEY }}
gradle-version: 8.6-rc-1
gradle-version: 8.6
- name: Check execute Gradle build with configuration cache enabled (but not restored)
working-directory: .github/workflow-samples/groovy-dsl
run: gradle test --configuration-cache
@@ -138,7 +137,7 @@ jobs:
with:
cache-read-only: false # For testing, allow writing cache entries on non-default branches
cache-encryption-key: ${{ secrets.GRADLE_ENCRYPTION_KEY }}
gradle-version: 8.6-rc-1
gradle-version: 8.6
- name: Execute 'help' with configuration-cache enabled
working-directory: .github/workflow-samples/kotlin-dsl
run: gradle help --configuration-cache
@@ -166,7 +165,7 @@ jobs:
with:
cache-read-only: false # For testing, allow writing cache entries on non-default branches
cache-encryption-key: ${{ secrets.GRADLE_ENCRYPTION_KEY }}
gradle-version: 8.6-rc-1
gradle-version: 8.6
- name: Execute 'test' with configuration-cache enabled
working-directory: .github/workflow-samples/kotlin-dsl
run: gradle test --configuration-cache
@@ -195,7 +194,7 @@ jobs:
with:
cache-read-only: true
cache-encryption-key: ${{ secrets.GRADLE_ENCRYPTION_KEY }}
gradle-version: 8.6-rc-1
gradle-version: 8.6
- name: Execute 'test' again with configuration-cache enabled
id: execute
working-directory: .github/workflow-samples/kotlin-dsl

View File

@@ -12,7 +12,6 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: restore-custom-gradle-home-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
seed-build:

View File

@@ -12,7 +12,6 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: restore-custom-gradle-home-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
seed-build:

View File

@@ -16,7 +16,6 @@ env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: restore-gradle-home-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_KEY_JOB: restore-gradle-home
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
seed-build:

View File

@@ -15,7 +15,6 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: restore-java-toolchain-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
seed-build:

View File

@@ -15,7 +15,6 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: sample-gradle-plugin-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
seed-build:

View File

@@ -15,7 +15,6 @@ on:
env:
DOWNLOAD_DIST: ${{ inputs.download-dist }}
GRADLE_BUILD_ACTION_CACHE_KEY_PREFIX: sample-kotlin-dsl-${{ inputs.cache-key-prefix }}
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
jobs:
seed-build:

View File

@@ -62,7 +62,7 @@ jobs:
uses: gradle/actions/dependency-submission@v3
with:
# Use a particular Gradle version instead of the configured wrapper.
gradle-version: 8.6-rc-2
gradle-version: 8.6
# The gradle project is not in the root of the repository.
build-root-directory: my-gradle-project
@@ -74,7 +74,130 @@ jobs:
dependency-graph: generate-and-upload
```
## Limiting the scope of the dependency graph
# Resolving a dependency vulnerability
## Finding the source of a dependency vulnerability
Once you have submitted a dependency graph, you may receive Dependabot Alerts warning about vulnerabilities in
dependencies of your project. In the case of transitive dependencies, it may not be obvious how that dependency is
used or what you can do to address the vulnerability alert.
The first step to investigating a Dependabot Alert is to determine the source of the dependency. One of the best ways to
do so is with a free Develocity Build Scan®, which makes it easy to explore the dependencies resolved in your build.
<img width="1069" alt="image" src="https://github.com/gradle/actions/assets/179734/3a637dfd-396c-4e94-8332-dcc6eb5a35ac">
In this example, we are searching for dependencies matching the name 'com.squareup.okio:okio' in the _Build Dependencies_ of
the project. You can easily see that this dependency originates from 'com.github.ben-manes:gradle-versions-plugin'.
Knowing the source of the dependency can help determine how to deal with the Dependabot Alert.
Note that you may need to look at both the _Dependencies_ and the _Build Dependencies_ of your project to find the
offending dependency.
### Publishing a Develocity Build Scan® from your dependency submission workflow
You can automatically publish a Build Scan on every run of `gradle/actions/dependency-submission`. Three input parameters are
required, one to enable publishing and two more to accept the [Develocity terms of service](https://gradle.com/terms-of-service).
```yaml
- name: Generate and submit dependency graph
uses: gradle/actions/dependency-submission@v3
with:
build-scan-publish: true
build-scan-terms-of-service-url: "https://gradle.com/terms-of-service"
build-scan-terms-of-service-agree: "yes"
```
### When you cannot publish a Build Scan®
If publishing a free Build Scan to https://scans.gradle.com isn't an option, and you don't have access to a private [Develocity
server](https://gradle.com/) for your project, you can obtain information about the each resolved dependency by running the `dependency-submission` workflow with debug logging enabled.
The simplest way to do so is to re-run the dependency-submission job with debug logging enabled:
<img width="665" alt="image" src="https://github.com/gradle/actions/assets/179734/d95b889a-09fb-4731-91f2-baebbf647e31">
When you do so, the Gradle build that generates the dependency-graph will include a log message for each dependency version included in the graph.
Given the details in one log message, you can run (locally) the built-in [dependencyInsight](https://docs.gradle.org/current/userguide/viewing_debugging_dependencies.html#dependency_insights) task
to determine exactly how the dependency was resolved.
For example, given the following message in the logs:
```
Detected dependency 'com.google.guava:guava:32.1.3-jre': project = ':my-subproject', configuration = 'compileClasspath'
```
You would run the following command locally:
```
./gradlew :my-subproject:dependencyInsight --configuration compileClasspath --dependency com.google.guava:guava:32.1.3-jre
```
#### Dealing with 'classpath' configuration
If the configuration value in the log message is "classpath" then instead of running `dependency-insight` you'll need to run the Gradle
`buildEnvironment` task.
For example, given the following message in the logs:
```
Detected dependency 'xerces:xercesImpl:2.12.2': project = ':my-subproject', configuration = 'classpath'
```
You would run the following command locally to expose the `xercesImpl` dependency:
```
./gradlew :my-subproject:buildEnvironment | grep -C 5 xercesImpl
```
## Updating the dependency version
Once you've discovered the source of the dependency, the most obvious fix is to update the dependency to a patched version that does not
suffer the vulnerability. For direct dependencies, this is often straightforward. But for transitive dependencies it can be tricky.
### Dependency source is specified directly in the build
If the dependency is used to compile your code or run your tests, it's normal for the underlying "source" of the dependency to have a
version configured directly in the build. For example, if you have a vulnerable version of `com.squareup.okio:okio` in your `compileClasspath`, then
it's likely you have a dependency like `com.squareup.moshi:moshi` configured as an `api` or `implementation` dependency.
In this case there are 2 possibilities:
1. There is a newer, compatible version of `com.squareup.moshi:moshi` available, and you can just bump the version number.
2. There isn't a newer, compatible version of `com.squareup.moshi:moshi`
In the second case, you can add a Dependency Constraint, to force the use of the newest version of `com.squareup.okio`:
```kotlin
dependencies {
implementation("com.squareup.moshi:moshi:1.12.0")
constraints {
// Force a newer version of okio in transitive resolution
implementation("com.squareup.okio:okio:3.6.0")
}
}
```
### Dependency source is a plugin classpath
If the vulnerable dependency is introduced by a Gradle plugin, again the best option is to look for a newer version of the plugin.
But if none is available, you can still use a dependency constraint to force a newer transitive version to be used.
The dependency constraint must be added to the `classpath` configuration of the buildscript that loads the plugin.
```kotlin
buildscript {
repositories {
gradlePluginPortal()
}
dependencies {
constraints {
// Force a newer version of okio in transitive resolution
classpath("com.squareup.okio:okio:3.6.0")
}
}
}
plugins {
id("com.github.ben-manes.versions") version("0.51.0")
}
```
## Limiting the dependencies that appear in the dependency graph
By default, the `dependency-submission` action attempts to detect all dependencies declared and used by your Gradle build.
At times it may helpful to limit the dependencies reported to GitHub, to avoid security alerts for dependencies that
@@ -128,19 +251,21 @@ jobs:
- name: Generate and submit dependency graph
uses: gradle/actions/dependency-submission@v3
env:
# Exclude all dependencies that originate solely in the 'buildSrc' project
DEPENDENCY_GRAPH_EXCLUDE_PROJECTS: ':buildSrc'
DEPENDENCY_GRAPH_EXCLUDE_CONFIGURATIONS: 'test(Compile|Runtime)Classpath'
# Exclude dependencies that are only resolved in test classpaths
DEPENDENCY_GRAPH_EXCLUDE_CONFIGURATIONS: '.*[Tt]est(Compile|Runtime)Classpath'
```
### Other configuration options
### Other filtering options
The [GitHub Dependency Graph Gradle Plugin](https://plugins.gradle.org/plugin/org.gradle.github-dependency-graph-gradle-plugin)
has other filtering options that may be useful.
See [the docs](https://github.com/gradle/github-dependency-graph-gradle-plugin?tab=readme-ov-file#filtering-which-gradle-configurations-contribute-to-the-dependency-graph) for details.
## Advance usage scenarios
# Advance usage scenarios
### Using a custom plugin repository
## Using a custom plugin repository
By default, the action downloads the `github-dependency-graph-gradle-plugin` from the Gradle Plugin Portal (https://plugins.gradle.org). If your GitHub Actions environment does not have access to this URL, you can specify a custom plugin repository to use.
Do so by setting the `GRADLE_PLUGIN_REPOSITORY_URL` environment variable.
@@ -158,7 +283,7 @@ jobs:
GRADLE_PLUGIN_REPOSITORY_URL: "https://gradle-plugins-proxy.mycorp.com"
```
### Integrating the `dependency-review-action`
## Integrating the `dependency-review-action`
The GitHub [dependency-review-action](https://github.com/actions/dependency-review-action) helps you
understand dependency changes (and the security impact of these changes) for a pull request,
@@ -194,7 +319,7 @@ jobs:
Note that the `dependency-submission` action submits the dependency graph at the completion of the workflow Job.
For this reason, the `dependency-review-action` must be executed in a dependent job, and not as a subsequent step in the job that generates the dependency graph.
### Usage with pull requests from public forked repositories
## Usage with pull requests from public forked repositories
This `contents: write` permission is [not available for any workflow that is triggered by a pull request submitted from a public forked repository](https://docs.github.com/en/actions/security-guides/automatic-token-authentication#permissions-for-the-github_token).
This limitation is designed to prevent a malicious pull request from effecting repository changes.
@@ -275,7 +400,7 @@ jobs:
The `retry-on-snapshot-warnings-timeout` (in seconds) needs to be long enough to allow the entire `Generate and save dependency graph` and `Download and submit dependency graph` workflows (above) to complete.
## Gradle version compatibility
# Gradle version compatibility
Dependency-graph generation is compatible with most versions of Gradle >= `5.2`, and is tested regularly against
Gradle versions `5.2.1`, `5.6.4`, `6.0.1`, `6.9.4`, `7.1.1` and `7.6.3`, as well as all patched versions of Gradle 8.x.

View File

@@ -50,9 +50,16 @@ inputs:
runs:
using: "composite"
steps:
- name: Check no setup-gradle
shell: bash
run: |
if [ -n "${GRADLE_BUILD_ACTION_SETUP_COMPLETED}" ]; then
echo "The dependency-submission action cannot be used in the same Job as the setup-gradle action. Please use a separate Job for dependency submission."
exit 1
fi
- name: Generate dependency graph
if: ${{ inputs.dependency-graph == 'generate-and-submit' || inputs.dependency-graph == 'generate-and-upload' }}
uses: gradle/actions/setup-gradle@v3.0.0
uses: gradle/actions/setup-gradle@v3.1.0
with:
dependency-graph: ${{ inputs.dependency-graph }}
dependency-graph-continue-on-failure: false
@@ -64,13 +71,14 @@ runs:
build-scan-terms-of-service-agree: ${{ inputs.build-scan-terms-of-service-agree }}
artifact-retention-days: 1
arguments: |
--no-configure-on-demand
--dependency-verification=off
-Dorg.gradle.configureondemand=false
-Dorg.gradle.dependency.verification=off
-Dorg.gradle.unsafe.isolated-projects=false
:ForceDependencyResolutionPlugin_resolveAllDependencies
${{ inputs.additional-arguments }}
- name: Download and submit dependency graph
if: ${{ inputs.dependency-graph == 'download-and-submit' }}
uses: gradle/actions/setup-gradle@v3.0.0
uses: gradle/actions/setup-gradle@v3.1.0
with:
dependency-graph: download-and-submit
dependency-graph-continue-on-failure: false

View File

@@ -139144,6 +139144,9 @@ class GradleStateCache {
fs_1.default.mkdirSync(actionCacheDir, { recursive: true });
this.copyInitScripts();
this.registerToolchains();
if (core.isDebug()) {
this.configureInfoLogLevel();
}
}
copyInitScripts() {
const initScriptsDir = path_1.default.resolve(this.gradleUserHome, 'init.d');
@@ -139182,9 +139185,22 @@ class GradleStateCache {
const absolutePath = path_1.default.resolve(__dirname, '..', '..', '..', 'sources', 'src', 'resources', ...paths);
return fs_1.default.readFileSync(absolutePath, 'utf8');
}
configureInfoLogLevel() {
const infoProperties = `org.gradle.logging.level=info\norg.gradle.logging.stacktrace=all\n`;
const propertiesFile = path_1.default.resolve(this.gradleUserHome, 'gradle.properties');
if (fs_1.default.existsSync(propertiesFile)) {
core.info(`Merged --info and --stacktrace into existing ${propertiesFile} file`);
const existingProperties = fs_1.default.readFileSync(propertiesFile, 'utf-8');
fs_1.default.writeFileSync(propertiesFile, `${infoProperties}\n${existingProperties}`);
}
else {
core.info(`Created a new ${propertiesFile} with --info and --stacktrace`);
fs_1.default.writeFileSync(propertiesFile, infoProperties);
}
}
debugReportGradleUserHomeSize(label) {
return __awaiter(this, void 0, void 0, function* () {
if (!(0, cache_utils_1.isCacheDebuggingEnabled)()) {
if (!(0, cache_utils_1.isCacheDebuggingEnabled)() && !core.isDebug()) {
return;
}
if (!fs_1.default.existsSync(this.gradleUserHome)) {
@@ -140722,6 +140738,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
};
Object.defineProperty(exports, "__esModule", ({ value: true }));
exports.gradleWrapperScript = exports.installScriptFilename = exports.wrapperScriptFilename = void 0;
const core = __importStar(__nccwpck_require__(42186));
const path = __importStar(__nccwpck_require__(71017));
const fs_1 = __importDefault(__nccwpck_require__(57147));
const IS_WINDOWS = process.platform === 'win32';
@@ -140755,7 +140772,8 @@ function verifyIsExecutableScript(toExecute) {
fs_1.default.accessSync(toExecute, fs_1.default.constants.X_OK);
}
catch (err) {
throw new Error(`Gradle script '${toExecute}' is not executable.`);
core.warning(`Gradle wrapper script '${toExecute}' is not executable. Action will set executable permission and continue.`);
fs_1.default.chmodSync(toExecute, '755');
}
}
@@ -141039,7 +141057,9 @@ function addPRComment(jobSummary) {
const pull_request_number = context.payload.pull_request.number;
core.info(`Adding Job Summary as comment to PR #${pull_request_number}.`);
const prComment = `<h3>Job Summary for Gradle</h3>
<h5>${github.context.workflow} :: <em>${github.context.job}</em></h5>
<a href="${context.serverUrl}/${context.repo.owner}/${context.repo.repo}/actions/runs/${context.runId}" target="_blank">
<h5>${context.workflow} :: <em>${context.job}</em></h5>
</a>
${jobSummary}`;
const github_token = params.getGithubToken();
@@ -141108,7 +141128,7 @@ function renderBuildScan(result) {
function renderBuildScanBadge(outcomeText, outcomeColor, targetUrl) {
const badgeUrl = `https://img.shields.io/badge/Build%20Scan%C2%AE-${outcomeText}-${outcomeColor}?logo=Gradle`;
const badgeHtml = `<img src="${badgeUrl}" alt="Build Scan ${outcomeText}" />`;
return `<a href="${targetUrl}" rel="nofollow">${badgeHtml}</a>`;
return `<a href="${targetUrl}" rel="nofollow" target="_blank">${badgeHtml}</a>`;
}
function shouldGenerateJobSummary(buildResults) {
if (!process.env[summary_1.SUMMARY_ENV_VAR]) {

File diff suppressed because one or more lines are too long

View File

@@ -136597,6 +136597,9 @@ class GradleStateCache {
fs_1.default.mkdirSync(actionCacheDir, { recursive: true });
this.copyInitScripts();
this.registerToolchains();
if (core.isDebug()) {
this.configureInfoLogLevel();
}
}
copyInitScripts() {
const initScriptsDir = path_1.default.resolve(this.gradleUserHome, 'init.d');
@@ -136635,9 +136638,22 @@ class GradleStateCache {
const absolutePath = path_1.default.resolve(__dirname, '..', '..', '..', 'sources', 'src', 'resources', ...paths);
return fs_1.default.readFileSync(absolutePath, 'utf8');
}
configureInfoLogLevel() {
const infoProperties = `org.gradle.logging.level=info\norg.gradle.logging.stacktrace=all\n`;
const propertiesFile = path_1.default.resolve(this.gradleUserHome, 'gradle.properties');
if (fs_1.default.existsSync(propertiesFile)) {
core.info(`Merged --info and --stacktrace into existing ${propertiesFile} file`);
const existingProperties = fs_1.default.readFileSync(propertiesFile, 'utf-8');
fs_1.default.writeFileSync(propertiesFile, `${infoProperties}\n${existingProperties}`);
}
else {
core.info(`Created a new ${propertiesFile} with --info and --stacktrace`);
fs_1.default.writeFileSync(propertiesFile, infoProperties);
}
}
debugReportGradleUserHomeSize(label) {
return __awaiter(this, void 0, void 0, function* () {
if (!(0, cache_utils_1.isCacheDebuggingEnabled)()) {
if (!(0, cache_utils_1.isCacheDebuggingEnabled)() && !core.isDebug()) {
return;
}
if (!fs_1.default.existsSync(this.gradleUserHome)) {
@@ -138360,7 +138376,9 @@ function addPRComment(jobSummary) {
const pull_request_number = context.payload.pull_request.number;
core.info(`Adding Job Summary as comment to PR #${pull_request_number}.`);
const prComment = `<h3>Job Summary for Gradle</h3>
<h5>${github.context.workflow} :: <em>${github.context.job}</em></h5>
<a href="${context.serverUrl}/${context.repo.owner}/${context.repo.repo}/actions/runs/${context.runId}" target="_blank">
<h5>${context.workflow} :: <em>${context.job}</em></h5>
</a>
${jobSummary}`;
const github_token = params.getGithubToken();
@@ -138429,7 +138447,7 @@ function renderBuildScan(result) {
function renderBuildScanBadge(outcomeText, outcomeColor, targetUrl) {
const badgeUrl = `https://img.shields.io/badge/Build%20Scan%C2%AE-${outcomeText}-${outcomeColor}?logo=Gradle`;
const badgeHtml = `<img src="${badgeUrl}" alt="Build Scan ${outcomeText}" />`;
return `<a href="${targetUrl}" rel="nofollow">${badgeHtml}</a>`;
return `<a href="${targetUrl}" rel="nofollow" target="_blank">${badgeHtml}</a>`;
}
function shouldGenerateJobSummary(buildResults) {
if (!process.env[summary_1.SUMMARY_ENV_VAR]) {

File diff suppressed because one or more lines are too long

View File

@@ -167,7 +167,7 @@ secrets](https://docs.gradle.org/release-nightly/userguide/configuration_cache.h
In order to benefit from configuration caching in your GitHub Actions workflow, you must:
- Execute your build with Gradle 8.6 or newer. This can be achieved directly, or via the Gradle Wrapper.
- Enable the configuration cache for your build.
- Generate a [valid Gradle encryption key](https://docs.gradle.org/8.6-rc-1/userguide/configuration_cache.html#config_cache:secrets:configuring_encryption_key) and save it as a [GitHub Actions secret](https://docs.github.com/en/actions/security-guides/using-secrets-in-github-actions).
- Generate a [valid Gradle encryption key](https://docs.gradle.org/8.6/userguide/configuration_cache.html#config_cache:secrets:configuring_encryption_key) and save it as a [GitHub Actions secret](https://docs.github.com/en/actions/security-guides/using-secrets-in-github-actions).
- Provide the secret key via the `cache-encryption-key` action parameter.
```yaml
@@ -178,7 +178,7 @@ jobs:
- uses: actions/checkout@v4
- uses: gradle/actions/setup-gradle@v3
with:
gradle-version: 8.6-rc-1
gradle-version: 8.6
cache-encryption-key: ${{ secrets.GradleEncryptionKey }}
- run: gradle build --configuration-cache
```
@@ -193,20 +193,6 @@ Specifically:
Using either of these mechanisms may interfere with the caching provided by this action. If you choose to use a different mechanism to save and restore the Gradle User Home, you should disable the caching provided by this action, as described above.
### Cache debugging and analysis
A report of all cache entries restored and saved is printed to the Job Summary when saving the cache entries.
This report can provide valuable insight into how much cache space is being used.
It is possible to enable additional debug logging for cache operations. You do via the `GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED` environment variable:
```yaml
env:
GRADLE_BUILD_ACTION_CACHE_DEBUG_ENABLED: true
```
Note that this setting will also prevent certain cache operations from running in parallel, further assisting with debugging.
## How Gradle User Home caching works
### Properties of the GitHub Actions cache
@@ -327,7 +313,6 @@ See [Using the cache read-only](#using-the-cache-read-only) for more details.
Note there are some cases where writing cache entries is typically unhelpful (these are disabled by default):
- For `pull_request` triggered runs, the cache scope is limited to the merge ref (`refs/pull/.../merge`) and can only be restored by re-runs of the same pull request.
- For `merge_group` triggered runs, the cache scope is limited to a temporary branch with a special prefix created to validate pull request changes, and won't be available on subsequent Merge Queue executions.
### Exclude content from Gradle User Home cache
@@ -366,6 +351,32 @@ Gradle Home cache cleanup is considered experimental and is disabled by default.
```yaml
gradle-home-cache-cleanup: true
```
## Debugging and Troubleshooting
In order to debug a failed job, it can be useful to run with [debug logging enabled](https://docs.github.com/en/actions/monitoring-and-troubleshooting-workflows/enabling-debug-logging).
You can enable debug logging either by adding an `ACTIONS_STEP_DEBUG` variable to your repository configuration, or by re-running a Job and checking the "Enable debug logging" box.
### Increased logging from Gradle builds
When debug logging is enabled, this action will cause all builds to run with the `--info` and `--stacktrace` options.
This is done by inserting the relevant [Gradle properties](https://docs.gradle.org/current/userguide/build_environment.html#sec:gradle_configuration_properties)
at the top of the `${GRADLE_USER_HOME}/gradle.properties` file.
If the additional Gradle logging produced is problematic, you may opt-out of this behaviour by setting these properties manually in your project `gradle.properties` file:
```properties
# default lifecycle
org.gradle.logging.level=lifecycle
org.gradle.logging.stacktrace=internal
```
### Cache debugging and analysis
A report of all cache entries restored and saved is printed to the Job Summary when saving the cache entries.
This report can provide valuable insight into how much cache space is being used.
When debug logging is enabled, more detailed logging of cache operations is included in the GitHub actions log.
This includes a breakdown of the contents of the Gradle User Home directory, which may assist in cache optimization.
## Build reporting
@@ -688,4 +699,3 @@ jobs:
- name: Run a Gradle build - a build scan will be published automatically
run: ./gradlew build
```

View File

@@ -192,6 +192,10 @@ export class GradleStateCache {
// Copy the default toolchain definitions to `~/.m2/toolchains.xml`
this.registerToolchains()
if (core.isDebug()) {
this.configureInfoLogLevel()
}
}
private copyInitScripts(): void {
@@ -241,11 +245,30 @@ export class GradleStateCache {
}
/**
* When cache debugging is enabled, this method will give a detailed report
* of the Gradle User Home contents.
* When the GitHub environment ACTIONS_RUNNER_DEBUG is true, run Gradle with --info and --stacktrace.
* see https://docs.github.com/en/actions/monitoring-and-troubleshooting-workflows/enabling-debug-logging
*
* @VisibleForTesting
*/
configureInfoLogLevel(): void {
const infoProperties = `org.gradle.logging.level=info\norg.gradle.logging.stacktrace=all\n`
const propertiesFile = path.resolve(this.gradleUserHome, 'gradle.properties')
if (fs.existsSync(propertiesFile)) {
core.info(`Merged --info and --stacktrace into existing ${propertiesFile} file`)
const existingProperties = fs.readFileSync(propertiesFile, 'utf-8')
fs.writeFileSync(propertiesFile, `${infoProperties}\n${existingProperties}`)
} else {
core.info(`Created a new ${propertiesFile} with --info and --stacktrace`)
fs.writeFileSync(propertiesFile, infoProperties)
}
}
/**
* When cache debugging is enabled (or ACTIONS_STEP_DEBUG is on),
* this method will give a detailed report of the Gradle User Home contents.
*/
private async debugReportGradleUserHomeSize(label: string): Promise<void> {
if (!isCacheDebuggingEnabled()) {
if (!isCacheDebuggingEnabled() && !core.isDebug()) {
return
}
if (!fs.existsSync(this.gradleUserHome)) {

View File

@@ -1,3 +1,4 @@
import * as core from '@actions/core'
import * as path from 'path'
import fs from 'fs'
@@ -37,6 +38,9 @@ function verifyIsExecutableScript(toExecute: string): void {
try {
fs.accessSync(toExecute, fs.constants.X_OK)
} catch (err) {
throw new Error(`Gradle script '${toExecute}' is not executable.`)
core.warning(
`Gradle wrapper script '${toExecute}' is not executable. Action will set executable permission and continue.`
)
fs.chmodSync(toExecute, '755')
}
}

View File

@@ -41,7 +41,9 @@ async function addPRComment(jobSummary: string): Promise<void> {
core.info(`Adding Job Summary as comment to PR #${pull_request_number}.`)
const prComment = `<h3>Job Summary for Gradle</h3>
<h5>${github.context.workflow} :: <em>${github.context.job}</em></h5>
<a href="${context.serverUrl}/${context.repo.owner}/${context.repo.repo}/actions/runs/${context.runId}" target="_blank">
<h5>${context.workflow} :: <em>${context.job}</em></h5>
</a>
${jobSummary}`
@@ -123,7 +125,7 @@ function renderBuildScan(result: BuildResult): string {
function renderBuildScanBadge(outcomeText: string, outcomeColor: string, targetUrl: string): string {
const badgeUrl = `https://img.shields.io/badge/Build%20Scan%C2%AE-${outcomeText}-${outcomeColor}?logo=Gradle`
const badgeHtml = `<img src="${badgeUrl}" alt="Build Scan ${outcomeText}" />`
return `<a href="${targetUrl}" rel="nofollow">${badgeHtml}</a>`
return `<a href="${targetUrl}" rel="nofollow" target="_blank">${badgeHtml}</a>`
}
function shouldGenerateJobSummary(buildResults: BuildResult[]): boolean {

View File

@@ -4,7 +4,7 @@ buildscript {
return System.getProperty(name) ?: System.getenv(envVarName)
}
def pluginRepositoryUrl = getInputParam('gradle.plugin-repository.url') ?: 'https://plugins.gradle.org/m2'
def dependencyGraphPluginVersion = getInputParam('dependency-graph-plugin.version') ?: '1.2.0'
def dependencyGraphPluginVersion = getInputParam('dependency-graph-plugin.version') ?: '1.2.2'
repositories {
maven { url pluginRepositoryUrl }

View File

@@ -0,0 +1,30 @@
import {GradleStateCache} from "../../src/cache-base"
import * as path from 'path'
import * as fs from 'fs'
describe("--info and --stacktrace", () => {
describe("will be created", () => {
it("when gradle.properties does not exists", async () => {
const emptyGradleHome = 'test/jest/resources/gradle-home/empty'
fs.rmSync(path.resolve(emptyGradleHome, "gradle.properties"), {force: true})
const stateCache = new GradleStateCache("ignored", emptyGradleHome)
stateCache.configureInfoLogLevel()
expect(fs.readFileSync(path.resolve(emptyGradleHome, "gradle.properties"), 'utf-8'))
.toBe("org.gradle.logging.level=info\norg.gradle.logging.stacktrace=all\n")
})
})
describe("will be added", () => {
it("and gradle.properties does exists", async () => {
const existingGradleHome = 'test/jest/resources/gradle-home/existing'
fs.writeFileSync(path.resolve(existingGradleHome, "gradle.properties"), "org.gradle.logging.level=debug\n")
const stateCache = new GradleStateCache("ignored", existingGradleHome)
stateCache.configureInfoLogLevel()
expect(fs.readFileSync(path.resolve(existingGradleHome, "gradle.properties"), 'utf-8'))
.toBe("org.gradle.logging.level=info\norg.gradle.logging.stacktrace=all\n\norg.gradle.logging.level=debug\n")
})
})
})

View File

@@ -0,0 +1 @@
gradle.properties

View File

@@ -0,0 +1 @@
org.gradle.logging.level=debug