diff --git a/.github/workflows/check-deprecated-exercises.yml b/.github/workflows/check-deprecated-exercises.yml index 562d96ca0..47267841d 100644 --- a/.github/workflows/check-deprecated-exercises.yml +++ b/.github/workflows/check-deprecated-exercises.yml @@ -14,7 +14,7 @@ jobs: name: Check for deprecated exercises runs-on: ubuntu-24.04 steps: - - uses: actions/checkout@9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0 + - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 with: fetch-depth: 0 - name: Test deprecated exercises using test-deprecated-exercises diff --git a/.github/workflows/create-configlet-sync-issues.yml b/.github/workflows/create-configlet-sync-issues.yml index 9ffcae10d..07a0ed615 100644 --- a/.github/workflows/create-configlet-sync-issues.yml +++ b/.github/workflows/create-configlet-sync-issues.yml @@ -19,7 +19,7 @@ jobs: steps: - name: Checkout repository - uses: actions/checkout@v7 + uses: actions/checkout@v7.0.1 - name: Fetch configlet run: ./bin/fetch-configlet diff --git a/.github/workflows/java.yml b/.github/workflows/java.yml index 2e57aa5b5..2fc8509d9 100644 --- a/.github/workflows/java.yml +++ b/.github/workflows/java.yml @@ -16,9 +16,9 @@ jobs: if: github.event_name == 'push' || github.event_name == 'workflow_dispatch' runs-on: ubuntu-24.04 steps: - - uses: actions/checkout@9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0 + - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 - name: Set up JDK 25 - uses: actions/setup-java@1bcf9fb12cf4aa7d266a90ae39939e61372fe520 + uses: actions/setup-java@03ad4de0992f5dab5e18fcb136590ce7c4a0ac95 with: java-version: 25 distribution: "temurin" @@ -31,11 +31,11 @@ jobs: if: github.event_name == 'pull_request' runs-on: ubuntu-24.04 steps: - - uses: actions/checkout@9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0 + - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 with: fetch-depth: 0 - name: Set up JDK 25 - uses: actions/setup-java@1bcf9fb12cf4aa7d266a90ae39939e61372fe520 + uses: actions/setup-java@03ad4de0992f5dab5e18fcb136590ce7c4a0ac95 with: java-version: 25 distribution: "temurin" @@ -47,9 +47,9 @@ jobs: if: github.event_name == 'push' || github.event_name == 'workflow_dispatch' runs-on: ubuntu-24.04 steps: - - uses: actions/checkout@9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0 + - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 - name: Set up JDK 25 - uses: actions/setup-java@1bcf9fb12cf4aa7d266a90ae39939e61372fe520 + uses: actions/setup-java@03ad4de0992f5dab5e18fcb136590ce7c4a0ac95 with: java-version: 25 distribution: "temurin" @@ -62,11 +62,11 @@ jobs: if: github.event_name == 'pull_request' runs-on: ubuntu-24.04 steps: - - uses: actions/checkout@9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0 + - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 with: fetch-depth: 0 - name: Set up JDK 25 - uses: actions/setup-java@1bcf9fb12cf4aa7d266a90ae39939e61372fe520 + uses: actions/setup-java@03ad4de0992f5dab5e18fcb136590ce7c4a0ac95 with: java-version: 25 distribution: "temurin" @@ -78,7 +78,7 @@ jobs: if: github.event_name == 'push' || github.event_name == 'workflow_dispatch' runs-on: ubuntu-24.04 steps: - - uses: actions/checkout@9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0 + - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 - name: Test all exercises using java-test-runner run: bin/test-with-test-runner - name: Print summary @@ -105,7 +105,7 @@ jobs: if: github.event_name == 'pull_request' runs-on: ubuntu-24.04 steps: - - uses: actions/checkout@9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0 + - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 with: fetch-depth: 0 - name: Test changed exercises using java-test-runner diff --git a/.github/workflows/markdown.yml b/.github/workflows/markdown.yml index 8367dc457..5a9f03fc3 100644 --- a/.github/workflows/markdown.yml +++ b/.github/workflows/markdown.yml @@ -17,6 +17,6 @@ jobs: name: Lint Markdown files runs-on: ubuntu-24.04 steps: - - uses: actions/checkout@9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0 + - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 - name: Lint markdown - uses: DavidAnson/markdownlint-cli2-action@ded1f9488f68a970bc66ea5619e13e9b52e601cd + uses: DavidAnson/markdownlint-cli2-action@6bf21b07787794f89a243495939cd651942aeabe diff --git a/concepts/maps/about.md b/concepts/maps/about.md index 86a820cf1..9590aefc0 100644 --- a/concepts/maps/about.md +++ b/concepts/maps/about.md @@ -145,7 +145,11 @@ Another common way to create maps is to use [Map.of][map-of-javadoc] or [Map.ofE Map temperatures = Map.of("Mon", 30, "Tue", 28, "Wed", 32); // or using Map.ofEntries -Map temperatures2 = Map.ofEntries(Map.entry("Mon", 30, "Tue", 28, "Wed", 32)); +Map temperatures2 = Map.ofEntries( + Map.entry("Mon", 30), + Map.entry("Tue", 28), + Map.entry("Wed", 32) +); ``` Unlike `HashMap`, they populate the map upfront and become read-only once created. diff --git a/exercises/practice/bob/.meta/tests.toml b/exercises/practice/bob/.meta/tests.toml index 5299e2895..8995c9235 100644 --- a/exercises/practice/bob/.meta/tests.toml +++ b/exercises/practice/bob/.meta/tests.toml @@ -18,6 +18,9 @@ description = "shouting" [d6c98afd-df35-4806-b55e-2c457c3ab748] description = "shouting gibberish" +[3c954328-86fb-4c71-8961-e18d6a5e2517] +description = "shouting a statement containing a question mark" + [8a2e771d-d6f1-4e3f-b6c6-b41495556e37] description = "asking a question" diff --git a/exercises/practice/bob/src/test/java/BobTest.java b/exercises/practice/bob/src/test/java/BobTest.java index 756fb93f8..3806670ab 100644 --- a/exercises/practice/bob/src/test/java/BobTest.java +++ b/exercises/practice/bob/src/test/java/BobTest.java @@ -37,6 +37,14 @@ public void shoutingGibberish() { .isEqualTo("Whoa, chill out!"); } + @Disabled("Remove to run test") + @Test + @DisplayName("shouting a statement containing a question mark") + public void shoutingAStatementContainingQuestionMark() { + assertThat(bob.hey("DO LIONS EAT PEOPLE? AHHHHH.")) + .isEqualTo("Whoa, chill out!"); + } + @Disabled("Remove to run test") @Test @DisplayName("asking a question") diff --git a/exercises/practice/nucleotide-count/.meta/config.json b/exercises/practice/nucleotide-count/.meta/config.json index f58c53240..b98277ed6 100644 --- a/exercises/practice/nucleotide-count/.meta/config.json +++ b/exercises/practice/nucleotide-count/.meta/config.json @@ -44,6 +44,6 @@ ] }, "blurb": "Given a DNA string, compute how many times each nucleotide occurs in the string.", - "source": "The Calculating DNA Nucleotides_problem at Rosalind", + "source": "The Counting DNA Nucleotides problem at Rosalind", "source_url": "https://rosalind.info/problems/dna/" } diff --git a/exercises/practice/perfect-numbers/.meta/config.json b/exercises/practice/perfect-numbers/.meta/config.json index 073f6f424..e65d254da 100644 --- a/exercises/practice/perfect-numbers/.meta/config.json +++ b/exercises/practice/perfect-numbers/.meta/config.json @@ -38,5 +38,5 @@ }, "blurb": "Determine if a number is perfect, abundant, or deficient based on Nicomachus' (60 - 120 CE) classification scheme for positive integers.", "source": "Taken from Chapter 2 of Functional Thinking by Neal Ford.", - "source_url": "https://www.oreilly.com/library/view/functional-thinking/9781449365509/" + "source_url": "https://nealford.com/books/functionalthinking.html" } diff --git a/exercises/practice/state-of-tic-tac-toe/.meta/src/reference/java/StateOfTicTacToe.java b/exercises/practice/state-of-tic-tac-toe/.meta/src/reference/java/StateOfTicTacToe.java index 1fcee86d2..d3ed3ab82 100644 --- a/exercises/practice/state-of-tic-tac-toe/.meta/src/reference/java/StateOfTicTacToe.java +++ b/exercises/practice/state-of-tic-tac-toe/.meta/src/reference/java/StateOfTicTacToe.java @@ -51,6 +51,18 @@ public GameState determineState(String[] board) { } } + if (xWin > 0 && xCount != oCount + 1) { + throw new IllegalArgumentException( + "Impossible board: game should have ended after the game was won" + ); + } + + if (oWin > 0 && xCount != oCount) { + throw new IllegalArgumentException( + "Impossible board: game should have ended after the game was won" + ); + } + if (xWin > 0 || oWin > 0) { return GameState.WIN; } @@ -82,7 +94,6 @@ private List getDiagonals(String[] board) { String[] diags = new String[2]; for (int i = 0; i < 3; i++) { - if (diags[0] == null) { diags[0] = String.valueOf(board[i].charAt(i)); } else { diff --git a/exercises/practice/state-of-tic-tac-toe/.meta/tests.toml b/exercises/practice/state-of-tic-tac-toe/.meta/tests.toml index 8fc25e211..5f574b2a1 100644 --- a/exercises/practice/state-of-tic-tac-toe/.meta/tests.toml +++ b/exercises/practice/state-of-tic-tac-toe/.meta/tests.toml @@ -99,3 +99,9 @@ reimplements = "b1dc8b13-46c4-47db-a96d-aa90eedc4e8d" [4801cda2-f5b7-4c36-8317-3cdd167ac22c] description = "Invalid boards -> Invalid board: players kept playing after a win" + +[5a84757a-fc86-4328-aec9-a5759e6ed35d] +description = "Invalid boards -> Invalid board: O kept playing after X wins" + +[cf25543d-583a-4656-b9ab-f82dc00a4a02] +description = "Invalid boards -> Invalid board: X kept playing after O wins" diff --git a/exercises/practice/state-of-tic-tac-toe/src/test/java/StateOfTicTacToeTest.java b/exercises/practice/state-of-tic-tac-toe/src/test/java/StateOfTicTacToeTest.java index d264db005..5ae93502b 100644 --- a/exercises/practice/state-of-tic-tac-toe/src/test/java/StateOfTicTacToeTest.java +++ b/exercises/practice/state-of-tic-tac-toe/src/test/java/StateOfTicTacToeTest.java @@ -95,7 +95,7 @@ public void testFinishedGameWhereXWonViaMiddleRowVictory() { @Disabled("Remove to run test") @Test - @DisplayName("Finished game where X won via middle row victory") + @DisplayName("Finished game where X won via bottom row victory") public void testFinishedGameWhereXWonViaBottomRowVictory() { assertThat( @@ -207,7 +207,7 @@ public void testDraw() { @Test @DisplayName("Another draw") public void testAnotherDraw() { - + assertThat( stateOfTicTacToe.determineState(new String[]{"XXO", "OXX", "XOO"}) ).isEqualTo(GameState.DRAW); @@ -282,4 +282,24 @@ public void testInvalidBoardPlayersKeptPlayingAfterAWin() { .isThrownBy(() -> stateOfTicTacToe.determineState(new String[]{"XXX", "OOO", "XOX"})) .withMessage("Impossible board: game should have ended after the game was won"); } + + @Disabled("Remove to run test") + @Test + @DisplayName("Invalid board: O kept playing after X wins") + public void testInvalidBoardOKeptPlayingAfterXWins() { + + assertThatExceptionOfType(IllegalArgumentException.class) + .isThrownBy(() -> stateOfTicTacToe.determineState(new String[]{"OO ", "XXX", " O "})) + .withMessage("Impossible board: game should have ended after the game was won"); + } + + @Disabled("Remove to run test") + @Test + @DisplayName("Invalid board: X kept playing after O wins") + public void testInvalidBoardXKeptPlayingAfterOWins() { + + assertThatExceptionOfType(IllegalArgumentException.class) + .isThrownBy(() -> stateOfTicTacToe.determineState(new String[]{"XX ", "OOO", " XX"})) + .withMessage("Impossible board: game should have ended after the game was won"); + } }