My requirement is to deploy war files into OSGI at runtime.
For to achieve that I am trying through below codes:
BundleContext bundlecontext = FrameworkUtil.getBundle(this.getClass()).getBundleContext();
Bundle b = bundlecontext.installBundle("file:" + "./war/testwar.war");
b.start();
But I am unable to achieve that, by using the above codes.
As I am new to OSGI I have very less idea of OSGi.
So I need help on this to achieve.
OSGi runtime is not an application server but environment that manages modules (bundles). A war is not (usually) an OSGi bundle and can not be installed the way you do it.
There are many different ways to achieve what you want and it's hard to suggest something. Here are some of the them:
Convert the WAR to WAB (Web Application Bundle). This way you can install it into any OSGi runtime. You would also need to install other bundles that can handle web requests (HTTP Whiteboard implementation for example)
Use an OSGi based product that can automatically convert wars to bundles. Liferay Portal does that but it may be too much to learn it if all you want is to run one app.
If you tagged the question with apache-karaf because that is your environment, then have a look at War deployer. That feature will allow you to install war files in Karaf. If you want to do it from code, you can have a look at the code of that feature and follow the same approach.
Related
I'm currently working on an ebanking platform, so out customers are banks. To extend this platform, we develop our own 'xDK' (development kit) for 3rd party developers (usually the banks themselves).
When xDK is used as a dependency (via maven or gradle), it brings along a lot of transitive dependencies in order to work (~25MB). I was trying to think of solutions to make the dependency a bit lighter to use (given that it needs all of its dependencies) which in turn will promote having smaller, more focused services (not exactly micro-services but at least a step closer).
The current situation's benefit is that every service/project can use its own version of xDK and it doesn't have to update until it needs to. The problem is that it doesn't scale. If we assume 100 WAR files having xDK as a dependency, we create a 2.5GB overhead on the application server (even if they all use the same version).
I'll list two options I was thinking of, but I'd like to know if there are better solutions for this problem. Feel free to ask for more info. Thanks in advance.
Similar to JavaEE components (JPA, JAX-RS, ...), we'll have an 'api' dependency and the implementation. The projects will only declare the 'api' as a provided dependency while the implementation will be provided like so:
JBoss module
I haven't worked with other application servers. We (and our customers) only use JBoss EAP, so this might be a JBoss specific solution. We can create a JBoss module for xDK and then make every deployment depend on it via the JBoss deployment descriptor. The benefit is that we get rid of the multiple copies of the library, but we lose on version flexibility. This would mean that there needs to be some kind of governance on which version of xDK you code against in your service. Also, every time there is a breaking change, we'd need to update all services if we want to update the JBoss module to the latest version.
Bundle in an EAR
EARs allow multiple WAR files in them and also jars as libs. xDK will be an EAR dependency. Again, we have the same pros and cons as the previous solution. This solution is JBoss independent. However, it needs an extra build step to collect all the projects and bundle them, which might be annoying for out customers if they need to bundle their own services.
How about using the maven dependency scope of provided to declare that for the individual war files the jar file is provided outside of the war file, and then have another mechanism to inject the shared jar file into the application server?
c.f. https://maven.apache.org/guides/introduction/introduction-to-dependency-mechanism.html
I need to run the service outside my eclipse. I have taken my OSGi bundles as jars. I need to up the service of the bundles one by one and access the methods in it. I am trying to use Karaf to do this process. Can anyone tell me a better way to do so?
If you have them as osgi bundles, why don't you just deploy them to karaf?
Do some implemented OSGi frameworks allow me to bundle css styles and javascript as well?
Or i have to use other approaches to do this?
One way is to create a WAB (Web Application Bundle), it's a war with OSGi manifest which needs a Web-ContextPath attribute, this doesn't necessarily be a war it may also be a jar with a war like structure.
Might want to take a look at the Pax Web Framework (or Karaf wich uses it).
The Pax Web framework provides all that is needed to deploy Servlets/JSPs resources etc. also in a OSGi manner. Yes also as Services via a Whiteboard approach. Another point is Servlet 3 and CDI, all of this is also supported by Pax Web (for CDI you'll also need Pax CDI)
Best take a look at the various samples and the integration tests.
You can have any resource in a jar. This is not the question of OSGi framework, but the question of the technology you would like to use. How will it find the resource in your jar.
E.g.: If you create a WAB, that behaves similar to a WAR.
Although WABs can be used with several OSGi based web server, I personally do not like them as they are monoholitic. There are alternatives to provide resources:
https://github.com/bndtools/aQute/tree/master/aQute.webserver
An implementation by Peter Kriens that allows us to download any files that are placed into the /static/ folder of any bundle. The Servlet is registered on the /static/ path so if you have a file in your bundle at /static/css/mystyle.css, you can access it via http://foo.com/static/css/mystyle.css
https://github.com/everit-org/webresource
Similar solution but this is based on bundle capabilities. The first release is expected in the end of October 2014, but the important logic is already implemented. This library needs OSGi 6.0 and Java 8 since the latest commit that might be a limitation for a while.
JSPs are other question. If you use a WAB and an embedded Servlet container with JSP support, they should work. You can also register the JSP servlet manually into your OSGi container based on the technology you use (e.g.: with whiteboard pattern).
Amdatu has support for this in the Web Resources component. You simply add your static resources to the bundle using the -Include-Resource bnd header and add a few manifest headers to serve the files directly.
An example of this could be the following. This example can be found in the Amdatu Chat example.
Include-Resource: \
app=dist/app
X-Web-Resource-Default-Page: index.html
X-Web-Resource-Version: 1.1
X-Web-Resource: /chat;app
We often have Custom Mediators (Java classes) that are performing transformations or other things. Each time we want to change only one little thing inside the class, we need to restart the whole WSO2 ESB.
May the "custom mediator" approach is wrong, but we'd like to keep the java classes, but de-coupled from the whole server - like proxies or endpoints. (Our classes are inside a .jar in /components/lib)
How can a custom mediator or java class added to the WSO2 ESB without restarting?
<class name="my.domain.MyJavaClassThatMustBeUpdatedWithoutRestart"/>
You can create an osgi bundle from your class and then you can control the classes behavior from the OSGI Console. You need to start esb with -DosgiConsole option. You can find more information from this blog post.
http://lalajisureshika.blogspot.co.uk/2013/03/some-useful-osgi-commands-to-find.html
While starting up we make OSGI bundles out of the non-OSGI jars in components/libs.
So you must restart if you want to change the custom mediator jars.
As per the below coment explaining the answer,
WSO2 Products are running on an OSGI based platform. So if you change an OSGI bundle you can restart the bundle from the OSGI Console without restarting the whole server. Also the OSGI Container used by WSO2 is Eclipse Equinox OSGI Container. It provides the ability to add non-OSGI jars to product with the feature of, converting those jars in to OSGI Bundles. And that feature works only at the server startup. So if you want to add/change those jars you should restart the server. In runtime you can change OSGI bundles, but you can not convert non-OSGI bundeles to OSGI in runtime.
Usually we start/stop bundles via OSGI console, but for web application, how to do that once it's deployed in a container ?
Regards,
Setya
Also not sure if I got you right, but anyway:
I think it depends on how you deploy a OSGi web application. The only way I already did was that I ran Tomcat within the OSGi context. Then Tomcat scans for bundles with a ".war" ending, so its basically started as soon as it's deployed and you can control it normally via the OSGi console
not sure If I got you right, but...
Mostly applications are started just after deployment(war or eclipse)... you don't need to do anything.
but in case you want to you can do exactly the same thing you do to bundles... go to the web console of your chosen AS and start it there.
Depends what you're using - please update question with container/framework details.
Otherwise, using Karaf you may simply SSH into the framework's shell and execute commands as normal.
Another alternative would be to use WebConsole from Apache Felix - this gives you a lot of control wrt bundles (you can even upload to deploy), and also gives you an embedded shell. It's quite extensible, you can write plugins to create new tabs etc. (AFAIK this will run fine in any framework).