I'm having problems defining configuration for a CDI application (glassfish 4).
I have:
#CacheResult(cacheName = "example")
public String getSomething(String something){
logger.debug("getSomething "+something);
return "this is "+something;
}
This works as expected, the second time is called is not executed because it's cached
However, I want to specify a configuration for my caches. I have tried writing a infinispan.xml file (in src/main/resources), but it's ignored. I have also tried with both:
#Produces
#Default
public Configuration defaultEmbeddedCacheConfiguration() {
return new ConfigurationBuilder().expiration().lifespan(3000l)
.eviction()
.strategy(EvictionStrategy.LRU)
.maxEntries(2)
.build();
}
#Produces
#ApplicationScoped
public EmbeddedCacheManager defaultEmbeddedCacheManager() {
return new DefaultCacheManager(defaultEmbeddedCacheConfiguration());
}
But these methods are never called.
I have also tried with #ConfigureCache
My dependencies are:
<dependency>
<groupId>org.infinispan</groupId>
<artifactId>infinispan-cdi</artifactId>
<version>6.0.2.Final</version>
</dependency>
<dependency>
<groupId>org.infinispan</groupId>
<artifactId>infinispan-jcache</artifactId>
<version>6.0.2.Final</version>
</dependency>
Any ideas?
Thx
Related
Im trying to run Webflux on Tomcat and try to create Sping WebClient with Apache Http Client.
Reference Documentation stated that theres built-in support:
https://docs.spring.io/spring-framework/docs/current/reference/html/web-reactive.html#webflux-client-builder-http-components
private ClientHttpConnector getApacheHttpClient(){
HttpAsyncClientBuilder clientBuilder = HttpAsyncClients.custom();
clientBuilder.setDefaultRequestConfig(RequestConfig.DEFAULT);
CloseableHttpAsyncClient client = clientBuilder.build();
ClientHttpConnector connector = new HttpComponentsClientHttpConnector(client);
return connector;
}
But Springs HttpComponentsClientHttpConnector is not accepting org.apache.http.impl.nio.client.CloseableHttpAsyncClient. It requires org.apache.hc.client5.http.impl.async.CloseableHttpAsyncClient. So there seems to be a package rename and I canĀ“t find a Maven Dependency that has the required class.
Does anybody know the right Maven Dependency for that class. Or how could I make it work?
Apache HTTP Client 5 is a separate artifact. You'll need to add the following dependencies to your pom.xml:
<dependency>
<groupId>org.apache.httpcomponents.client5</groupId>
<artifactId>httpclient5</artifactId>
<version>5.1</version>
</dependency>
<dependency>
<groupId>org.apache.httpcomponents.core5</groupId>
<artifactId>httpcore5-reactive</artifactId>
<version>5.1</version>
</dependency>
import org.apache.hc.client5.http.impl.async.HttpAsyncClients;
import org.springframework.http.client.reactive.HttpComponentsClientHttpConnector;
public class ApacheHttp {
public static void main(String[] args) {
new HttpComponentsClientHttpConnector(HttpAsyncClients.custom().build())
}
}
I defined a pipeline in Apache Beam to consume messages of a given queue in RabbitMQ message broker.
I defined an exchange and routing key in RabbitMQ.
I used AmqpIO.read() in Beam (version 2.9.0) but I did not found any API to set the echange and the routing key.
(Following this doc : https://beam.apache.org/releases/javadoc/2.4.0/org/apache/beam/sdk/io/amqp/AmqpIO.html)
Is there any possibility to do that ? Even with any other plugin.
Regards,
Ali
There is a new (experimental) IO connector for RabbitMQ shipped with the latest v2.9.0 Apache Beam release. The AMQP connector will not work for RabbitMQ.
If you are using Maven add the following dependency in your POM
<!-- Beam MongoDB I/O -->
<dependency>
<groupId>org.apache.beam</groupId>
<artifactId>beam-sdks-java-io-mongodb</artifactId>
<version>2.9.0</version>
</dependency>
and you can use it in a pipeline like
public class RabbitMQPipeline {
final static Logger log = LoggerFactory.getLogger(RabbitMQPipeline.class);
/**
* Mongo Pipeline options.
*/
public interface RabbitMQPipelineOptions extends PipelineOptions {
#Description("Path of the file to read from")
#Default.String("amqp://localhost")
#Required
String getUri();
void setUri(String uri);
}
/**
* #param args
*/
public static void main(String[] args) {
RabbitMQPipelineOptions options = PipelineOptionsFactory.fromArgs(args).withValidation()
.as(RabbitMQPipelineOptions.class);
Pipeline pipeline = Pipeline.create(options);
PCollection<RabbitMqMessage> messages = pipeline
.apply(RabbitMqIO2.read().withUri(options.getUri()).withQueue("test"));
messages.apply(ParDo.of(new DoFn<RabbitMqMessage, String>() {
#ProcessElement
public void process(#Element RabbitMqMessage msg) {
System.out.println(msg.toString());
}
}));
pipeline.run().waitUntilFinish();
}
}
The RabbitMqIO Javadoc has examples of how to use the reader and writer.
A word of caution
There is a known bug that has been fixed but scheduled for release in v2.11.0 that blocks the connector from working even in the simplest scenarios. The fix is really simple (see JIRA issue) but you will need to rebuild a new version of the class. In case you want to give it a try make sure you add the following Maven dependency
<dependency>
<groupId>com.google.auto.value</groupId>
<artifactId>auto-value</artifactId>
<version>1.5.2</version>
<scope>provided</scope>
</dependency>
and add the following configuration in Maven Compiler plugin
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.6.1</version>
<configuration>
<source>1.8</source>
<target>1.8</target>
<annotationProcessors>
<annotationProcessor>com.google.auto.value.processor.AutoValueProcessor</annotationProcessor>
</annotationProcessors>
</configuration>
</plugin>
If you are using Eclipse make sure you install the m2-apt Maven plugin. Good luck!
In my Spring Boot project it seems none of the spring.jackson properties are working. I want to take controll over date fields and I tried to add the following properties to my application.properties file:
spring.jackson.serialization.WRITE_DATES_AS_TIMESTAMPS=false
spring.jackson.date-format=yyyy-MM-dd HH:mm:ss
spring.jackson.joda-date-time-format=yyyy-MM-dd HH:mm:ss
Dates still come as timestamps (java.util.Date and joda.time). I have the following dependencies:
<dependency>
<groupId>com.fasterxml.jackson.datatype</groupId>
<artifactId>jackson-datatype-jdk8</artifactId>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.datatype</groupId>
<artifactId>jackson-datatype-jsr310</artifactId>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.datatype</groupId>
<artifactId>jackson-datatype-joda</artifactId>
</dependency>
I didn't add version number but it says the managed version number is 2.8.7 (with all three).
I've read if I use #EnableWebMvc annotation on any class, it won't work. But I don't use such annotation. (However I have spring-webmvc on my classpath.)
When I start the application (in Tomcat), I got these log messages:
2017-04-23 16:54:55 DEBUG JndiTemplate:150 - Looking up JNDI object with name [java:comp/env/spring.jackson.serialization.WRITE_DATES_AS_TIMESTAMPS]
2017-04-23 16:54:55 DEBUG JndiLocatorDelegate:101 - Converted JNDI name [java:comp/env/spring.jackson.serialization.WRITE_DATES_AS_TIMESTAMPS] not found - trying original name [spring.jackson.serialization.WRITE_DATES_AS_TIMESTAMPS]. javax.naming.NameNotFoundException: Name [spring.jackson.serialization.WRITE_DATES_AS_TIMESTAMPS] is not bound in this Context. Unable to find [spring.jackson.serialization.WRITE_DATES_AS_TIMESTAMPS].
2017-04-23 16:54:55 DEBUG JndiTemplate:150 - Looking up JNDI object with name [spring.jackson.serialization.WRITE_DATES_AS_TIMESTAMPS]
2017-04-23 16:54:55 DEBUG JndiPropertySource:99 - JNDI lookup for name [spring.jackson.serialization.WRITE_DATES_AS_TIMESTAMPS] threw NamingException with message: Name [spring.jackson.serialization.WRITE_DATES_AS_TIMESTAMPS] is not bound in this Context. Unable to find [spring.jackson.serialization.WRITE_DATES_AS_TIMESTAMPS].. Returning null.
2017-04-23 16:54:55 DEBUG PropertySourcesPropertyResolver:151 - Found key 'spring.jackson.serialization.WRITE_DATES_AS_TIMESTAMPS' in [URL [file:C:/Program Files/Apache Software Foundation/Tomcat 9.0/conf/Catalina/localhost/Blowfish/config/application.properties]] with type [String]
Only one thing worked with both java.util.Date and joda.time:
#Configuration
public class AppConfig extends WebMvcConfigurerAdapter{
#Override
public void extendMessageConverters(List<HttpMessageConverter<?>> converters) {
for (HttpMessageConverter<?> converter : converters) {
if (converter instanceof MappingJackson2HttpMessageConverter) {
MappingJackson2HttpMessageConverter jsonMessageConverter = (MappingJackson2HttpMessageConverter) converter;
ObjectMapper objectMapper = jsonMessageConverter.getObjectMapper();
objectMapper.disable(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS);
break;
}
}
}
}
But I don't like this solution, it would be more elegant to use some configuriation in my application.properties.
I use Spring Boot 1.5.2.
I am able to deploy a RESTEasy application working well with Weld (meaning my CDI works) but I am having some trouble with my integration tests. I get this error:
org.jboss.weld.exceptions.DeploymentException:
WELD-001408: Unsatisfied dependencies for type SomeService with qualifiers #Default
while testing:
#RunWith(WeldJUnit4Runner.class)
public class SomeServiceIT {
#Inject
private SomeService service;
#Test
public void test() {
System.out.println(service);
}
}
The last message in my logs is
DEBUG::WELD-000100: Weld initialized. Validating beans
Content of src/test/resources/META-INF/beans.xml:
<beans xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd"
version="1.1" bean-discovery-mode="all">
</beans>
By the way I tried the cdi-unit library and it works, but I need to use my own WeldJUnit4Runner which is currently:
public class WeldJUnit4Runner extends BlockJUnit4ClassRunner {
private final Weld weld;
private final WeldContainer container;
public WeldJUnit4Runner(Class<?> klass) throws InitializationError {
super(klass);
this.weld = new Weld();
this.container = weld.initialize();
}
#Override
protected Object createTest() throws Exception {
return container.instance().select(getTestClass().getJavaClass()).get();
}
}
I use weld-se 2.4.1.Final for testing.
Thanks.
EDIT:
So it seems like Weld only looks into src/test/java (when I copy SomeService over to src/test/java it woks). This is silly, I am not going to duplicate all my classes to test them... How to tell Weld to retrieve classes from src/main/java?
So I was able to make it work by creating src/main/resources/META-INF/beans.xml in addition to the existing src/main/webapp/WEB-INF/beans.xml and src/test/resources/META-INF/beans.xml meaning now I have 3 times the exact same file in the same project which I find silly but I guess this is how it is in the Weld world...
Thanks all for your time.
EDIT:
Actually I am able to deploy the application with only src/main/resources/META-INF/beans.xml (I removed src/main/webapp/WEB-INF/beans.xml)
Sorry, I have no solution, but only a small clue: if you want to do some customizations of the BlockJUnit4ClassRunner - why don't you try to extend the org.jglue.cdiunit.CdiRunner or org.apache.deltaspike.testcontrol.api.junit.CdiTestRunner? Or at least take a look at their source code.
Ps. I always find Weld's class-path scanning brittle & error prone. And try to avoid it as much as possible.
It should work so I post here what I did.
Firstly, I use :
Eclipse Luna
JDK 7
The tree of my project is the following one :
Here are my pom dependencies :
<dependency>
<groupId>javax</groupId>
<artifactId>javaee-api</artifactId>
<version>7.0</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.11</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.jboss.weld.se</groupId>
<artifactId>weld-se-core</artifactId>
<version>2.4.1.Final</version>
<scope>test</scope>
</dependency>
The SomeService interface :
package org.jvi.cdirunner;
public interface SomeService {
void test();
}
The SomeServiceImpl implementation :
package org.jvi.cdirunner;
public class SomeServiceImpl implements SomeService {
#Override
public void test() {
// TODO Auto-generated method stub
}
}
And the test to run :
package org.jvi.cdirunner.test;
import javax.inject.Inject;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.jvi.cdirunner.SomeService;
#RunWith(WeldJUnit4Runner.class)
public class SomeServiceIT {
#Inject
private SomeService service;
#Test
public void test() {
System.out.println(service);
}
}
And everything works fine if I run the test under Eclipse. I can't figure out why it doesn't work on your side.
I am using Glassfish 4.1.1 as my Java server. I am trying to #Inject a simple #Stateless bean in my JAX-RS class having #Path annotation. Here is the exception I am getting:
javax.servlet.ServletException: A MultiException has 1 exceptions. They are:
1. org.glassfish.hk2.api.UnsatisfiedDependencyException: There was no object available for injection at SystemInjecteeImpl(requiredType=MongoCollectionStore,parent=DemoJaxrsApp,qualifiers={},position=-1,optional=false,self=false,unqualified=null,310751270)
Here is my JAX-RS config:
import javax.ws.rs.ApplicationPath;
import javax.ws.rs.core.Application;
#ApplicationPath("/rest")
public class JaxrsAppConfig extends Application {
}
This is how my JAX-RS resource class looks like:
#Path("/tn-collection")
#Produces(MediaType.APPLICATION_JSON)
#Consumes(MediaType.APPLICATION_JSON)
public class DemoJaxrsApp {
#Inject
MongoCollectionStore mongoCollectionStore;
#POST
public List<CollectionTO> getColl() {
return mongoCollectionStore.findAll();
}
}
I am using only 2 dependencies:
<dependency>
<groupId>org.mongodb</groupId>
<artifactId>mongo-java-driver</artifactId>
<version>3.3.0</version>
</dependency>
<dependency>
<groupId>com.google.code.gson</groupId>
<artifactId>gson</artifactId>
<version>2.3.1</version>
</dependency>
It shouldn't be a problem with dependencies. I am not using any xml files (other than POM.xml and nb-configuration.xml, generated by Netbeans 8.1) as Java EE 7 need not have any config files. I don't know what might have going wrong.
Could anybody please help me out with this UnsatisfiedDependencyException problem?
UPDATE:
Here is my MongoCollectionStore Java class:
#Stateless
public class MongoCollectionStore {
public List<CollectionTO> findAll(MongoConfig mongoConfig) {
List<CollectionTO> tuples = new ArrayList<>();
Gson gson = new Gson();
MongoClient mongoClient = new MongoClient("127.0.0.1", 27017);
MongoDatabase mongoDB = mongoClient.getDatabase("Demo");
MongoCollection<Document> coll = mongoDB.getCollection("DemoCollection");
try(MongoCursor<Document> cursor = coll.find().iterator()) {
while (cursor.hasNext()) {
String jsonDoc = cursor.next().toJson();
CollectionTO tuple = gson.fromJson(jsonDoc, CollectionTO.class);
tuples.add(tuple);
}
}
return tuples;
}
}
I was looking through this problem on internet and found that a CDI bean can only be injected into another CDI bean. They both need to be managed by the container. So, I made my DemoJaxrsApp #RequestScoped, in order to make it a CDI bean.
For guys coming here from Google, Original (and more elaborate) answer can be found here:
Inject an EJB into JAX-RS (RESTful service)
One thing I still don't know is that when I #Injected a #Stateless resource inside my #RequestScoped class, was that resource an EJB? Or, was it a CDI bean? I guess, that's a different question altogether.