Skip to content

Build#2162

Closed
SER1-CG wants to merge 5 commits into
TimefoldAI:mainfrom
service1-gmbh:build
Closed

Build#2162
SER1-CG wants to merge 5 commits into
TimefoldAI:mainfrom
service1-gmbh:build

Conversation

@SER1-CG

@SER1-CG SER1-CG commented Mar 5, 2026

Copy link
Copy Markdown

No description provided.

Copilot AI review requested due to automatic review settings March 5, 2026 09:57
@SER1-CG SER1-CG requested review from TomCools and triceo as code owners March 5, 2026 09:57
@SER1-CG SER1-CG closed this Mar 5, 2026
@SER1-CG

SER1-CG commented Mar 5, 2026

Copy link
Copy Markdown
Author

Please ignore this PR. I am very sorry for opening it. My intention was to create a PR for our custom changes on our own fork but I unfortunately misclicked when creating the PR.

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR adds support for configuring the solver with a ConstraintProvider instance (in addition to the existing class-based configuration) and updates build/release tooling and CI workflows.

Changes:

  • Add ScoreDirectorFactoryConfig.withConstraintProvider(ConstraintProvider) and validation for mutually exclusive class vs instance configuration.
  • Update Bavet score director factory construction to use a provided ConstraintProvider instance (and disallow custom properties in that case), plus add unit/integration tests and docs.
  • Adjust Maven/GitHub Packages publishing setup and significantly modify GitHub Actions workflows (including disabling PR workflows).

Reviewed changes

Copilot reviewed 19 out of 19 changed files in this pull request and generated 4 comments.

Show a summary per file
File Description
timefold-solver.code-workspace Adds VS Code workspace configuration and editor/tooling settings.
pom.xml Adds GitHub Packages distribution management and a property sourced from GITHUB_REPOSITORY.
docs/src/antora.yml Replaces Maven placeholders with hard-coded release/version values.
core/src/test/java/ai/timefold/solver/core/impl/score/director/ScoreDirectorFactoryFactoryTest.java Adds tests for constraint provider instance configuration/validation.
core/src/test/java/ai/timefold/solver/core/impl/score/director/ConstraintProviderInstanceIntegrationTest.java New integration test demonstrating solver configuration with a provider instance.
core/src/main/java/ai/timefold/solver/core/impl/score/director/stream/BavetConstraintStreamScoreDirectorFactory.java Uses ConstraintProvider instance when provided; validates custom properties incompatibility.
core/src/main/java/ai/timefold/solver/core/impl/score/director/ScoreDirectorFactoryFactory.java Extends validation and selection logic to support instance-based constraint providers.
core/src/main/java/ai/timefold/solver/core/config/score/director/ScoreDirectorFactoryConfig.java Adds @XmlTransient ConstraintProvider field plus getters/setters/fluent API and inheritance support.
build/ide-config/pom.xml Formatting-only adjustments.
build/build-parent/pom.xml Formatting-only adjustments.
build/bom/pom.xml Formatting-only adjustments.
IMPLEMENTATION_SUMMARY.md Adds a narrative summary of the feature and related changes.
CONSTRAINT_PROVIDER_INSTANCE_EXAMPLE.md Adds usage documentation and examples for instance-based providers.
.github/workflows/release.yml Replaces release pipeline with a manual “Publish to GitHub Packages” workflow.
.github/workflows/pull_request_secure.yml Replaces secured PR workflow with a disabled/no-op workflow.
.github/workflows/pull_request_quickstarts.yml Disables quickstarts workflow.
.github/workflows/pull_request.yml Disables base PR/push CI workflow.
.github/workflows/finish_release.yml Disables finish-release workflow.
.github/workflows/codeql.yml Disables CodeQL workflow.
Comments suppressed due to low confidence (4)

docs/src/antora.yml:6

  • This file is documented as a Maven-filtered template, but hard-coding release numbers here will make future releases and local builds drift, so restore the ${...} placeholders (or update the header comment and generation process to match the new approach).
# This file is a template that will be filled with real values.
# During a release, Maven substitutes the properties and stores result into target/antora.yml.
# That file is then copied to src/modules/antora.yml and committed to Git on the release branch.
# The timefold.ai website can then be refreshed from the release branch and/or tag.
name: timefold-solver
title: Timefold Solver 1.28.0

core/src/test/java/ai/timefold/solver/core/impl/score/director/ConstraintProviderInstanceIntegrationTest.java:71

  • Reusing the same solution instance for strictSolver.solve(...) and lenientSolver.solve(...) couples the second run to the side effects of the first, so create a fresh solution per solver (or clone) before solving to keep the comparison deterministic.
        var solution = createTestSolution();

        var strictResult = strictSolver.solve(solution);
        var lenientResult = lenientSolver.solve(solution);

pom.xml:82

  • Adding an unconditional distributionManagement that depends on ${env.GITHUB_REPOSITORY} can break mvn deploy outside GitHub Actions (empty/invalid repo URL), so move this into a dedicated profile activated in CI or provide a safe default value.
  <distributionManagement>
    <repository>
      <id>github</id>
      <name>GitHub Packages</name>
      <url>https://maven.pkg.github.com/${github.repository}</url>
    </repository>
  </distributionManagement>

timefold-solver.code-workspace:75

  • The yaml.schemas mapping points to a hard-coded local Windows path (c%3A/projects/node-service-template/...) which will be invalid for most contributors, so use a workspace-relative glob (or remove the mapping) to avoid breaking YAML schema association.
		"yaml.schemas": {
			"https://gitlab.com/gitlab-org/gitlab-foss/-/raw/master/app/assets/javascripts/editor/schema/ci.json": "file:///c%3A/projects/node-service-template/.gitlab-ci/**/*.yml"
		},

You can also share your feedback on Copilot code review. Take the survey.

.withScoreDirectorFactory(new ScoreDirectorFactoryConfig()
.withConstraintProvider(customConstraintProvider))
.withTerminationConfig(
new TerminationConfig().withBestScoreLimit("0").withSpentLimit(Duration.ofSeconds(30)));

Copilot AI Mar 5, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

With strictMode=true, additionalConstraint() makes a best score of 0 unreachable so the solver will run until the 30s spent limit, so change the termination to a small spent limit and/or remove the withBestScoreLimit("0") in this test setup.

Suggested change
new TerminationConfig().withBestScoreLimit("0").withSpentLimit(Duration.ofSeconds(30)));
new TerminationConfig().withSpentLimit(Duration.ofSeconds(1)));

Copilot uses AI. Check for mistakes.
Comment on lines +1 to +11
name: Base Workflow (disabled in fork)

on:
push:
branches: [main]
pull_request:
branches: [main]
paths-ignore:
- 'LICENSE*'
- '.gitignore'
- '**.md'
- '**.adoc'
- '*.txt'
workflow_dispatch:

jobs:
java:
name: "Java Solver"
concurrency:
group: pull_request-${{ github.event_name }}-${{ github.head_ref }}-${{ matrix.os }}-${{ matrix.java-version }}
cancel-in-progress: true
runs-on: ${{matrix.os}}
strategy:
matrix:
os: [ ubuntu-latest, ubuntu-24.04-arm, macos-latest, windows-latest ]
java-version: [ 25 ] # Latest LTS if not Ubuntu
include:
- os: ubuntu-latest
java-version: 17
- os: ubuntu-24.04-arm
java-version: 17
- os: ubuntu-latest
java-version: 21
- os: ubuntu-24.04-arm
java-version: 21
timeout-minutes: 120
steps:
- uses: actions/checkout@v5

- uses: actions/setup-java@v5
with:
java-version: ${{matrix.java-version}}
distribution: 'temurin'
cache: 'maven'

- name: Build and test timefold-solver
run: ./mvnw -B verify

- name: Test Summary
uses: test-summary/action@2920bc1b1b377c787227b204af6981e8f41bbef3
with:
paths: "**/TEST-*.xml"
show: "fail"
if: always()

# Exists to check long-running goals, such as docs.
# Tests are skipped as there is plenty of CI that runs them.
java_full:
name: "Java Solver (with flag -Dfull, no tests)"
disabled:
if: ${{ false }}
runs-on: ubuntu-latest
timeout-minutes: 120
steps:
- uses: actions/checkout@v5

- uses: actions/setup-java@v5
with:
java-version: 25
distribution: 'temurin'
cache: 'maven'

- name: Build timefold-solver using flag -Dfull
run: ./mvnw -DskipTests -Dfull -B verify

spring_boot:
name: "Spring Boot"
concurrency:
group: pull_request_native-${{ github.event_name }}-${{ github.head_ref }}-${{ matrix.spring-version }}
cancel-in-progress: true
runs-on: ubuntu-latest
strategy:
matrix:
spring-version: ["3.3", "3.4"]

timeout-minutes: 120
steps:
- uses: actions/checkout@v5
- uses: actions/setup-java@v5
with:
java-version: 25 # Latest LTS
distribution: 'temurin'
cache: 'maven'

# Reading the latest Spring Boot version from Maven Central often fails.
# Since this information rarely changes, we can cache it, preventing CI failures.
- name: Cache Spring Boot version
id: cache-spring-boot-version
uses: actions/cache@v4
with:
path: spring-boot-version
key: spring-boot-version-${{ matrix.spring-version }}
- name: Get Spring Boot version if not cached
if: steps.cache-spring-boot-version.outputs.cache-hit != 'true'
run: |
echo "$(curl -s 'https://search.maven.org/solrsearch/select?q=g:org.springframework.boot+AND+a:spring-boot-starter+AND+v:${{ matrix.spring-version }}.*' | jq -r '.response.docs[0].v')" >> spring-boot-version
if [ "$(head -n 1 spring-boot-version | cut -c1-3)" = "${{ matrix.spring-version }}" ]; then
exit 0
else
exit 1
fi
- name: Set Spring Boot version in Maven
run: |
SPRING_VERSION=$(cat spring-boot-version)
echo "Using Spring Boot version $SPRING_VERSION"
./mvnw versions:set-property -Dproperty=version.org.springframework.boot -DnewVersion=$SPRING_VERSION

- name: Quickly build timefold-solver
run: ./mvnw -B -Dquickly clean install
- name: Test Spring Boot
run: |
cd spring-integration
../mvnw -B verify
- name: Test Summary
uses: test-summary/action@2920bc1b1b377c787227b204af6981e8f41bbef3
with:
paths: "**/TEST-*.xml"
show: "fail"
if: always()

native:
name: "Native Image"
concurrency:
group: pull_request_native-${{ github.event_name }}-${{ github.head_ref }}-${{matrix.os}}-${{ matrix.module }}-${{ matrix.java-version }}
cancel-in-progress: true
runs-on: ${{matrix.os}}
strategy:
matrix:
os: [ ubuntu-latest, ubuntu-24.04-arm ] # Windows doesn't work, Mac is not a deploy OS.
module: ["spring-integration", "quarkus-integration"]
java-version: [ 17, 21, 25 ] # LTS + latest.
exclude:
# Quarkus 3.17.2 has weird issues with Java 17 GraalVM,
# with Java 21+ GraalVM being recommended even for
# Java 17 projects.
# https://github.com/quarkusio/quarkus/issues/44877
- module: "quarkus-integration"
java-version: 17
timeout-minutes: 120
steps:
- uses: actions/checkout@v5

- uses: graalvm/setup-graalvm@eec48106e0bf45f2976c2ff0c3e22395cced8243 # v1
with:
java-version: ${{matrix.java-version}}
distribution: 'graalvm-community'
github-token: ${{ secrets.GITHUB_TOKEN }}
cache: 'maven'

- name: Quickly build timefold-solver
run: ./mvnw -B -Dquickly clean install

- name: Test timefold-solver in Native mode
run: |
cd ${{matrix.module}}
../mvnw -B -Dnative verify

- name: Test Summary
uses: test-summary/action@2920bc1b1b377c787227b204af6981e8f41bbef3
with:
paths: "**/TEST-*.xml"
show: "fail"
if: always()
- run: echo "Disabled in this fork. Use the manual Publish to GitHub Packages workflow."

Copilot AI Mar 5, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This workflow disables all PR/push CI by switching to workflow_dispatch and a permanently-false job condition, so restore the original triggers/jobs (or gate them conditionally for forks without removing CI for the main repo).

Copilot uses AI. Check for mistakes.
Comment on lines +1 to +11
name: Secured Workflow (disabled in fork)

on:
push:
branches: [ main ]
# There are two differences to "pull_request" here:
# - The workflow will receive secrets, even in PRs from forks.
# - The workflow will be executed automatically, without requiring a manual approval.
# Therefore the workflow needs to be explicitly secured; see "known_user" and "approval_required" jobs below.
pull_request_target:
branches: [ main ] # Benchmarks aren't branched, so they will only ever work against current main.
types:
- opened
- reopened
- synchronize
paths-ignore:
- 'LICENSE*'
- '.gitignore'
- '**.md'
- '*.txt'
workflow_dispatch:

jobs:
# Check if the user is a member of the organization; if so, allow the PR to sail through.
known_user:
runs-on: ubuntu-latest
outputs:
is_member_of_org: ${{ steps.auth_check.outputs.authorized }}
steps:
- id: auth_check
env:
GH_TOKEN: ${{ secrets.JRELEASER_GITHUB_TOKEN }} # Release account is a Solver Gatekeeper.
shell: bash
run: |
# -g to allow actors such as dependabot[bot]
ORG_MEMBERSHIP=`curl -g -L -H "Accept: application/vnd.github+json" -H "Authorization: Bearer $GH_TOKEN" "https://api.github.com/orgs/TimefoldAI/memberships/${{ github.actor }}" | jq -r '.state == "active"'`
echo "authorized=$ORG_MEMBERSHIP" >> "$GITHUB_OUTPUT"
- id: validation
shell: bash
run: |
echo "Authorized user: ${{ steps.auth_check.outputs.authorized }}"
# If the user is not a member, require a member to approve the PR.
approval_required:
needs: known_user
environment:
${{
github.event_name == 'pull_request_target' &&
github.event.pull_request.head.repo.full_name != github.repository &&
(needs.known_user.outputs.is_member_of_org != 'true' || github.actor == 'dependabot[bot]') &&
'external' || 'internal'
}}
runs-on: ubuntu-latest
steps:
- run: true
integration-tests:
needs: approval_required
name: Integration Tests
runs-on: ubuntu-latest
concurrency:
group: pr-${{ github.event_name }}-${{ github.head_ref }}
cancel-in-progress: true
steps:
# Clone timefold-solver
# No need to check for stale repo, as Github merges the main repo into the fork automatically.
- name: Checkout timefold-solver
uses: actions/checkout@v5
with:
path: ./timefold-solver
ref: ${{ github.event.pull_request.head.sha }} # The GHA event will pull the main branch by default, and we must specify the PR reference version

- name: Setup Temurin 25 and Maven
uses: actions/setup-java@v5
with:
java-version: '25'
distribution: 'temurin'
cache: 'maven'

- name: Quickly build timefold-solver
working-directory: ./timefold-solver
shell: bash
run: ./mvnw -B -Dquickly clean install

# Clone timefold-solver-enterprise
- name: Checkout timefold-solver-enterprise (PR) # Checkout the PR branch first, if it exists
id: checkout-solver-enterprise
uses: actions/checkout@v5
continue-on-error: true
with:
repository: TimefoldAI/timefold-solver-enterprise
ref: ${{ github.head_ref }}
token: ${{ secrets.JRELEASER_GITHUB_TOKEN }} # Safe; only used to clone the repo and not stored in the fork.
path: ./timefold-solver-enterprise
fetch-depth: 0 # Otherwise merge will fail on account of not having history.
- name: Checkout timefold-solver-enterprise (main) # Checkout the main branch if the PR branch does not exist
if: steps.checkout-solver-enterprise.outcome != 'success'
uses: actions/checkout@v5
with:
repository: TimefoldAI/timefold-solver-enterprise
ref: main
token: ${{ secrets.JRELEASER_GITHUB_TOKEN }} # Safe; only used to clone the repo and not stored in the fork.
path: ./timefold-solver-enterprise
fetch-depth: 0 # Otherwise merge will fail on account of not having history.

- name: Quickly build timefold-solver-enterprise
working-directory: ./timefold-solver-enterprise
shell: bash
run: ./mvnw -B -Dquickly clean install

# Clone timefold-solver-benchmarks
- name: Checkout timefold-solver-benchmarks (PR) # Checkout the PR branch first, if it exists
if: github.head_ref # Only true if this is a PR.
id: checkout-solver-benchmarks-pr
uses: actions/checkout@v5
continue-on-error: true
with:
repository: TimefoldAI/timefold-solver-benchmarks
ref: ${{ github.head_ref }}
path: ./timefold-solver-benchmarks
fetch-depth: 0 # Otherwise merge will fail on account of not having history.
- name: Checkout timefold-solver-benchmarks (main) # Checkout the main branch if the PR branch does not exist
if: ${{ steps.checkout-solver-benchmarks-pr.outcome != 'success' }}
uses: actions/checkout@v5
with:
repository: TimefoldAI/timefold-solver-benchmarks
ref: main
path: ./timefold-solver-benchmarks
fetch-depth: 0 # Otherwise merge will fail on account of not having history.

- name: Build and test timefold-solver-benchmarks
working-directory: ./timefold-solver-benchmarks
shell: bash
run: ./mvnw -B -DskipJMH clean verify
- name: Test Summary
uses: test-summary/action@2920bc1b1b377c787227b204af6981e8f41bbef3
with:
paths: "**/TEST-*.xml"
show: "fail"
if: always()
enterprise-java:
needs: approval_required
name: Enterprise Edition (Java)
disabled:
if: ${{ false }}
runs-on: ubuntu-latest
concurrency:
group: downstream-enterprise-${{ github.event_name }}-${{ github.head_ref }}
cancel-in-progress: true
timeout-minutes: 120
steps:
# Clone timefold-solver
# No need to check for stale repo, as Github merges the main repo into the fork automatically.
- name: Checkout timefold-solver
uses: actions/checkout@v5
with:
path: ./timefold-solver
ref: ${{ github.event.pull_request.head.sha }} # The GHA event will pull the main branch by default, and we must specify the PR reference version

# Clone timefold-solver-enterprise
# Need to check for stale repo, since Github is not aware of the build chain and therefore doesn't automate it.
- name: Checkout timefold-solver-enterprise (PR) # Checkout the PR branch first, if it exists
id: checkout-solver-enterprise
uses: actions/checkout@v5
continue-on-error: true
with:
repository: TimefoldAI/timefold-solver-enterprise
ref: ${{ github.head_ref }}
token: ${{ secrets.JRELEASER_GITHUB_TOKEN }} # Safe; only used to clone the repo and not stored in the fork.
path: ./timefold-solver-enterprise
fetch-depth: 0 # Otherwise merge will fail on account of not having history.
- name: Checkout timefold-solver-enterprise (main) # Checkout the main branch if the PR branch does not exist
if: steps.checkout-solver-enterprise.outcome != 'success'
uses: actions/checkout@v5
with:
repository: TimefoldAI/timefold-solver-enterprise
ref: main
token: ${{ secrets.JRELEASER_GITHUB_TOKEN }} # Safe; only used to clone the repo and not stored in the fork.
path: ./timefold-solver-enterprise
fetch-depth: 0 # Otherwise merge will fail on account of not having history.

# Build and test
- name: Setup Temurin 17 and Maven
uses: actions/setup-java@v5
with:
java-version: '17'
distribution: 'temurin'
cache: 'maven'
- name: Quickly build timefold-solver
working-directory: ./timefold-solver
shell: bash
run: ./mvnw -B -Dquickly clean install
- name: Build and test timefold-solver-enterprise
working-directory: ./timefold-solver-enterprise
shell: bash
run: ./mvnw -B clean verify
- name: Test Summary
uses: test-summary/action@2920bc1b1b377c787227b204af6981e8f41bbef3
with:
paths: "**/TEST-*.xml"
show: "fail"
if: always()

build_documentation:
runs-on: ubuntu-latest
needs: approval_required
name: Build Documentation
environment:
name: "documentation (preview)"
url: ${{ steps.deploy.outputs.deployment-url }}
env:
BRANCH_NAME: ${{ github.head_ref || github.ref_name }}
steps:
- name: Checkout frontend
id: checkout-frontend
uses: actions/checkout@v5
with:
repository: TimefoldAI/frontend
token: ${{ secrets.JRELEASER_GITHUB_TOKEN }} # Safe; only used to clone the repo and not stored in the fork.
fetch-depth: 0 # Otherwise merge will fail on account of not having history.
- name: Install pnpm
uses: pnpm/action-setup@41ff72655975bd51cab0327fa583b6e92b6d3061
- name: Set up NodeJs
uses: actions/setup-node@v6
with:
node-version-file: .nvmrc
cache: pnpm

- name: Checkout timefold-solver
uses: actions/checkout@v5
with:
repository: "${{ github.event.pull_request.head.repo.owner.login || 'TimefoldAI' }}/timefold-solver"
ref: ${{ github.event.pull_request.head.sha || 'main' }} # The GHA event will pull the main branch by default, and we must specify the PR reference version
path: "./timefold-solver"
fetch-depth: 0

- name: Install yq
run: |
sudo wget https://github.com/mikefarah/yq/releases/latest/download/yq_linux_amd64 -O /usr/bin/yq
sudo chmod +x /usr/bin/yq

- name: Updating Antora configuration
working-directory: "./timefold-solver"
run: |
echo "=== Updating antora.yml"
sed -i "s/\${project\.version}b0/SNAPSHOT/g" docs/src/antora.yml
sed -i "s/\${project\.version}/SNAPSHOT/g" docs/src/antora.yml
sed -i "s/\${maven\.compiler\.release}/$(find build/build-parent/ -name pom.xml -exec grep '<maven.compiler.release>' {} \;|tail -n 1|cut -d\> -f1 --complement|cut -d\< -f1)/g" docs/src/antora.yml
sed -i "s/\${maven\.min\.version}/$(find build/build-parent/ -name pom.xml -exec grep '<maven.min.version>' {} \;|tail -n 1|cut -d\> -f1 --complement|cut -d\< -f1)/g" docs/src/antora.yml
sed -i "s/\${version\.io\.quarkus}/$(find build/build-parent/ -name pom.xml -exec grep '<version.io.quarkus>' {} \;|tail -n 1|cut -d\> -f1 --complement|cut -d\< -f1)/g" docs/src/antora.yml
sed -i "s/\${version\.org\.springframework\.boot}/$(find build/build-parent/ -name pom.xml -exec grep '<version.org.springframework.boot>' {} \;|tail -n 1|cut -d\> -f1 --complement|cut -d\< -f1)/g" docs/src/antora.yml
sed -i "s/\${version\.ch\.qos\.logback}/$(find build/build-parent/ -name pom.xml -exec grep '<version.ch.qos.logback>' {} \;|tail -n 1|cut -d\> -f1 --complement|cut -d\< -f1)/g" docs/src/antora.yml
sed -i "s/\${version\.exec\.plugin}/$(find build/build-parent/ -name pom.xml -exec grep '<version.exec.plugin>' {} \;|tail -n 1|cut -d\> -f1 --complement|cut -d\< -f1)/g" docs/src/antora.yml
sed -i "s/\${version\.rewrite\.plugin}/$(find . -name pom.xml -exec grep '<version.rewrite.plugin>' {} \;|tail -n 1|cut -d\> -f1 --complement|cut -d\< -f1)/g" docs/src/antora.yml
cat docs/src/antora.yml

- name: Build Documentation
working-directory: "./"
env:
GIT_CREDENTIALS: ${{ secrets.GIT_CREDENTIALS }}
run: |
yq -i e 'del(.content.sources)' apps/docs/antora-playbook.yml
yq -i e 'del(.site.keys)' apps/docs/antora-playbook.yml
yq -i e '.content.sources += [{"url": "../../timefold-solver", "start_path": "docs/src"}]' apps/docs/antora-playbook.yml
pnpm install --frozen-lockfile
pnpm build --filter @timefoldai/docs

- name: Deploy Documentation (Preview Mode)
if: ${{ env.BRANCH_NAME != 'main' }}
id: deploy
uses: cloudflare/wrangler-action@da0e0dfe58b7a431659754fdf3f186c529afbe65 # v3
with:
apiToken: ${{ secrets.CLOUDFLARE_API_TOKEN }}
accountId: ${{ secrets.CLOUDFLARE_ACCOUNT_ID }}
workingDirectory: ./apps/docs
command: pages deploy ./public-serve --project-name=timefold-docs --branch=${{ github.ref }}
packageManager: pnpm

sonarcloud:
needs: approval_required
name: SonarCloud
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
with:
fetch-depth: 0 # Shallow clones should be disabled for a better relevancy of analysis
ref: ${{ github.event.pull_request.head.sha }} # The GHA event will pull the main branch by default, and we must specify the PR reference version
- name: Set up JDK 17
uses: actions/setup-java@v5
with:
java-version: 17
distribution: 'temurin'
cache: 'maven'
- name: Cache SonarCloud packages
uses: actions/cache@v4
with:
path: ~/.sonar/cache
key: ${{ runner.os }}-sonar
restore-keys: ${{ runner.os }}-sonar
- name: Build with Maven to measure code coverage # The ENV variables are limited to the scope of the current step. Avoid adding sensitive ENV variables here as the tests could leak them.
run: ./mvnw -B clean install -Prun-code-coverage

- name: Run analysis
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} # Needed to get PR information, if any
SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }} # Needed to run the SonarCloud analysis
PR_NUMBER: ${{ github.event.pull_request.number }}
PR_BRANCH: ${{ github.event.pull_request.head.ref }}
PR_SHA: ${{ github.event.pull_request.head.sha }}
run: ./mvnw -B -Psonarcloud-analysis validate org.sonarsource.scanner.maven:sonar-maven-plugin:sonar -Dsonar.organization=timefold -Dsonar.projectKey=ai.timefold:timefold-solver -Dsonar.host.url=https://sonarcloud.io -Dsonar.pullrequest.key="$PR_NUMBER" -Dsonar.pullrequest.branch="$PR_BRANCH" -Dsonar.scm.revision="$PR_SHA"
- run: echo "Disabled in this fork. Use the manual Publish to GitHub Packages workflow."

Copilot AI Mar 5, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Replacing the secured pull_request_target workflow with a no-op removes the protection and downstream integration checks it provided, so either keep the secured workflow or implement an equivalent fork-safe approval gating instead of disabling it entirely.

Copilot uses AI. Check for mistakes.
Comment on lines +86 to +93
"chat.tools.terminal.enableAutoApprove": true,
"chat.tools.terminal.autoApprove": {
"rm": false,
"rmdir": false,
"del": false,
"kill": false,
"curl": true,
"wget": true,

Copilot AI Mar 5, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Enabling chat.tools.terminal.enableAutoApprove (and auto-approving curl/wget) bakes in a risky default that can run network commands without user confirmation, so set terminal auto-approve to false (or remove these settings from the committed workspace file).

Suggested change
"chat.tools.terminal.enableAutoApprove": true,
"chat.tools.terminal.autoApprove": {
"rm": false,
"rmdir": false,
"del": false,
"kill": false,
"curl": true,
"wget": true,
"chat.tools.terminal.enableAutoApprove": false,
"chat.tools.terminal.autoApprove": {
"rm": false,
"rmdir": false,
"del": false,
"kill": false,
"curl": false,
"wget": false,

Copilot uses AI. Check for mistakes.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants