Apache Camel 4.x Upgrade Guide

This document is for helping you upgrade your Apache Camel application from Camel 4.x to 4.y. For example, if you are upgrading Camel 4.0 to 4.2, then you should follow the guides from both 4.0 to 4.1 and 4.1 to 4.2.

The Camel Upgrade Recipes project provides automated assistance for some common migration tasks. Note that manual migration is still required. See the documentation page for details.

Upgrading Camel 4.18 to 4.19

camel-bom

The camel-test module has been removed from camel-bom. This module was included by mistake, as since Camel 4, this is not a JAR but a pom.xml file. Camel end users should use the camel-test-junit5 / camel-test-junit6 JARs and the others directly.

camel-cloud (Removal)

The camel-cloud module and the serviceCall EIP have been removed. These were deprecated in Camel 3.19 and 4.7. The camel-service component has also been removed.

The cloud integration from the following components has been removed: camel-consul, camel-dns, camel-http, camel-jetty, camel-kubernetes, camel-netty-http, and camel-zookeeper.

camel-core

The WireTap EIP has removed the pattern option from its model (not in use) as wiretap always uses InOnly pattern.

Removed 2 deprecated methods in Java DSL for throttler EIP.

Saga EIP

The Saga EIP has fixed the model for how to configure completion and compensation URIs.

For Java DSL there is no changes, but XML and YAML DSL is affected. Here the <compensation> and <completion> tags has been changed to be an attribute on <saga> instead as shown below:

Before:

<route>
    <from uri="direct:start"/>
    <saga sagaService="mySagaService">
        <compensation uri="mock:compensation"/>
        <completion uri="mock:completion"/>
        <option key="myOptionKey">
            <constant>myOptionValue</constant>
        </option>
        <option key="myOptionKey2">
            <constant>myOptionValue2</constant>
        </option>
    </saga>
    <choice>
        <when>
            <simple>${body} == 'fail'</simple>
            <throwException exceptionType="java.lang.RuntimeException" message="fail"/>
        </when>
    </choice>
    <to uri="mock:end"/>
</route>

In YAML DSL the changes are even simpler as the endpoint is moved from uri to the value of completion or compensation.

- route:
    from:
      uri: direct:start
      steps:
        - saga:
            sagaService: mySagaService
            compensation:
              uri: mock:compensation
            completion:
              uri: mock:completion
            key: myOptionKey2
        - choice:
            when:
              - expression:
                  simple:
                    expression: "${body} == 'fail'"
                steps:
                  - throwException:
                      message: fail
                      exceptionType: java.lang.RuntimeException
        - to:
            uri: mock:end

After:

<route>
    <from uri="direct:start"/>
    <saga sagaService="mySagaService" compensation="mock:compensation" completion="mock:completion">
        <option key="myOptionKey">
            <constant>myOptionValue</constant>
        </option>
        <option key="myOptionKey2">
            <constant>myOptionValue2</constant>
        </option>
    </saga>
    <choice>
        <when>
            <simple>${body} == 'fail'</simple>
            <throwException exceptionType="java.lang.RuntimeException" message="fail"/>
        </when>
    </choice>
    <to uri="mock:end"/>
</route>
- route:
    from:
      uri: direct:start
      steps:
        - saga:
            sagaService: mySagaService
            compensation: mock:compensation
            completion: mock:completion
            key: myOptionKey2
        - choice:
            when:
              - expression:
                  simple:
                    expression: "${body} == 'fail'"
                steps:
                  - throwException:
                      message: fail
                      exceptionType: java.lang.RuntimeException
        - to:
            uri: mock:end

camel-simple

In the simple language then init blocks syntax has changed to require that each variable ends with a semicolon and new line (no trailing comments etc is allowed)

For example

    - setBody:
        simple:
          expression: |-
            $init{
              // this is a java like comment
              $sum := ${sum(${header.lines},100)}

              $sku := ${iif(${body} contains 'Camel',123,999)}
            }init$
            orderId=$sku,total=$sum

Should be changed to have semicolons as shown below:

    - setBody:
        simple:
          expression: |-
            $init{
              // this is a java like comment
              $sum := ${sum(${header.lines},100)};

              $sku := ${iif(${body} contains 'Camel',123,999)};
            }init$
            orderId=$sku,total=$sum

camel-test-infra

The test infrastructure modules no longer produce test-jar artifacts. All classes (service interfaces, container implementations, JUnit extensions, and service factories) are now packaged in the regular JAR artifact.

If your project depends on camel-test-infra-* modules with <type>test-jar</type>, remove the <type> element:

Before:

<dependency>
    <groupId>org.apache.camel</groupId>
    <artifactId>camel-test-infra-kafka</artifactId>
    <version>${camel.version}</version>
    <type>test-jar</type>
    <scope>test</scope>
</dependency>

After:

<dependency>
    <groupId>org.apache.camel</groupId>
    <artifactId>camel-test-infra-kafka</artifactId>
    <version>${camel.version}</version>
    <scope>test</scope>
</dependency>

This applies to all camel-test-infra-* artifacts, including camel-test-infra-common.

camel-yaml-io / camel-xml-io

In the YAML DSL we have renamed routePolicy to routePolicyRef on the route node, as that is the correct name.

When dumping routes in YAML or XML format via camel-yaml-io or camel-xml-io then the structure of routes and all the EIP options now respect the intended order in the model.

For example id is always first, and the following attributes are ordered so the most commonly used at in the top. EIPs such as circuitBreaker now has onFallback last.

This order is also the same order that UI builders like Camel Karavan and Kaoto do as well.

camel-jbang

Support for exporting to use Gradle as build tool has been removed (it was deprecated and not working well) The deprecated options buildToool and gradleWrapper has been removed.

camel-kafka

The Kafka client library has been upgraded from 3.9.1 to 4.2.0. This is a major version upgrade of Apache Kafka with several notable changes:

  • The default value of lingerMs (producer linger.ms) has been changed from 0 to 5 to align with the Kafka 4.x default. This improves batching efficiency as larger batches typically result in similar or lower producer latency.

  • Two new consumer configuration options have been added:

    • groupProtocol — Controls which consumer group protocol to use. Valid values are classic (default) and consumer. Setting this to consumer enables the new KIP-848 consumer rebalance protocol which provides faster and more efficient rebalancing.

    • groupRemoteAssignor — The name of the server-side assignor to use when groupProtocol is set to consumer. If not specified, the group coordinator will use the default assignor configured on the broker.

  • If you had explicitly configured the partitioner option to use org.apache.kafka.clients.producer.internals.DefaultPartitioner or org.apache.kafka.clients.producer.UniformStickyPartitioner, you must remove that configuration as these classes have been removed in Kafka 4.0. The built-in default partitioner (used when no partitioner is set) continues to work.

camel-google-pubsub-lite

The camel-google-pubsub-lite component has been removed. The component was deprecated in Camel 4.10 following Google Cloud Platform’s deprecation of the underlying Pub/Sub Lite service.

Google recommends migrating your Pub/Sub Lite workloads to either:

  • Google Cloud Pub/Sub → use the camel-google-pubsub component

  • Google Cloud Managed Service for Apache Kafka → use the camel-kafka component

camel-json-patch

The camel-json-patch is now deprecated - the library it uses is not active maintained and this module does not work with Jackon 3.

camel-mail

When configured a custom IdempotentRepository on camel-mail endpoint, then Camel will now auto-start the bean which is similar to what camel-file do as well.

camel-nitrite (Removal)

The camel-nitrite is removed in this version. It was deprecated in 4.10.