clarification about EAR project structure and maven - jsf

it's been a while now and still there are several things that are not clear to me.
Lets start with the basics: what I need to do.
I'm building a web application that manipulate some data, do some computation and give the user an output. There will be also a standalone version, with some simplifications.
So I thought this is the right time to use EAR packaging structure and EJB. I've created with netbeans a basic j2ee ear project with maven support:
All of them have their own pom.xml.
For what i understand, the first one is just a wrapper, the second one is the "real" project that doesn't contain source code, but encapsulate the other two.
In the web project I put all of the web stuff plus jsf backing beans. In the ejb one I was planning to put my data model with all the required annotations, and that comprehend also JPA and JAXB. There should be also some additional classes: a facade class, or session bean, that allow me basic data manipulation with the database, and some classes that contain my business logic strictly related to my data.
Question: is it correct to put all this things into an EJB project? Why not a simple project that the web module depends on?
Moving forward: the web project. First things is, netbeans doesn't put the EJB project dependency into its pom. So I can't see my beans from here. Is that correct or I have to manually add the SRA-ejb into the pom as a dependency?
Secondly, using some netbeans macro, like the ones that generate session beans from entity, or CRUD jsf pages from entities, it looks like he try to generate and put session beans here, in the web project. I think they fits better in the ejb one. What do you think?
One last question: in my stand alone application I was planning to use just the ejb module. But I think I have to carry with me an EJB container, am I right?

it's been a while now and still there are several things that are not
clear to me.
I know that feeling for sure :D
All of them have their own pom.xml. For what i understand, the first
one is just a wrapper, the second one is the "real" project that
doesn't contain source code, but encapsulate the other two.
Correct, it doesn't contain any sourcecode but can contain XML files for declarations and a common lib folder which contains shared libraries of the web and EJB projects.
In the web project I put all of the web stuff plus jsf backing beans.
In the ejb one I was planning to put my data model with all the
required annotations, and that comprehend also JPA and JAXB. There
should be also some additional classes: a facade class, or session
bean, that allow me basic data manipulation with the database, and
some classes that contain my business logic strictly related to my
data.
Question: is it correct to put all this things into an EJB project?
Why not a simple project that the web module depends on?
I don't know what you mean with a "simple project", if you mean just a plain JAR file with classes: an EJB module is nearly the same plus a deployment descriptor which invokes scanning of the annotations.
Moving forward: the web project. First things is, netbeans doesn't put
the EJB project dependency into its pom. So I can't see my beans from
here. Is that correct or I have to manually add the SRA-ejb into the
pom as a dependency?
Yes, in your case you need this dependency. You web project depends on your "service".
Secondly, using some netbeans macro, like the ones that generate
session beans from entity, or CRUD jsf pages from entities, it looks
like he try to generate and put session beans here, in the web
project. I think they fits better in the ejb one. What do you think?
I think it makes more sense to put them in the EJB project because they come from the javax.ejb.* package and belong to the EJB layer. You can put them in the we project, but then you don't really need an EAR and you can use a normal web project like you did before.
One last question: in my stand alone application I was planning to use
just the ejb module. But I think I have to carry with me an EJB
container, am I right?
No, you don't need an EJB container. You can lookup your EJBs via JNDI but you'll need an EJB with a remote interface and a copy of this interface in your standalone client.
You can find some tutorials about that here:
EJB invocations from a remote client using JNDI (JBoss)
How do I access a Remote EJB component from a stand-alone java client? (GlassFish)
GlassFish Project - Simple EJB 3.0 Stateless Session Bean Example
See also:
Maven2: Best practice for Enterprise Project (EAR file)
EAR package structure
Maven structure and Java EE applications

Related

Purpose of jsf-api.jar and jsf-impl.jar [duplicate]

I have started studying JSF and I would like to know what is the JAR to include within our classpath to start using JSF. Is it jsf-api or jsf-impl? Or we have to include both? And if it is both then why they are not merged?
I'll assume that you're not using a real Java EE application server like WildFly, TomEE, Payara, etc, but a barebones JSP/Servlet container like Tomcat which indeed doesn't ship with JSF out the box and you thus had to manually install it. Otherwise, all this fuss with JARs is unnecessary.
Is it jsf-api or jsf-impl? Or we have to include both?
You need both. The jsf-api.jar contains the API, which exist of almost only abstract classes and interfaces. It are the javax.faces.* types which you are importing and using in your code. The jsf-impl.jar contains the implementation, which exist of the real hard working code. The implementation is internally loaded via factories in API. It are the com.sun.faces.* classes which you are not supposed to import and use directly in your code. If you do, then you wouldn't be able to switch to a different JSF implementation, such as MyFaces.
And if it is both then why they are not merged?
There exist a merged JAR, the javax.faces.jar. You can pick this one instead of the two loose JARs.
See also:
Our JSF wiki page
JSF implementations and component libraries
Difference between Mojarra and MyFaces
In simplest terms, what is a factory?
How to properly install and configure JSF libraries via Maven?

Multiple faces-config.xml

My scenario is this:
I have a template with some base code for my application. This template has some custom renderers and some beans in the faces-config.xml file.
Then I have my application that inherits the base code from the template and this application has some additional beans. And everytime I refresh from the template I need to manually add the "local" application beans into faces-config.xml.
Is there a way to have multiple faces-config.xml files or is there another way to fix this problem?
This sounds like a perfect use case for an OSGi plugin: shared features applied to an application that, in turn, has its own custom behavior. An XSP Library supports multiple faces-config files because there's an explicit method for declaring which files to load. An NSF, on the other hand, assumes it contributes only one of its own.

How to modularize an Enterprise Application with OSGi and EE6?

I know that there are already some questions related to this topic but I couldn't find a real solution yet.
Currently I am developing applications with EE6, using JPA, CDI, JSF. I would like to take a more modular approach than packaging everything into a WAR or EAR and deploy the whole thing on an Application Server.
I am trying to design my applications as modular as possible by separating a module into 3 maven projects:
API - Contains the interfaces for (stateless) services
Model - Contains the JPA Entities for the specific module
Impl - Contains the implementation of the API, mostly CDI beans
The view logic of every module is currently bundeled within a big web project, which is ugly. I already thought of web fragmets, but if I spread my bean classes and xhtml files in jar files, I would have to implement a hook so that the resources could be looked up by a parent web application. This kind of solution would at least enable me to have a fourth project per module that would contain all the view logic related to the module, which is a good start.
What I want is not only that I can have those 4 kinds of projects, but also that every project is hot swappable. This led me to OSGi, which was at first really cool until I realized that the EE6 technologies are not very well supported within an OSGi Container.
JPA
Let's look at JPA first. There are some tutorials[1] around that explain how to make a JPA enabled OSGi Bundle, but none of these tutorials shows how to spread entities into different bundles(the model project of a module). I would want to have for example three different modules
Core
User
Blog
The model project of the blog module has a (compile-time)dependency on the model project of user.
The model project of the user module has a (compile-time)dependency on the model project of core.
How can I make JPA work in such a scenario without having to create a Persistence Unit for each model project of a module? I want one persistence unit that is aware of all entities available at runtime. The model projects in which the entities are should of course be hot swappable. Maybe I will need to make a separate project for every client that imports all the needed entities of the projects and contains a persistence.xml that includes all necessary configuration things. Are there any available maven plugins for building such a projects or even other approaches to solve that issue?
CDI
CDI is very nice. I really love it and I don't want to miss it any more! I use CDI extensions like MyFaces CODI and DeltaSpike which are awesome!
I inject my (stateless) services into other services or into the view layer which is just great. Since my services are stateless it should not be a problem to use them as OSGi Services, but what about CDI integration in OSGi? I found a glassfish CDI Extension[2] that would the injection of OSGi Services into CDI beans, but I also want may OSGi Services to be CDI beans. I am not totally sure how to achive that, probably I would have to use the BeanManager to instantiate the implementations and then register every implementation for its interface in the ServiceRegistry within a BundleActivator. Is there any standard way for doing that? I would like to avoid any (compile-time)dependencies to the OSGi framework.
I would also like to use my services just like I use them right now, without changing anything(implementations not annotated and injection points not qualified).
There is a JBoss Weld extension/sub project[3] that seems to target that issue but it seems to be inactive, i can't find any best practices or how-tos.
How can I leave my implementation as it is but still be able to use OSGi? I mean it would not be a big deal to add an annotation to the implementations since every implementation is already annotated with a stereotype annotation, anyway I would like to prevent that.
JSF
As mentioned before I would like to be able to spread my view logic module wise. As far as I know this is not really possible out of the box. Pax Web[4] should solve that somehow, but I am not familiar with it.
I would like to have a project "CoreWeb" in the module "core" that contains a Facelet template, let's call it "template.xhtml". A JSF page in a project called "BlogWeb" in the module "blog" should then be able to reference that template and apply a composition.
To be able to extend the view I would introduce a java interface "Extension" that can be implemented by a specific class of a module. A controller for a view would then inject all implementations of the extension. An extension would for example provide a list of subviews that will be included into a main view.
The described extension mechanism can be implemented easily, but the following requirements must be fulfilled:
When adding new OSGi Bundles to the application server, the set of available extensions might change, the extensions must be available for the controller of the view.
The subviews(from a separate bundle) which should be included into a main view should be accessible.
The concept of a single host but multiple slice applications of Spring Slices[5] is very interesting, but seems limited to Spring DM Server and the project also seems to be inactive.
Summary
After all the examples and behaviors I described I hope that you know what I would like to achive. It's simply an EE6 App that is very dynamic and modularized.
What I look for at the end is at least documentation on how to get everything running as I would expect it or even better an already working solution!
[1] http://jaxenter.com/tutorial-using-jpa-in-an-osgi-environment-36661.html
[2] https://blogs.oracle.com/sivakumart/entry/typesafe_injection_of_dynamic_osgi
[3] http://www.slideshare.net/TrevorReznik/weldosgi-injecting-easiness-in-osgi
[4] http://team.ops4j.org/wiki//display/paxweb/Pax+Web
[5] https://jira.springsource.org/browse/SLICE
To answer some of your questions, using a single persistence unit but spreading your entities across multiple bundles is not recommended, but may occasionally work. However, if your entities are so closely related that they need to share a persistence unit, splitting them across modules may not make sense. Also, don't forget you can handle compile-time dependencies by separating the implementation and interface for each entity - interface and implementation need not be in the same bundle.
For dependency injection, you may like Blueprint.
Several implementations are available and most application servers with enterprise OSGi support support Blueprint out of the box. It uses XML to add metadata, so classes themselves won't need any modification.

Define backing bean in one JSF app into another JSF app

I have an EAR which will contain multiple JSF 1.2 + RF 3.3.(0/3) WARs.
The requirement is that I need to invoke a method in one WAR from another WAR. Its sure that both of them are JSF applications.
So is it possible to declare a bean in one WAR into faces-config of another WAR but both WARs residing in one EAR?
Or is there a better alternative for this work?
========edit======================================================
Or to make the problem more simple/complex : another scenario why this question came up is,
I am trying to invoke one application screen from another app.
Ex : Invoking app is invoke.war and invoked app is target.war .
If I directly access target.war it has 1st screen which process the data and moves to second screen.
But If I have to invoke target.war from invoke.war, I already process the data (in invoke.war) and so want to go directly to second screen, so that target.war does not have to process again.
For this I thought of above approach :)
No, it is not possible to directly call methods in a backing bean in another WAR. Here are a few alternative approaches:
Expose the methods in the "other WAR" using something like Remote EJBs or SOAP/REST services.
Store the data in a cache that is visible to both WARs. If you use JBoss, then JBoss Cache could meet your needs.
Enable session-sharing, and store the data in the session. Not all app servers support this; I know WebSphere does.

JSF in jetty-equinox, Cannot find Bean classes in other bundles

I have problems running JSF in an OSGi environment. I am using jetty web container and equinox to provide the OSGi functionality. The structure of my application is as follows:
The first bundle has all the JSF libs, web.xml and a config.xml. It looks as the following:
bundle1
----src/main/java
-------de/package
----------Activator.java
----------JSFResolver.java
----src/main/resource
------ WebContent
----------META-INF
-------------face-config.xml
-------------web.xhtml
----------start.xhtml
-----------include.xhtml
----libs (containing all JSF required Jars)
The structure of the second bundle is as follows:
bundle2
---src/main/java
------de/package
----------Bean.java
---src/main/resource
------META-INF
---------face-config.xml
------WebContent
---------index.xhtml
When running the application of equinox, the bundle1 is the main bundle where all the browser requests are sent to. In the second bundle, the index.xhtml file can be retrieved the by first bundle upon request. The index.xhtml in bundle 2 gets its values and properties from the 'Bean.java' in bundle 2. The problem comes when i request the 'index.xhtml', the Bean.java class is not found. I think this is because the class loader of bundle1 cannot find it, it has no knowledge of it. So i would like to ask if anyone knows how to solve this problem. If so please do assist me, i have tried all the possibilities i had..
Is it in fact possible to have JSF run on multiple bundles using the same FaceletsContex? Can i be able to have seperate faces-config.xml files in each bundle, which can all be connected other faces-config.xml in other bundles? Can anyone please provide me a solution. Sample code would help.
If any one is interested in the answer, in this case, the faces-config.xml is of no use. So i had to use the plug-in.xml file to register all my beans across all plug-in projects. I created an extension point in the main plug-in, which other plug-ins could register their Beans as extension. I had to override the managedBean class of JSF for it to be able to read the bean properties from extension point rather than from the faces-config.xml.
So during runtime, the application reads all extensions registered in the managedBeans extension point, and then creates all the required bean instances from all plug-ins. Therefore the error will no longer be there. If anyone wants to implement JSF in such a structure, you should know that almost all the functionality in the faces-config.xml will have to be moved to the plug-in.xml of the plug-ins, this includes the navigation rules aswell. One has to do alot of customizations but at the end, you get a nice modular JSF application running on equinox, without having to embed it in a .WAR file.. which seems to be very advantageoous.

Resources