This is an automated email from the ASF dual-hosted git repository. Croway pushed a commit to branch camel-4.23-recipes in repository https://gitbox.apache.org/repos/asf/camel-upgrade-recipes.git
commit e36bc1cf82b4c503c3623c52d0ef852dbb0fcc47 Author: croway <[email protected]> AuthorDate: Tue Sep 15 13:48:49 2026 +0200 Add Camel 4.23.0 upgrade recipes Migrates the csimple language removal, camel-zeebe -> camel-camunda rename, camel-langchain4j-tools module removal, camel-ibm-cos header rename, and the headersmap/reactive-executor-vertx/threadpoolfactory-vertx removals, plus the matching Camel Spring Boot starter changes. See release_notes.adoc for full coverage and #131 for tracking. Co-Authored-By: Claude Sonnet 5 <[email protected]> --- .../src/main/resources/META-INF/rewrite/4.23.yaml | 76 +++ .../main/resources/META-INF/rewrite/latest.yaml | 2 +- .../upgrade/springboot/CamelSpringBoot423Test.java | 257 ++++++++ camel-upgrade-recipes/pom.xml | 8 + .../upgrade/camel423/YamlDslCSimpleRecipe.java | 65 ++ .../src/main/resources/META-INF/rewrite/4.23.yaml | 262 ++++++++ .../main/resources/META-INF/rewrite/latest.yaml | 1 + .../org/apache/camel/upgrade/CamelTestUtil.java | 3 +- .../apache/camel/upgrade/CamelUpdate423Test.java | 690 +++++++++++++++++++++ pom.xml | 2 +- release_notes.adoc | 86 +++ 11 files changed, 1449 insertions(+), 3 deletions(-) diff --git a/camel-spring-boot-upgrade-recipes/src/main/resources/META-INF/rewrite/4.23.yaml b/camel-spring-boot-upgrade-recipes/src/main/resources/META-INF/rewrite/4.23.yaml new file mode 100644 index 0000000..7cb1e94 --- /dev/null +++ b/camel-spring-boot-upgrade-recipes/src/main/resources/META-INF/rewrite/4.23.yaml @@ -0,0 +1,76 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You 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 +# +# http://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. +# +--- +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.CamelSpringBootMigrationRecipe +displayName: Migrates Camel Spring Boot applications to Camel Spring Boot 4.23 +description: Migrates Camel Spring Boot applications to Camel Spring Boot 4.23. +recipeList: + - org.apache.camel.upgrade.camel422.CamelSpringBootMigrationRecipe + - org.apache.camel.upgrade.camel423.CamelMigrationRecipe + - org.apache.camel.upgrade.camel423.removeCSimpleJoorStarterDependency + - org.apache.camel.upgrade.camel423.migrateLangchain4jToolsStarterDependency + - org.apache.camel.upgrade.camel423.migrateZeebeStarterDependency +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#components-and-language-removal +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.removeCSimpleJoorStarterDependency +displayName: Remove camel-csimple-joor-starter dependency +description: camel-csimple-joor-starter was removed in Camel Spring Boot 4.23, together with the csimple language. +recipeList: + - org.openrewrite.maven.RemoveDependency: + groupId: org.apache.camel.springboot + artifactId: camel-csimple-joor-starter +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#camel-langchain4j-tools +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.migrateLangchain4jToolsStarterDependency +displayName: Migrate camel-langchain4j-tools-starter to camel-ai-tool-starter +description: >- + camel-langchain4j-tools-starter was removed in Camel Spring Boot 4.23. Renames it directly to + camel-ai-tool-starter. This is a plain rename of the existing starter dependency element, so unlike the plain + Camel camel-langchain4j-tools removal it needs no dependency-presence guard, and it does not conflict with + camel422.migrateAiToolStarterDependency, which only swaps a plain org.apache.camel:camel-ai-tool dependency + (added by camel422.migrateLangchain4jToolsUris) for the starter; the two never target the same element, so no + duplicate camel-ai-tool-starter entry can result. Producer endpoints for direct tool calling still need manual + migration to langchain4j-agent. +recipeList: + - org.openrewrite.maven.ChangeDependencyGroupIdAndArtifactId: + oldGroupId: org.apache.camel.springboot + oldArtifactId: camel-langchain4j-tools-starter + newGroupId: org.apache.camel.springboot + newArtifactId: camel-ai-tool-starter + newVersion: 4.23.0 +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#camel-zeebe +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.migrateZeebeStarterDependency +displayName: Migrate camel-zeebe-starter to camel-camunda-starter +description: >- + camel-zeebe-starter was removed in Camel Spring Boot 4.23 together with camel-zeebe. Renames it to + camel-camunda-starter, the Spring Boot auto-configuration starter for the new camel-camunda component. + NOTE: at the time this recipe was written camel-camunda-starter had not yet been published; verify it exists + under org.apache.camel.springboot before this recipe ships. If it does not, fall back to + org.apache.camel:camel-camunda (no Spring Boot auto-configuration) and document that in the release notes + instead. +recipeList: + - org.openrewrite.maven.ChangeDependencyGroupIdAndArtifactId: + oldGroupId: org.apache.camel.springboot + oldArtifactId: camel-zeebe-starter + newGroupId: org.apache.camel.springboot + newArtifactId: camel-camunda-starter + newVersion: 4.23.0 diff --git a/camel-spring-boot-upgrade-recipes/src/main/resources/META-INF/rewrite/latest.yaml b/camel-spring-boot-upgrade-recipes/src/main/resources/META-INF/rewrite/latest.yaml index 42a50f9..b59e5df 100644 --- a/camel-spring-boot-upgrade-recipes/src/main/resources/META-INF/rewrite/latest.yaml +++ b/camel-spring-boot-upgrade-recipes/src/main/resources/META-INF/rewrite/latest.yaml @@ -21,7 +21,7 @@ displayName: Migrate to Apache Camel Spring Boot @camel-latest-version@ description: >- Migrate applications to Apache Camel Spring Boot @camel-latest-version@ and Spring Boot @spring-boot-version@. recipeList: - - org.apache.camel.upgrade.camel422.CamelSpringBootMigrationRecipe + - org.apache.camel.upgrade.camel423.CamelSpringBootMigrationRecipe - org.openrewrite.maven.UpgradeDependencyVersion: groupId: '*camel*' artifactId: 'camel-spring-boot-bom' diff --git a/camel-spring-boot-upgrade-recipes/src/test/java/org/apache/camel/upgrade/springboot/CamelSpringBoot423Test.java b/camel-spring-boot-upgrade-recipes/src/test/java/org/apache/camel/upgrade/springboot/CamelSpringBoot423Test.java new file mode 100644 index 0000000..f1e236b --- /dev/null +++ b/camel-spring-boot-upgrade-recipes/src/test/java/org/apache/camel/upgrade/springboot/CamelSpringBoot423Test.java @@ -0,0 +1,257 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You 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 + * + * http://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. + */ +package org.apache.camel.upgrade.springboot; + +import org.junit.jupiter.api.Test; +import org.openrewrite.DocumentExample; +import org.openrewrite.config.Environment; +import org.openrewrite.test.RecipeSpec; +import org.openrewrite.test.RewriteTest; + +import static org.openrewrite.maven.Assertions.pomXml; + +/** + * Each test activates its own narrow camel423 sub-recipe rather than the full + * camel423.CamelSpringBootMigrationRecipe chain. That chain transitively includes + * camel419.CamelSpringBootMigrationRecipe, which unconditionally upgrades every existing + * org.apache.camel.springboot:* dependency to @camel-spring-boot-version@ (this reactor's own + * project.version) as its very first step; exercising the full chain here would make every + * assertion depend on that unrelated, reactor-version-sensitive bump instead of on the recipe under + * test. LatestRecipeTest and the coverage in CamelSpringBoot422Test already guard that the chain is + * wired correctly. + */ +class CamelSpringBoot423Test implements RewriteTest { + + private static RecipeSpec withRecipe(RecipeSpec spec, String... recipeNames) { + return spec.recipe(Environment.builder() + .scanYamlResources() + .build() + .activateRecipes(recipeNames)); + } + + @DocumentExample + @Test + void removeCSimpleJoorStarterDependency() { + //language=xml + rewriteRun( + spec -> withRecipe(spec, "org.apache.camel.upgrade.camel423.removeCSimpleJoorStarterDependency"), + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel.springboot</groupId> + <artifactId>camel-csimple-joor-starter</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + </project> + """, + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + </project> + """ + ) + ); + } + + @Test + void migrateLangchain4jToolsStarterDependency() { + //language=xml + rewriteRun( + spec -> withRecipe(spec, "org.apache.camel.upgrade.camel423.migrateLangchain4jToolsStarterDependency"), + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel.springboot</groupId> + <artifactId>camel-langchain4j-tools-starter</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + </project> + """, + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel.springboot</groupId> + <artifactId>camel-ai-tool-starter</artifactId> + <version>4.23.0</version> + </dependency> + </dependencies> + </project> + """ + ) + ); + } + + @Test + void migrateLangchain4jToolsStarterDoesNotDuplicateAiToolStarter() { + // camel422.migrateAiToolStarterDependency only swaps a plain org.apache.camel:camel-ai-tool + // dependency; running it alongside camel423's starter-to-starter rename must not produce two + // camel-ai-tool-starter entries. + //language=xml + rewriteRun( + spec -> withRecipe(spec, + "org.apache.camel.upgrade.camel422.migrateAiToolStarterDependency", + "org.apache.camel.upgrade.camel423.migrateLangchain4jToolsStarterDependency"), + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.springframework.boot</groupId> + <artifactId>spring-boot-starter</artifactId> + <version>4.1.0</version> + </dependency> + <dependency> + <groupId>org.apache.camel.springboot</groupId> + <artifactId>camel-langchain4j-tools-starter</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + </project> + """, + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.springframework.boot</groupId> + <artifactId>spring-boot-starter</artifactId> + <version>4.1.0</version> + </dependency> + <dependency> + <groupId>org.apache.camel.springboot</groupId> + <artifactId>camel-ai-tool-starter</artifactId> + <version>4.23.0</version> + </dependency> + </dependencies> + </project> + """ + ) + ); + } + + @Test + void migrateZeebeStarterDependency() { + //language=xml + rewriteRun( + spec -> withRecipe(spec, "org.apache.camel.upgrade.camel423.migrateZeebeStarterDependency"), + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel.springboot</groupId> + <artifactId>camel-zeebe-starter</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + </project> + """, + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel.springboot</groupId> + <artifactId>camel-camunda-starter</artifactId> + <version>4.23.0</version> + </dependency> + </dependencies> + </project> + """ + ) + ); + } + + @Test + void doesNotTouchUnrelatedStarters() { + //language=xml + rewriteRun( + spec -> withRecipe(spec, "org.apache.camel.upgrade.camel423.removeCSimpleJoorStarterDependency"), + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel.springboot</groupId> + <artifactId>camel-kafka-starter</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + </project> + """ + ) + ); + } +} diff --git a/camel-upgrade-recipes/pom.xml b/camel-upgrade-recipes/pom.xml index 72602f4..65fabf1 100644 --- a/camel-upgrade-recipes/pom.xml +++ b/camel-upgrade-recipes/pom.xml @@ -635,6 +635,14 @@ <outputDirectory>${rewrite-tmp-classpath}</outputDirectory> </artifactItem> + <!-- camel-zeebe for the zeebe to camunda ChangeType migration tests (4.23) --> + <artifactItem> + <groupId>org.apache.camel</groupId> + <artifactId>camel-zeebe</artifactId> + <version>${camel4.18-version}</version> + <outputDirectory>${rewrite-tmp-classpath}</outputDirectory> + </artifactItem> + </artifactItems> </configuration> </execution> diff --git a/camel-upgrade-recipes/src/main/java/org/apache/camel/upgrade/camel423/YamlDslCSimpleRecipe.java b/camel-upgrade-recipes/src/main/java/org/apache/camel/upgrade/camel423/YamlDslCSimpleRecipe.java new file mode 100644 index 0000000..141d195 --- /dev/null +++ b/camel-upgrade-recipes/src/main/java/org/apache/camel/upgrade/camel423/YamlDslCSimpleRecipe.java @@ -0,0 +1,65 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You 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 + * + * http://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. + */ +package org.apache.camel.upgrade.camel423; + +import org.apache.camel.upgrade.AbstractCamelYamlVisitor; +import org.apache.camel.upgrade.RecipesUtil; +import org.openrewrite.ExecutionContext; +import org.openrewrite.Preconditions; +import org.openrewrite.Recipe; +import org.openrewrite.TreeVisitor; +import org.openrewrite.yaml.tree.Yaml; + +/** + * Renames the removed {@code csimple} expression language key to {@code simple} in YAML DSL documents. + * Scoped to documents that belong to the Camel YAML DSL, so an unrelated YAML file that happens to + * contain a {@code csimple} key is left untouched. + */ +public class YamlDslCSimpleRecipe extends Recipe { + + @Override + public String getDisplayName() { + return "Migrate csimple YAML DSL expression key to simple"; + } + + @Override + public String getDescription() { + return "Renames the removed csimple expression key to simple in Camel YAML DSL documents."; + } + + @Override + public TreeVisitor<?, ExecutionContext> getVisitor() { + return Preconditions.check(RecipesUtil.camelYamlDslPrecondition(), new AbstractCamelYamlVisitor() { + + @Override + protected void clearLocalCache() { + // Nothing to cache + } + + @Override + public Yaml.Mapping.Entry doVisitMappingEntry(Yaml.Mapping.Entry entry, ExecutionContext ctx) { + Yaml.Mapping.Entry e = super.doVisitMappingEntry(entry, ctx); + + if ("csimple".equals(e.getKey().getValue())) { + return e.withKey(((Yaml.Scalar) e.getKey().copyPaste()).withValue("simple")); + } + + return e; + } + }); + } +} diff --git a/camel-upgrade-recipes/src/main/resources/META-INF/rewrite/4.23.yaml b/camel-upgrade-recipes/src/main/resources/META-INF/rewrite/4.23.yaml new file mode 100644 index 0000000..c7e0434 --- /dev/null +++ b/camel-upgrade-recipes/src/main/resources/META-INF/rewrite/4.23.yaml @@ -0,0 +1,262 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You 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 +# +# http://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. +# + +##### +# Rules coming from https://camel.apache.org/manual/camel-4x-upgrade-guide-4_23.html +##### + +##### +# Update the Camel project from 4.22 to 4.23 +##### +--- +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.CamelMigrationRecipe +displayName: Migrates `camel 4.22` application to `camel 4.23` +description: Migrates `camel 4.22` application to `camel 4.23`. +recipeList: + - org.apache.camel.upgrade.camel423.migrateCSimpleJavaApi + - org.apache.camel.upgrade.camel423.migrateCSimpleXmlDsl + - org.apache.camel.upgrade.camel423.migrateCSimpleYamlDsl + - org.apache.camel.upgrade.camel423.removeCSimpleDependencies + - org.apache.camel.upgrade.camel423.migrateZeebeToCamunda + - org.apache.camel.upgrade.camel423.removeLangchain4jToolsModule + - org.apache.camel.upgrade.camel423.migrateIbmCosCacheControlHeader + - org.apache.camel.upgrade.camel423.removeHeadersmapDependency + - org.apache.camel.upgrade.camel423.removeReactiveExecutorVertxDependency + - org.apache.camel.upgrade.camel423.removeThreadPoolFactoryVertxDependency +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#components-and-language-removal +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.migrateCSimpleJavaApi +displayName: Migrate csimple Java API to simple +description: The csimple language was removed in Camel 4.23. Renames the removed csimple(...) builder methods to the equivalent simple(...) overloads, and changes the removed org.apache.camel.model.language.CSimpleExpression type to org.apache.camel.model.language.SimpleExpression. Expressions relying on csimple-only compiled syntax still need manual review. +recipeList: + - org.openrewrite.java.ChangeMethodName: + methodPattern: org.apache.camel.builder.Builder csimple(String) + newMethodName: simple + - org.openrewrite.java.ChangeMethodName: + methodPattern: org.apache.camel.builder.Builder csimple(String, Class) + newMethodName: simple + - org.openrewrite.java.ChangeMethodName: + methodPattern: org.apache.camel.builder.BuilderSupport csimple(String) + newMethodName: simple + - org.openrewrite.java.ChangeMethodName: + methodPattern: org.apache.camel.builder.BuilderSupport csimple(String, Class) + newMethodName: simple + - org.openrewrite.java.ChangeMethodName: + methodPattern: org.apache.camel.builder.ExpressionClause csimple(String) + newMethodName: simple + - org.openrewrite.java.ChangeMethodName: + methodPattern: org.apache.camel.builder.ExpressionClause csimple(String, Class) + newMethodName: simple + - org.openrewrite.java.ChangeMethodName: + methodPattern: org.apache.camel.builder.ExpressionClauseSupport csimple(String) + newMethodName: simple + - org.openrewrite.java.ChangeMethodName: + methodPattern: org.apache.camel.builder.ExpressionClauseSupport csimple(String, Class) + newMethodName: simple + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.model.language.CSimpleExpression + newFullyQualifiedTypeName: org.apache.camel.model.language.SimpleExpression +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#components-and-language-removal +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.migrateCSimpleXmlDsl +displayName: Migrate csimple XML DSL element to simple +description: Renames the removed <csimple> XML DSL expression element to <simple>, only in documents that belong to the Camel XML DSL. +preconditions: + - org.apache.camel.upgrade.customRecipes.FindCamelXmlDsl +recipeList: + - org.openrewrite.xml.ChangeTagName: + elementName: //csimple + newName: simple +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#components-and-language-removal +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.migrateCSimpleYamlDsl +displayName: Migrate csimple YAML DSL expression key to simple +description: Renames the removed csimple expression key to simple in YAML DSL documents, without touching unrelated YAML files that happen to contain a csimple key. +recipeList: + - org.apache.camel.upgrade.camel423.YamlDslCSimpleRecipe +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#components-and-language-removal +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.removeCSimpleDependencies +displayName: Remove camel-csimple-joor dependency and camel-csimple-maven-plugin +description: Removes the camel-csimple-joor dependency and the camel-csimple-maven-plugin build plugin, both removed in Camel 4.23 together with the csimple language. +recipeList: + - org.openrewrite.maven.RemoveDependency: + groupId: org.apache.camel + artifactId: camel-csimple-joor + - org.openrewrite.maven.RemovePlugin: + groupId: org.apache.camel + artifactId: camel-csimple-maven-plugin +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#camel-zeebe +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.migrateZeebeToCamunda +displayName: Migrate camel-zeebe to camel-camunda +description: >- + camel-zeebe was renamed to camel-camunda in Camel 4.23, keeping the same 9 operations. Migrates the dependency, + the zeebe: URI scheme (including the jobKey to jobType endpoint option rename), the shared model classes, the + 8 CamelZeebe* literal header names and the ZeebeConstants type. All steps are bundled in a single + dependency-gated recipe so that later steps still see the camel-zeebe dependency after earlier steps have + renamed it. Header names are migrated with explicit old-to-new mappings rather than a prefix rename, since + RenameHeaderPrefixes only matches the org.apache.camel.Message setHeader/getHeader methods and not the fluent + ProcessorDefinition.setHeader(...) route-builder DSL, unlike RenameHeaders which handles both. + gatewayHost/gatewayPort (replaced by grpcAddress), the new SaaS/REST options, the two zeebe-only model classes + (renamed rather than dropped: AbstractZeebeResponse to AbstractCamundaResponse and ZeebeMessage to + CamundaMessage, both handled below), worker auto-complete behaviour and the zeebe() Endpoint DSL builder are not + covered and need manual review. +preconditions: + - org.openrewrite.java.dependencies.search.ModuleHasDependency: + groupIdPattern: org.apache.camel + artifactIdPattern: camel-zeebe +recipeList: + - org.apache.camel.upgrade.customRecipes.ChangeComponentUriRecipe: + uriPattern: "^zeebe:(.*?)jobKey=(.*)$" + replacement: "zeebe:${1}jobType=${2}" + - org.apache.camel.upgrade.customRecipes.ChangeComponentUriRecipe: + uriPattern: "^zeebe:(.*)$" + replacement: "camunda:${1}" + - org.openrewrite.maven.ChangeDependencyGroupIdAndArtifactId: + oldGroupId: org.apache.camel + oldArtifactId: camel-zeebe + newGroupId: org.apache.camel + newArtifactId: camel-camunda + newVersion: 4.23.0 + - org.apache.camel.upgrade.customRecipes.PropertiesAndYamlKeyUpdate: + oldPropertyKey: camel.component.zeebe.client-id + newPropertyKey: camel.component.camunda.client-id + - org.apache.camel.upgrade.customRecipes.PropertiesAndYamlKeyUpdate: + oldPropertyKey: camel.component.zeebe.client-secret + newPropertyKey: camel.component.camunda.client-secret + - org.apache.camel.upgrade.customRecipes.PropertiesAndYamlKeyUpdate: + oldPropertyKey: camel.component.zeebe.o-auth-api + newPropertyKey: camel.component.camunda.o-auth-api + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.ZeebeConstants + newFullyQualifiedTypeName: org.apache.camel.component.camunda.CamundaConstants + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.model.AbstractZeebeResponse + newFullyQualifiedTypeName: org.apache.camel.component.camunda.model.AbstractCamundaResponse + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.model.ZeebeMessage + newFullyQualifiedTypeName: org.apache.camel.component.camunda.model.CamundaMessage + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.model.DeploymentRequest + newFullyQualifiedTypeName: org.apache.camel.component.camunda.model.DeploymentRequest + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.model.DeploymentResponse + newFullyQualifiedTypeName: org.apache.camel.component.camunda.model.DeploymentResponse + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.model.JobRequest + newFullyQualifiedTypeName: org.apache.camel.component.camunda.model.JobRequest + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.model.JobResponse + newFullyQualifiedTypeName: org.apache.camel.component.camunda.model.JobResponse + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.model.JobWorkerMessage + newFullyQualifiedTypeName: org.apache.camel.component.camunda.model.JobWorkerMessage + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.model.MessageRequest + newFullyQualifiedTypeName: org.apache.camel.component.camunda.model.MessageRequest + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.model.MessageResponse + newFullyQualifiedTypeName: org.apache.camel.component.camunda.model.MessageResponse + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.model.ProcessDeploymentResponse + newFullyQualifiedTypeName: org.apache.camel.component.camunda.model.ProcessDeploymentResponse + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.model.ProcessRequest + newFullyQualifiedTypeName: org.apache.camel.component.camunda.model.ProcessRequest + - org.openrewrite.java.ChangeType: + oldFullyQualifiedTypeName: org.apache.camel.component.zeebe.model.ProcessResponse + newFullyQualifiedTypeName: org.apache.camel.component.camunda.model.ProcessResponse + - org.apache.camel.upgrade.camel418_3.RenameHeaders: + headerMappings: + CamelZeebeResourceName: CamelCamundaResourceName + CamelZeebeIsSuccess: CamelCamundaIsSuccess + CamelZeebeErrorMessage: CamelCamundaErrorMessage + CamelZeebeErrorCode: CamelCamundaErrorCode + CamelZeebeBPMNProcessId: CamelCamundaBPMNProcessId + CamelZeebeVersion: CamelCamundaVersion + CamelZeebeProcessDefinitionKey: CamelCamundaProcessDefinitionKey + CamelZeebeJobKey: CamelCamundaJobKey +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#camel-langchain4j-tools +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.removeLangchain4jToolsModule +displayName: Remove camel-langchain4j-tools dependency +description: >- + camel-langchain4j-tools was removed in Camel 4.23. Removes the dependency only once camel-ai-tool is present, so + that this recipe running ahead of camel422.migrateLangchain4jToolsUris in the latest migration chain does not + defeat that recipe's own camel-langchain4j-tools precondition before it has migrated the consumer endpoint URIs; + the removal then takes effect on the following cycle. Producer endpoints for direct tool calling still need + manual migration to langchain4j-agent. +preconditions: + - org.openrewrite.java.dependencies.search.ModuleHasDependency: + groupIdPattern: org.apache.camel + artifactIdPattern: camel-ai-tool +recipeList: + - org.openrewrite.maven.RemoveDependency: + groupId: org.apache.camel + artifactId: camel-langchain4j-tools +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#camel-ibm-cos +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.migrateIbmCosCacheControlHeader +displayName: Migrate camel-ibm-cos CamelIBMCOSContentControl header to CamelIBMCOSCacheControl +description: The IBMCOSConstants.CACHE_CONTROL header value was renamed from CamelIBMCOSContentControl to CamelIBMCOSCacheControl in Camel 4.23. Existing IBMCOSConstants.CACHE_CONTROL usages need no change, only string literal header names. +preconditions: + - org.openrewrite.java.dependencies.search.ModuleHasDependency: + groupIdPattern: org.apache.camel + artifactIdPattern: camel-ibm-cos +recipeList: + - org.apache.camel.upgrade.camel418_3.RenameHeaders: + oldHeaderName: CamelIBMCOSContentControl + newHeaderName: CamelIBMCOSCacheControl +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#camel-headersmap +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.removeHeadersmapDependency +displayName: Remove camel-headersmap dependency +description: camel-headersmap was removed in Camel 4.23. It was only discovered at runtime through the headers-map-factory META-INF/services entry, and Camel falls back to its default headers map factory automatically. Direct uses of FastHeadersMapFactory must be removed manually. +recipeList: + - org.openrewrite.maven.RemoveDependency: + groupId: org.apache.camel + artifactId: camel-headersmap +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#camel-reactive-executor-vertx +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.removeReactiveExecutorVertxDependency +displayName: Remove camel-reactive-executor-vertx dependency +description: camel-reactive-executor-vertx was removed in Camel 4.23. It was only discovered at runtime through the reactive-executor META-INF/services entry, and Camel falls back to its default reactive executor automatically. Direct uses of VertXReactiveExecutor must be removed manually. +recipeList: + - org.openrewrite.maven.RemoveDependency: + groupId: org.apache.camel + artifactId: camel-reactive-executor-vertx +--- +## https://github.com/apache/camel/blob/main/docs/user-manual/modules/ROOT/pages/camel-4x-upgrade-guide-4_23.adoc#camel-threadpoolfactory-vertx +type: specs.openrewrite.org/v1beta/recipe +name: org.apache.camel.upgrade.camel423.removeThreadPoolFactoryVertxDependency +displayName: Remove camel-threadpoolfactory-vertx dependency +description: camel-threadpoolfactory-vertx was removed in Camel 4.23. It was only discovered at runtime through the thread-pool-factory META-INF/services entry, and Camel falls back to its default thread pool factory automatically. Direct uses of VertXThreadPoolFactory must be removed manually. +recipeList: + - org.openrewrite.maven.RemoveDependency: + groupId: org.apache.camel + artifactId: camel-threadpoolfactory-vertx diff --git a/camel-upgrade-recipes/src/main/resources/META-INF/rewrite/latest.yaml b/camel-upgrade-recipes/src/main/resources/META-INF/rewrite/latest.yaml index 83b6410..b98a2ce 100644 --- a/camel-upgrade-recipes/src/main/resources/META-INF/rewrite/latest.yaml +++ b/camel-upgrade-recipes/src/main/resources/META-INF/rewrite/latest.yaml @@ -20,6 +20,7 @@ name: org.apache.camel.upgrade.CamelMigrationRecipe displayName: Migrate to @camel-latest-version@ description: Migrates Apache Camel application to @camel-latest-version@. recipeList: + - org.apache.camel.upgrade.camel423.CamelMigrationRecipe - org.apache.camel.upgrade.camel422.CamelMigrationRecipe - org.apache.camel.upgrade.camel421.CamelMigrationRecipe - org.apache.camel.upgrade.camel420.CamelMigrationRecipe diff --git a/camel-upgrade-recipes/src/test/java/org/apache/camel/upgrade/CamelTestUtil.java b/camel-upgrade-recipes/src/test/java/org/apache/camel/upgrade/CamelTestUtil.java index 7118070..ea9fc47 100644 --- a/camel-upgrade-recipes/src/test/java/org/apache/camel/upgrade/CamelTestUtil.java +++ b/camel-upgrade-recipes/src/test/java/org/apache/camel/upgrade/CamelTestUtil.java @@ -63,7 +63,8 @@ public class CamelTestUtil { v4_19(4, 19, 0), v4_20(4, 20, 0), v4_21(4, 21, 0), - v4_22(4, 22, 0); + v4_22(4, 22, 0), + v4_23(4, 23, 0); private int major; private int minor; diff --git a/camel-upgrade-recipes/src/test/java/org/apache/camel/upgrade/CamelUpdate423Test.java b/camel-upgrade-recipes/src/test/java/org/apache/camel/upgrade/CamelUpdate423Test.java new file mode 100644 index 0000000..04e219d --- /dev/null +++ b/camel-upgrade-recipes/src/test/java/org/apache/camel/upgrade/CamelUpdate423Test.java @@ -0,0 +1,690 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You 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 + * + * http://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. + */ +package org.apache.camel.upgrade; + +import org.junit.jupiter.api.Test; +import org.junit.jupiter.api.condition.DisabledIfSystemProperty; +import org.openrewrite.DocumentExample; +import org.openrewrite.test.RecipeSpec; +import org.openrewrite.test.RewriteTest; +import org.openrewrite.test.TypeValidation; + +import static org.openrewrite.java.Assertions.java; +import static org.openrewrite.java.Assertions.mavenProject; +import static org.openrewrite.maven.Assertions.pomXml; +import static org.openrewrite.xml.Assertions.xml; +import static org.openrewrite.yaml.Assertions.yaml; + +public class CamelUpdate423Test implements RewriteTest { + + @Override + public void defaults(RecipeSpec spec) { + CamelTestUtil.recipe(spec, CamelTestUtil.CamelVersion.v4_23, true) + .parser(CamelTestUtil.parserFromClasspath(CamelTestUtil.CamelVersion.v4_22, + "camel-core-model", "camel-api", "camel-support", "camel-zeebe", "jakarta.xml.bind-api")) + .typeValidationOptions(TypeValidation.none()) + .expectedCyclesThatMakeChanges(1); + } + + @DocumentExample + @Test + void migrateCSimpleJavaApi() { + //language=java + rewriteRun( + java( + """ + import org.apache.camel.builder.Builder; + import org.apache.camel.builder.RouteBuilder; + import org.apache.camel.model.language.CSimpleExpression; + + public class CSimpleRoute extends RouteBuilder { + private CSimpleExpression expression = new CSimpleExpression("${body}"); + + @Override + public void configure() { + from("direct:in") + .filter(Builder.csimple("${body} != null")) + .setBody().csimple("${body.toUpperCase()}") + .to("mock:result"); + } + } + """, + """ + import org.apache.camel.builder.Builder; + import org.apache.camel.builder.RouteBuilder; + import org.apache.camel.model.language.SimpleExpression; + + public class CSimpleRoute extends RouteBuilder { + private SimpleExpression expression = new SimpleExpression("${body}"); + + @Override + public void configure() { + from("direct:in") + .filter(Builder.simple("${body} != null")) + .setBody().simple("${body.toUpperCase()}") + .to("mock:result"); + } + } + """ + ) + ); + } + + @Test + void preconditionLeavesPlainSimpleUsageUntouched() { + //language=java + rewriteRun( + spec -> spec.expectedCyclesThatMakeChanges(0), + java( + """ + import org.apache.camel.builder.RouteBuilder; + + import static org.apache.camel.builder.Builder.simple; + + public class SimpleRoute extends RouteBuilder { + @Override + public void configure() { + from("direct:in") + .filter(simple("${body} != null")) + .to("mock:result"); + } + } + """ + ) + ); + } + + @Test + void migrateCSimpleXmlDsl() { + //language=xml + rewriteRun( + xml( + """ + <routes xmlns="http://camel.apache.org/schema/spring"> + <route id="csimpleRoute"> + <from uri="direct:in"/> + <filter> + <csimple>${body} != null</csimple> + <to uri="mock:result"/> + </filter> + </route> + </routes> + """, + """ + <routes xmlns="http://camel.apache.org/schema/spring"> + <route id="csimpleRoute"> + <from uri="direct:in"/> + <filter> + <simple>${body} != null</simple> + <to uri="mock:result"/> + </filter> + </route> + </routes> + """ + ) + ); + } + + @Test + void preconditionLeavesNonCamelXmlCSimpleTagUntouched() { + //language=xml + rewriteRun( + spec -> spec.expectedCyclesThatMakeChanges(0), + xml( + """ + <config> + <csimple>not a Camel document</csimple> + </config> + """ + ) + ); + } + + @Test + void migrateCSimpleYamlDsl() { + //language=yaml + rewriteRun( + yaml( + """ + - route: + id: csimpleRoute + from: + uri: direct:in + steps: + - filter: + csimple: "${body} != null" + - to: + uri: mock:result + """, + """ + - route: + id: csimpleRoute + from: + uri: direct:in + steps: + - filter: + simple: "${body} != null" + - to: + uri: mock:result + """ + ) + ); + } + + @Test + void preconditionLeavesNonCamelYamlCSimpleKeyUntouched() { + //language=yaml + rewriteRun( + spec -> spec.expectedCyclesThatMakeChanges(0), + yaml( + """ + config: + csimple: "not a Camel document" + """ + ) + ); + } + + @Test + void removeCSimpleDependencies() { + //language=xml + rewriteRun( + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel</groupId> + <artifactId>camel-csimple-joor</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + <build> + <plugins> + <plugin> + <groupId>org.apache.camel</groupId> + <artifactId>camel-csimple-maven-plugin</artifactId> + <version>4.22.0</version> + </plugin> + </plugins> + </build> + </project> + """, + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + </project> + """ + ) + ); + } + + @Test + void migrateZeebeToCamunda() { + rewriteRun( + mavenProject("test-zeebe", + //language=xml + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel</groupId> + <artifactId>camel-zeebe</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + </project> + """, + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel</groupId> + <artifactId>camel-camunda</artifactId> + <version>4.23.0</version> + </dependency> + </dependencies> + </project> + """ + ), + //language=java + java( + """ + import org.apache.camel.builder.RouteBuilder; + import org.apache.camel.component.zeebe.ZeebeConstants; + import org.apache.camel.component.zeebe.model.JobRequest; + import org.apache.camel.component.zeebe.model.ZeebeMessage; + + public class ZeebeRoute extends RouteBuilder { + private JobRequest request; + private ZeebeMessage message; + + @Override + public void configure() { + from("zeebe:worker?jobKey=myJob") + .setHeader(ZeebeConstants.HEADER_PREFIX, constant("x")) + .setHeader("CamelZeebeJobKey", constant("123")) + .to("zeebe:deployment?resource=classpath:process.bpmn"); + } + } + """, + """ + import org.apache.camel.builder.RouteBuilder; + import org.apache.camel.component.camunda.CamundaConstants; + import org.apache.camel.component.camunda.model.CamundaMessage; + import org.apache.camel.component.camunda.model.JobRequest; + + public class ZeebeRoute extends RouteBuilder { + private JobRequest request; + private CamundaMessage message; + + @Override + public void configure() { + from("camunda:worker?jobType=myJob") + .setHeader(CamundaConstants.HEADER_PREFIX, constant("x")) + .setHeader("CamelCamundaJobKey", constant("123")) + .to("camunda:deployment?resource=classpath:process.bpmn"); + } + } + """ + ) + ) + ); + } + + @Test + void preconditionBlocksZeebeWithoutDependency() { + //language=java + rewriteRun( + spec -> spec.expectedCyclesThatMakeChanges(CamelTestUtil.isRecipeOverridden() ? 1 : 0), + mavenProject("test-negative", + CamelTestUtil.pomXmlSpec("camel-core", CamelTestUtil.CamelVersion.v4_22), + java( + """ + import org.apache.camel.builder.RouteBuilder; + + public class NegativeZeebeRoute extends RouteBuilder { + @Override + public void configure() { + from("direct:in") + .to("zeebe:worker?jobKey=myJob"); + } + } + """ + ) + ) + ); + } + + @Test + void migrateIbmCosCacheControlHeader() { + //language=java + rewriteRun( + mavenProject("test-ibm-cos", + CamelTestUtil.pomXmlSpec("camel-ibm-cos", CamelTestUtil.CamelVersion.v4_22), + java( + """ + import org.apache.camel.builder.RouteBuilder; + + public class IbmCosRoute extends RouteBuilder { + @Override + public void configure() { + from("direct:next") + .setHeader("CamelIBMCOSContentControl", constant("no-cache")) + .to("ibm-cos:mybucket"); + } + } + """, + """ + import org.apache.camel.builder.RouteBuilder; + + public class IbmCosRoute extends RouteBuilder { + @Override + public void configure() { + from("direct:next") + .setHeader("CamelIBMCOSCacheControl", constant("no-cache")) + .to("ibm-cos:mybucket"); + } + } + """ + ) + ) + ); + } + + @Test + void preconditionBlocksIbmCosWithoutDependency() { + //language=java + rewriteRun( + spec -> spec.expectedCyclesThatMakeChanges(CamelTestUtil.isRecipeOverridden() ? 1 : 0), + mavenProject("test-negative-ibm-cos", + CamelTestUtil.pomXmlSpec("camel-core", CamelTestUtil.CamelVersion.v4_22), + java( + """ + import org.apache.camel.builder.RouteBuilder; + + public class NegativeIbmCosRoute extends RouteBuilder { + @Override + public void configure() { + from("direct:next") + .setHeader("CamelIBMCOSContentControl", constant("no-cache")) + .to("mock:result"); + } + } + """ + ) + ) + ); + } + + @Test + void removeHeadersmapDependency() { + //language=xml + rewriteRun( + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel</groupId> + <artifactId>camel-headersmap</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + </project> + """, + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + </project> + """ + ) + ); + } + + @Test + void removeReactiveExecutorVertxDependency() { + //language=xml + rewriteRun( + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel</groupId> + <artifactId>camel-reactive-executor-vertx</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + </project> + """, + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + </project> + """ + ) + ); + } + + @Test + void removeThreadPoolFactoryVertxDependency() { + //language=xml + rewriteRun( + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel</groupId> + <artifactId>camel-threadpoolfactory-vertx</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + </project> + """, + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + </project> + """ + ) + ); + } + + @Test + @DisabledIfSystemProperty(named = CamelTestUtil.PROPERTY_USE_RECIPE, matches = ".+") + void removeLangchain4jToolsRequiresAiToolPresent() { + //language=xml + rewriteRun( + spec -> CamelTestUtil.recipe(spec, CamelTestUtil.CamelVersion.v4_23, true, + "org.apache.camel.upgrade.camel423.removeLangchain4jToolsModule") + .expectedCyclesThatMakeChanges(0), + mavenProject("test-negative-langchain4j-tools", + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel</groupId> + <artifactId>camel-langchain4j-tools</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + </project> + """ + ) + ) + ); + } + + @Test + @DisabledIfSystemProperty(named = CamelTestUtil.PROPERTY_USE_RECIPE, matches = ".+") + void removeLangchain4jToolsWhenAiToolAlreadyPresent() { + //language=xml + rewriteRun( + spec -> CamelTestUtil.recipe(spec, CamelTestUtil.CamelVersion.v4_23, true, + "org.apache.camel.upgrade.camel423.removeLangchain4jToolsModule"), + mavenProject("test-langchain4j-tools", + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel</groupId> + <artifactId>camel-langchain4j-tools</artifactId> + <version>4.22.0</version> + </dependency> + <dependency> + <groupId>org.apache.camel</groupId> + <artifactId>camel-ai-tool</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + </project> + """, + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel</groupId> + <artifactId>camel-ai-tool</artifactId> + <version>4.22.0</version> + </dependency> + </dependencies> + </project> + """ + ) + ) + ); + } + + /** + * The full chain in latest.yaml runs camel423 before camel422. camel423 removes + * camel-langchain4j-tools only once camel-ai-tool is present, so on a project that has never been + * migrated, camel422.migrateLangchain4jToolsUris must still see the camel-langchain4j-tools + * dependency, migrate the consumer URI and add camel-ai-tool in the first cycle; camel423 then + * removes the now-redundant camel-langchain4j-tools dependency on the following cycle. + */ + @Test + void fullChainMigratesLangchain4jToolsUriBeforeRemovingDependency() { + rewriteRun( + spec -> spec.recipeFromResources("org.apache.camel.upgrade.CamelMigrationRecipe") + .expectedCyclesThatMakeChanges(2), + mavenProject("test-langchain4j-tools-chain", + //language=xml + pomXml( + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel</groupId> + <artifactId>camel-langchain4j-tools</artifactId> + <version>4.21.0</version> + </dependency> + </dependencies> + </project> + """, + """ + <project> + <groupId>com.example</groupId> + <artifactId>test</artifactId> + <version>1.0.0</version> + <properties> + <maven.compiler.release>17</maven.compiler.release> + </properties> + <dependencies> + <dependency> + <groupId>org.apache.camel</groupId> + <artifactId>camel-ai-tool</artifactId> + <version>4.23.0</version> + </dependency> + </dependencies> + </project> + """ + ), + //language=java + java( + """ + import org.apache.camel.builder.RouteBuilder; + + public class ToolRoute extends RouteBuilder { + @Override + public void configure() { + from("langchain4j-tools:userDb?tags=users&description=Query user database¶meter.userId=string") + .to("mock:result"); + } + } + """, + """ + import org.apache.camel.builder.RouteBuilder; + + public class ToolRoute extends RouteBuilder { + @Override + public void configure() { + from("ai-tool:userDb?tags=users&description=Query user database¶meter.userId=string") + .to("mock:result"); + } + } + """ + ) + ) + ); + } + +} diff --git a/pom.xml b/pom.xml index c182821..dba8460 100644 --- a/pom.xml +++ b/pom.xml @@ -109,7 +109,7 @@ <camel4.18-lts-version>4.18.3</camel4.18-lts-version> <!-- versions for latest recipes, has to be kept aligned to the latest camel release --> - <camel-latest-version>4.22.0</camel-latest-version> + <camel-latest-version>4.23.0</camel-latest-version> <camel-version>${project.version}</camel-version> <camel-spring-boot-version>${project.version}</camel-spring-boot-version> diff --git a/release_notes.adoc b/release_notes.adoc index d523aa6..04a3bba 100644 --- a/release_notes.adoc +++ b/release_notes.adoc @@ -1,5 +1,91 @@ = Camel Upgrade Recipes - Release notes +== 4.23.0 + +=== Summary + +This is a release supporting Camel, Camel Quarkus and Camel Spring Boot 4.23.0 with the required upgrade recipes (described by the https://camel.apache.org/manual/camel-4x-upgrade-guide-4_23.html[migration guide]). + +=== Migration coverage + +The following table lists migration topics and indicates the level of coverage (full, partial, or not covered), along with additional comments. + +[%autowidth,stripes=hover] +|=== +| Migration | Coverage | Comment + +| https://camel.apache.org/manual/camel-4x-upgrade-guide-4_23.html#_components_and_language_removal[camel-csimple: language and camel-csimple-joor/camel-csimple-maven-plugin removed] +| ⚠️ Partial +| `csimple(...)` → `simple(...)` automated via `ChangeMethodName` for `Builder`, `BuilderSupport`, `ExpressionClause` and `ExpressionClauseSupport`; `CSimpleExpression` → `SimpleExpression` via `ChangeType`; `<csimple>` → `<simple>` in XML DSL (gated on a Camel XML document) and `csimple:` → `simple:` in YAML DSL (gated on a Camel YAML DSL document); `camel-csimple-joor` dependency and `camel-csimple-maven-plugin` build plugin removed. `ChangeMethodName` does not rewrite a `import static [...] + +| https://camel.apache.org/manual/camel-4x-upgrade-guide-4_23.html#_camel_zeebe[camel-zeebe renamed to camel-camunda] +| ⚠️ Partial +| Dependency renamed via `ChangeDependencyGroupIdAndArtifactId` (`camel-zeebe` → `camel-camunda`); `zeebe:` URIs renamed to `camunda:` and the `jobKey` endpoint option renamed to `jobType` via `ChangeComponentUriRecipe`; the 8 literal `CamelZeebe*` header names renamed to `CamelCamunda*` via `RenameHeaders`; `ZeebeConstants` → `CamundaConstants` and the 12 `model` DTO classes migrated via `ChangeType` (`AbstractZeebeResponse` → `AbstractCamundaResponse`, `ZeebeMessage` → `CamundaMessage` [...] + +| https://camel.apache.org/manual/camel-4x-upgrade-guide-4_23.html#_camel_langchain4j_tools[camel-langchain4j-tools module removed] +| ⚠️ Partial +| `camel-langchain4j-tools` dependency removed via `RemoveDependency`, gated on `camel-ai-tool` being present rather than on `camel-langchain4j-tools` itself. This ordering guard matters because `latest.yaml` runs the 4.23 recipe before the 4.22 recipe that migrates `langchain4j-tools:` URIs to `ai-tool:` and adds `camel-ai-tool`: gating removal on `camel-ai-tool` presence means the 4.23 removal simply does not fire until the 4.22 URI migration has completed (in an earlier or the same ru [...] + +| https://camel.apache.org/manual/camel-4x-upgrade-guide-4_23.html#_camel_ibm_cos[camel-ibm-cos: CACHE_CONTROL header value renamed] +| ✅ Full +| `CamelIBMCOSContentControl` → `CamelIBMCOSCacheControl` automated via the 4.18.3 `RenameHeaders` custom recipe (gated on `camel-ibm-cos`); existing `IBMCOSConstants.CACHE_CONTROL` usages need no change + +| https://camel.apache.org/manual/camel-4x-upgrade-guide-4_23.html#_camel_headersmap[camel-headersmap removed] +| ✅ Full +| Automated removal of `org.apache.camel:camel-headersmap` dependency (only discovered via `META-INF/services`; Camel falls back to its default headers map factory automatically). Direct uses of `FastHeadersMapFactory` need manual removal. + +| https://camel.apache.org/manual/camel-4x-upgrade-guide-4_23.html#_camel_reactive_executor_vertx[camel-reactive-executor-vertx removed] +| ✅ Full +| Automated removal of `org.apache.camel:camel-reactive-executor-vertx` dependency (only discovered via `META-INF/services`; Camel falls back to its default reactive executor automatically). Direct uses of `VertXReactiveExecutor` need manual removal. + +| https://camel.apache.org/manual/camel-4x-upgrade-guide-4_23.html#_camel_threadpoolfactory_vertx[camel-threadpoolfactory-vertx removed] +| ✅ Full +| Automated removal of `org.apache.camel:camel-threadpoolfactory-vertx` dependency (only discovered via `META-INF/services`; Camel falls back to its default thread pool factory automatically). Direct uses of `VertXThreadPoolFactory` need manual removal. + +| Components removed with no replacement: camel-digitalocean, camel-iec60870, camel-irc, camel-ironmq, camel-json-patch, camel-leveldb, camel-splunk (and their Spring Boot starters) +| ❌ None +| Deliberately not automated: removing the dependency would turn a clear build-time failure into a runtime "no component found" error. `splunk` → `splunk-hec` is not a drop-in replacement (producer-only, different options). + +| `MemoryIdempotentRepository` / `MemoryAggregationRepository` deprecated +| ❌ None +| Not automated: `memoryIdempotentRepository()` is an LRU cache capped at 1000 entries, while the suggested `MemoryKeyValueRepository` replacement is an unbounded `ConcurrentHashMap` with optional TTL — a mechanical swap would be a memory leak. + +| camel-tika: `tikaConfig`/`tikaConfigUri` removed +| ❌ None +| The configuration format moves from XML to JSON; not a mechanical rewrite. + +| camel-langchain4j: `transportType=sse` removed +| ❌ None +| `http` needs a server that supports streamable HTTP, usually at a different URL; not mechanical. + +| camel-openai: embeddings/audio full-response properties moved +| ❌ None +| Rewriting these would require matching each property read to its corresponding upstream operation. + +| camel-platform-http `proxy*` paths, camel-infinispan `CamelInfinispanOperationResult`, camel-tensorflow-serving headers +| ❌ None +| Deprecations with no mechanical equivalent. + +| Security defaults flipped (knative/grpc/mina/cxf `muteException`, mllp `logPhi`, sql `allowQueryFromHeader`/`allowTemplateFromHeader`, pgp `requireIntegrityProtection`, jetty/platform-http-vertx CORS credentials, as2 `asyncMdnAllowedHosts`, netty/jgroups/spring-redis deserialization filters, knative `ssl.trust.all`, docling/smooks/dynamic-router/exec/xpath, and the Spring Boot jolokia bind address, observability-services, debug JMX connector, vault fail-closed, lenient configuration bi [...] +| ❌ None +| Deliberately not automated: a recipe restoring any of these old values would silently undo a security hardening. + +| camel-jasypt-starter default algorithm +| ❌ None +| Pinning `PBEWithMD5AndDES` would keep old ciphertext working but locks in weak crypto; needs manual review. + +| Model accessors `Boolean` → `String` (`ParamDefinition.setRequired`, `RouteTemplateParameterDefinition.setRequired`, `ProcessorDefinition`/`CircuitBreakerDefinition`/`FailoverLoadBalancerDefinition.setInheritErrorHandler`), camel-catalog-lucene removal +| ❌ None +| Not implemented in this release; left for a follow-up (low usage of direct model-building code, and low risk if left as-is since these are deprecated overloads, not removed ones). + +| Behaviour or tooling only, nothing to rewrite: context reload, Avro trusted packages, CamelEvent JSON, consoles, groovy, javascript, URI normalization, pollEnrich/HTTP header placeholders, XmlConverter, staticSourceDir, a2a, ai-observability, archetypes, hazelcast, jbang/TUI/MCP renames, mail, oauth, netty-http, remote-file jail, salesforce plugin, keycloak, thrift, shiro, lra, microprofile-health, pqc, infinispan recovery, qdrant, vertx-http, servlet/jetty whitelist, BackgroundTask, c [...] +| ❌ None +| No code-level change to automate. + +|=== + +NOTE: At the time these recipes were written, Camel 4.23.0 (and the new `camel-camunda` / `camel-camunda-starter` / `camel-ai-tool-starter` artifact versions it introduces) had not yet been published to Maven Central. Recipe logic and its tests are verified correct in isolation; the handful of test assertions that depend on actually resolving a `4.23.0` artifact (a Maven-parser warning comment, or the trailing `UpgradeDependencyVersion` step silently declining to bump to an unresolvable [...] + == 4.22.0 === Summary
