I have a Spring-boot Camel application that receives HTTP requests and has to put them on an ActiveMQ.
I am using Maven to handle my dependencies, but I have a problem with the Camel-ActiveMQ component.
When using camel I am trying to keep the versions of different components the same. So far version 2.24.2 was working fine until I wanted to add a route with an ActiveMQ endpoint. There is no Camel-ActiveMQ 2.24.2 version in the Maven repositories that I am looking in.
I can not find a version of the Camel-ActiveMQ artifact that matches my other camel-components.
Some links to the components that I am using:
- Camel-ActiveMQ
- Camel-HTTP4
- Camel-Spring-Boot-Starter
I have tried using mixed versions of Camel Components (e.g. 2.24.2 for all components but 3.0.0-RC1 for ActiveMQ). This causes class loading exceptions on runtime due to multiple versions of classes being available.
I have found a versions that exist for the rest of my components and Camel-ActiveMQ (3.0.0-M1) but this again gives classloading exceptions when running the applications
Where can I find compatible versions?
Reading further I found the following in the Camel-ActiveMQ documentation:
SPRING BOOT AUTO-CONFIGURATION
When using Spring Boot make sure to use the following Maven dependency to have support for auto configuration:
<dependency>
<groupId>org.apache.camel</groupId>
<artifactId>camel-activemq-starter</artifactId>
<version>x.x.x</version>
<!-- use the same version as your Camel core version -->
</dependency>
There is no 2.24.2 version available, but running with 3.0.0-M1 seems to work. Seems that the Camel-Spring-Boot functionality is kinda new, and will force me to use a 3.x version of camel.
Related
I'm using jsonrpc4j library to handle my jsonrpc api. After migrating to new release of SpringBoot 3.0.0 it builds, but fails on run with an error of RemoteExporter:
ERROR 22396 --- [ main] o.s.boot.SpringApplication : Application run failed
java.lang.NoClassDefFoundError: org/springframework/remoting/support/RemoteExporter
as jsonrpc4j uses it in it.
The reason seems to me in a version of Spring Context which comes with SpringBoot 3.0.0 dependency. org.springframework.remoting package is lack of .support package in that version.
Is there any way to avoid the issue?
It looks like org.springframework.remoting was removed in Spring 6 (see Drop RPC-style remoting: Hessian, HTTP Invoker, JMS Invoker, JAX-WS #27422). In Spring 5.3, the subclasses of RemoteExporter are marked deprecated (see Deprecate remoting technologies support #25379), but interestingly enough, RemoteExporter itself wasn't marked as such, but it has been removed anyway. You'll need to find a replacement library or ask the developers of jsonrpc4j to provide a version which supports Spring 6/Spring Boot 3.
I am using the answer here to implement authentication on a jax-rs REST endpoint running on WebSphere Application Server.
Eclipse is telling me that it can't find #NameBinding anywhere in the classpath.
pom:
<dependency>
<groupId>javax.ws.rs</groupId>
<artifactId>jsr311-api</artifactId>
<version>1.0</version>
</dependency>
As I understand it, I can't use a different version of JSR because WAS 8.5.5 only supports JAX-RS 1.1 (see WAS API Docs and the JSR Specification it links to
I now understand that NameBinding is not available in the 3.11 spec; so what's my alternative?
You can bring your own JAX-RS 2.0 API and implementation and configure your application to use that. Two major steps:
Disable the JAX-RS engine in WAS: https://www.ibm.com/docs/en/was/8.5.5?topic=djrwa-disabling-jax-rs-runtime-environment (the most important part there is setting the JVM custom property com.ibm.websphere.jaxrs.server.DisableIBMJAXRSEngine to true).
Put your desired API and implementation jars in a shared library, select the option to use an isolated class loader for the library (so it loads its own classes in preference to the server's), and associate that shared library with the server.
With that configuration, the server will avoid starting its own JAX-RS component or processing JAX-RS annotations, and the application will get its JAX-RS API and implementation classes from the shared library.
We have recently upgraded Camel version in our application from 2.20.2 to 3.11.2. Hawtio web console used to show some Camel related details with Camel 2.20.2 which are missing after the upgrade to 3.11.2. After doing some analysis, I found that Hawtio is trying to access some MBeans which Camel used to expose before, but not now after the upgrade.
MBean not available
I just want to check if Hawtio is compatible with Camel 3.x or not, or is there anything else that I'm missing.
Currently we are using:
Camel 3.11.2 with Spring DSL
Hawtio 2.13.0
You are probably missing one dependency.
Here is the full list of mines - ok probably too much as components are included in this list, but you will also find some basic one (like "camel-base-engine-3.9.0.jar").
camel-api-3.9.0.jar
camel-base-3.9.0.jar
camel-base-engine-3.9.0.jar
camel-bean-3.9.0.jar
camel-bindy-3.9.0.jar
camel-catalog-3.9.0.jar
camel-cdi-3.9.0.jar
camel-core-3.9.0.jar
camel-core-catalog-3.9.0.jar
camel-core-engine-3.9.0.jar
camel-core-languages-3.9.0.jar
camel-core-model-3.9.0.jar
camel-core-processor-3.9.0.jar
camel-core-reifier-3.9.0.jar
camel-core-xml-3.9.0.jar
camel-csv-3.9.0.jar
camel-direct-3.9.0.jar
camel-directvm-3.9.0.jar
camel-file-3.9.0.jar
camel-ftp-3.9.0.jar
camel-health-3.9.0.jar
camel-http-3.9.0.jar
camel-http-base-3.9.0.jar
camel-http-common-3.9.0.jar
camel-jackson-3.9.0.jar
camel-jaxb-3.9.0.jar
camel-json-validator-3.9.0.jar
camel-jsonpath-3.9.0.jar
camel-jta-3.9.0.jar
camel-log-3.9.0.jar
camel-main-3.9.0.jar
camel-management-3.9.0.jar
camel-management-api-3.9.0.jar
camel-microprofile-config-3.9.0.jar
camel-microprofile-health-3.9.0.jar
camel-microprofile-metrics-3.9.0.jar
camel-mock-3.9.0.jar
camel-seda-3.9.0.jar
camel-sjms-3.9.0.jar
camel-sjms2-3.9.0.jar
camel-support-3.9.0.jar
camel-timer-3.9.0.jar
camel-util-3.9.0.jar
camel-xml-jaxb-3.9.0.jar
camel-xml-jaxp-3.9.0.jar
camel-xpath-3.9.0.jar
today I faced following problem:
One of my core dependencies unfortunately pulls servlet.api to my classpath. Because of this, my spring-boot thinks I'm automatically a server, while I'm a desktop app, and does not want to start without some factories needed to web.
This is what it says:
Caused by: org.springframework.context.ApplicationContextException: Unable to start ServletWebServerApplicationContext due to missing ServletWebServerFactory bean.
Unfortunately I can't get rid of this dependency, and for them to fix their transitive dependencies will probably take some time.
Is there any hack to walk around this?
Thanks
If you're using Spring boot 2.x, you can disable the web application by setting the spring.main.web-application-type property to none:
spring.main.web-application-type=none
If you're using Spring boot 1.x, you could set the spring.main.web-environment property:
spring.main.web-environment=false
The reason this changed is because Spring boot 2.x can now be configured to be either reactive, servlet-based or none, while in Spring boot 1.x it was either servlet-based or none (so it could be just a boolean).
Alternatively, you can also use a custom SpringApplication instance as mentioned by the documentation (and in the comments):
public static void main(String[] args) {
new SpringApplicationBuilder(Application.class)
.web(WebApplicationType.NONE) // Use this for Spring boot 2.x
.web(false) // Use this for Spring boot 1.x
.run(args);
}
Not all Spring applications have to be web applications (or web services). If you want to execute some code in a main method but also bootstrap a Spring application to set up the infrastructure to use, you can use the SpringApplication features of Spring Boot. A SpringApplication changes its ApplicationContext class, depending on whether it thinks it needs a web application or not. The first thing you can do to help it is to leave server-related dependencies (e.g. servlet API) off the classpath. If you cannot do that (for example, you run two applications from the same code base) then you can explicitly call setWebApplicationType(WebApplicationType.NONE) on your SpringApplication instance or set the applicationContextClass property (through the Java API or with external properties).
You are missing some required JAR file to run it as web application. Please make sure to that you have included spring-boot-starter-web.jar file.
If we are using maven, do it as follows.
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<version>1.3.2.RELEASE</version>
</dependency>
Is there any development mode in Spring like in Struts. In Struts if we set dev mode to true all the configuration files are loaded in every request. However now when I'm developing in Spring MVC, I have to restart server after every change. Or is there some other method by which I can force reload.
No there is no such configuration for Spring MVC. But it is a good idea for an feature request.
Answering both of your questions and keeping it short.
No, there is nothing like a devmode in Spring framework so you can throw it out of your head.
Yes, you could skip reloading by using some bytecode manipulation techniques. You can use either:
external tool (like JRebel or Javaleon)
server with hot deployment (like Jetty)
IDE (some IDEs offer such functionalities as well)
Hope that helps.
What change you refer to? Template changes?
Even with struts, JSP and velocity templates shouldn't reload the servlet container. Only Java classes would do that.
I have written a blog post Spring-mvc + Velocity + DCEVM about how to use Spring + Velocity + Dynamic Code Evolution VM (DCEVM) in order to not restart the server when developing:
Yes: If you are using Tomcat or a derivative (VMWare vFabric tc Server), you can configure application reload behavior (hot deploy). This allows changes to say a method to be reloaded without restart. The key is to set:
Publishing set to Automatically publish when resources change
Your web module set to Auto Reload disabled.
VMWare vFabric tc Server 2.6+ (packaged with STS 2.9+) provides two options:
Java Agent-based reloading
JMX-based reloading
If you are using Spring Boot, then all you need to do is add the dependency devtools to your project. This allow you to have your application deployed each time you modify a classpath file.
maven
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<optional>true</optional>
</dependency>
</dependencies>
Gradle:
dependencies {
compileOnly("org.springframework.boot:spring-boot-devtools")
}
Spring docs: Spring boot devtools