How to JPA within a JAR? - java

Is it possible to use JPA within plain Java applications resulting in JAR files run locally? I often used the EntityManager and #Entity annotations for web application creation resulting in WAR files and configured the persistence unit for use over databases configured and managed within the Wildfly server. I find this functionality quite convenient and would like to use it outside of an application server environment. Are there working examples to that? Or maybe similar approaches?

Try SpringBoot using JPA, here is a definitive guide by Spring: https://spring.io/guides/gs/accessing-data-jpa/
Using springboot, you can get a single jar file with it's dependencies within it.

Related

Spring Boot library usage in plain Java project

i´m currently working on a Spring Boot jar library for reuseable components like
ldap
email
messaging with apache kafka
rest api usage
Aim:
Every Java "user/coder" of our company should be able to "put" this jar in ones project (by maven or whatever) and use the reusable components instead of coding all things by hand over and over again.
Building microservices for that issue over REST is not an alternative to us.
My question is:
Can i reuse this Spring Boot jar library in any plain Java projects?
Beeing fond, can i "put" this jar library into a Java project and wire my Spring Boot services from that library in my "non Spring Boot" vanilla Java project?
Notice / Edited:
I have used Spring Boot as project template (spring-boot-starter-parent).
I configure my templates like the LdapTemplate by hand and don´t let Spring Boot do the magic.
Edit
As far as the reuse in Spring Boot/Spring projects is concerned, everything is fine. I´ve done that already.
My aim with that library may be that every Java "user" can use this library, like so:
final SuperCoolLibary scl = new SuperCoolLibrary();
final boolean exists = scl.searchForLdapUser("tlang");
So another question maybe:
Would it be better do switch this library to maybe the new Java Jigsaw module infrastructure?
Write your own Spring-Boot-Auto-Starter. A guide can be found under: https://docs.spring.io/spring-boot/docs/current/reference/html/boot-features-developing-auto-configuration.html
This way your library can be used in every spring boot project by just adding it as dependency (which means the jar must be in your classpath).
If your Java Application does not use the SpringContext the services cannot be "wired" by spring into your plain vanilla java application.

How to deploy spring boot web application with configurable properties

After researching i learned that the common way to deploy spring boot web applications is as a war file.However,i have a project i made for a company,now i need to send them the project to try it out and they need to be able to configure the application.properties or to be specific the database location and credentials.so my question is do i need to deploy the project in a different way or is there a way to make the war file application properties modifiable later ?
Did you consider Spring Cloud Config Server
https://cloud.spring.io/spring-cloud-config/multi/multi__spring_cloud_config_server.html.
This is the most elegant way to configure and externalize your properties. If not I would strongly suggest incorporating that component. Plug the config server with your spring boot app without much coding and your application will be much more manageable and extensible.
Spring Boot applications are actually typically packaged as Uber jars with Tomcat embedded. You can accomplish this using spring-boot maven plugin or a similar gradle plugin if need be.
Once in this state the jar can be started normally and you can override configuration properties when invoking it.
java $JAVA_OPTS -Dspring.service.name=my-service -jar /my-service.jar
EDIT: This is not the only way you can solve this problem, and #piy26's answer is an excellent solution for injecting external configuration into an enterprise ready spring boot application. However for the case that your are describing you would need the company to set up there own configuration server, and whats more they will still have to override the configuration server location property so the application will pull properties from their config-server. For your example it seems you need the simplest way to override application properties within the jar.

Spring boot basic

Just started exploring spring boot and trying to understand.....
In a normal project scenario, we create multiple projects / modules depending on functionality. Ultimately, package all different jars , wars in .ear and deploy it.
With spring boot, new project are deployed on a separate of instances of tomcat.
But if all these projects are related, it will need reconciliation of proprty files and any other resources differently utilized, before you create .ear.
While I understand the advantages of spring boot while development, is there any thought on how to make this process better when using spring boot?
Modern cloud architectures are moving away from using property files. Your Ops or DevOps teams should appreciate if your app would accept configurations via system properties. Spring Boot is perfectly suited for that.
Older fashioned orchestrators would replace placeholders in your properties files during deployment phase.

Exclude certain WebApplicationInitializers in CloudFoundry WAR deploy

There's a specific version of this question and a general version; I'll ask it both ways.
Specific Question
We have a traditional Spring Web application that integrates with Apache Camel that we're pushing to Cloud Foundry. It depends on a custom library that pulls in spring-cloud-security (and therefore, spring-boot-autoconfigure, among others). When deploying to Cloud Foundry, the Java Autoreconfiguration looks for WebApplicationInitializers on the classpath and one that it finds is JerseyAutoConfiguration. When it invokes that particular WebApplicationInitializer, we get annotation parsing errors. Is there a way to exclude that one? #EnableAutoConfiguration(exclude=...) doesn't work because this isn't happening during the AutoConfiguration step.
General Question
Is there a way, via web.xml or some other facility, to tell the Java Autoreconfigure code (included via the Java buildpack) to skip executing certain WebApplicationInitializers?
If you deploy the app as an executable instead of as a WAR then there is no scanning for WebApplicationInitializers (it's a Spring thing not a buildpack thing).

Java EE deployment issue

I'm running into some issues in deploying my Java EE application, and could use some advice.
I have 3 components to deploy:
Integration layer (Data): POJOs and CDI Beans - JAR file
Application layer (BL): EJBs, CDI Beans and POJOs - JAR file
Presentation layer: Servlets and such - WAR file
Optimally, I would like to be able to deploy both the integration and application layer JARs in the same Java EE server, but as separate JARs (since I might want to change the hardware configuration later on and separate them into two different servers on two separate machines).
The problem, is that I'm unable to get the CDI injection from the integration layer JAR to the application layer JAR to work. The server says (and probably rightfully so) that it's impossible to resolve the injections.
So far I came up with these possible solutions:
Package the two JARs into a single EAR file (maybe throw in the WAR as well ...), and deploy that
Use JNDI between the different layers (possibly create a CDI producer to do a generic injection based on JNDI names or something like that)
In the integration layer, make the objects being injected into the application layer (the DAOs) EJBs instead of CDI beans
I don't like either of these solutions (especially the last), since they restrict my future deployment options. The second solution does not restrict me, but it might become tedious at some point (when I accumulate a lot of code).
Finally, my question is:
Is there an option I didn't find yet, that would allow me to deploy the two JARs on the same server with the CDI injections working ? Possibly something that would still work if at some point I separate the JARs into different servers ?
Yes, there are other options as well.
Use a java EE container that supports OSGi as well, and use OSGi interface for your deployment dependencies. At least Websphere, Glassfish, JBoss (with jbosgi installed), Jonas support deploying OSGi bundles. This means your modules should be converted into OSGi bundles.
Use a container-specific extension that allows modules to communicate between each other. JBoss as jboss-deployment-structure.xml that you can use to have a dependency to another deployment.
Use a server-provided shared classpath for your dependencies. Wouldn't really recommend this.
My vote would go for OSGi.
None of them will work by themselves however if you deploy packages to different servers. A remote technology like remote EJBs, remote JNDI lookups, Spring remoting, HTTP-based api, CORBA or similar is needed between different servers. In Java EE, EJB is the de-facto standard for this, but Spring remoting is not bad either.
Update: you added that you use TomEE servers. Indeed TomEE won't support the first two options I mentioned. I would use EJB in that case - the fact that you're using EJBs can be abstracted away from the business layer using an EJB delegate, and you could use EJB (stateless session bean) only for the interface part, leaving your DAOs as POJOs.
not sure what your goal is but deploying a war is fine, can even be done manually with these commands:
mkdir -p webapps/myapp/WEB-INF/lib
cp myjar*.jar webapps/myapp/WEB-INF/lib/
If your goal is to be able to split them you can use TomEE skinny war feature.
Create a war with a WEB-INF/jars.txt file.
In this jars.txt put one line by dependency/jar. It can be the path to the jar or maven coordinates.
Once setup it will allow you to change jars one by one then simply restart the server. This is great when several teams work on the same binary.
There are some alternative with TomEE but this one has the advantage to be easy to change to a portable one (war).

Categories