I have a project that its main part (e.g. main.jar) depends on libraries (e.g. u1.jar, u2.jar etc) that has been created as distinct separate projects.
So one could reuse the library elsewhere i.e. there is no dependency between the utility libraries and the main part.
The main part has dependencies on the libraries of course but this is ok.
Now I need to add a specific functionality in one of the libraries.
The needed functionality is already implemented.
It is implemented via a spring bean and the user can configure how the implementation will behave at runtime.
The spring application context is created and used only via the main project and so I do not have access to the spring context
from the utility libraries.
The problem is that I would like to reuse this implementation (and not duplicate the code) and it is not possible to move that part elsewhere
What comes to mind is to create a dependency in this specific util jar to refer to the main.jar.
I will do this to be able to have access to the spring context from the utility jar as well.
What concerns me is that now, I have a cyclic dependency between main.jar and util.jar.
I.e. main.jar already depends on util.jar and now I will create a reverse dependecy as well.
Is this a good idea to do it? Or am I into trouble (class loading issues etc)?
Is there a nice approach for these kind of issues?
Thanks
create an interface and let util.jar work with interface with main.jar passing the implementation which simply wraps this context?
cyclic dependency looks like a nightmare. Which one will you build first?
Once you see that you have cyclic dependency, you know that you have something wrong in the design. Have you thought about if you can apply the Observer Pattern ? Or try to read this one about Acyclic Relationships
Related
In my project i have dependencies displaytag and birt-runtime. And here display tag needs itext-2.0.1.jar and birt-runtime needs itext-2.1.7.jar so how can i declare this in my pom.xml to use itext-2.0.1.jar only by displaytag and use itext-2.1.7.jar only by birt-runtime. could some one let me know how to achieve this?
Thanks in advance.
In normal java application this is not possible, because in the application itext 2.1 and 2.0 will share the same classloader.
But normally, java-apis take care about backward-compatibility, so it should be possible to include only 2.1.
If not, you need multiple classloaders and then it will become complicated.
Existing solutions:
You could try to add an OSGi container to your application and run
both dependencies as a separate osgi-bundle.
If you run a jboss
application server, you could create one module with displaytag and
another one with birt-runtime.
DIY:
I've never done this but you could try to create to manage your own classloaders in your application and load the dependent jars into each own classloader. This article seems to cover the topic.
Short answer: you can't.
Long answer: Maven is a build tool and has no effect on runtime class loading in your application. Normally what it generates is one (or more) artifact(s), tipically jar or war files that may or may not contain your project's dependencies (depending on your POM files).
What you want to achieve is done at runtime by class loaders but under normal circumstances you don't want to tamper with class loading.
What you could do is:
Exclude unnecessary transitive dependencies of a dependency in your pom by defining exclusions, this way only one version of itext would be used. Of course, this only works if your dependencies don't rely on the internals of itext and their public API's are compatible but this might be the cleanest and easiest solution.
Use a framework/container that has stronger control over class loading, such as an OSGi container. These container provide bundles (somewhat equivalent to artifacts) with "private" class loaders enabling your application having multiple versions of the same library loaded that don't interfere with each other. This solution, however, has other disadvantages and I would only recommend this if you're already familiar with OSGi.
We have a situation where some of our dependencies have conflicting dependencies.
We depend on A & B.
A dependes on version a of X.
B depends on version b of X.
Are there any dependency management tools that handle this type of a situation. I feel as if I had heard about some dependency management tool that dynamically loaded the dependencies or something. It seemed like it avoided ever running into a situation like above. I think you could specify somehow which version of X to load at a given instant or something.
Is it possible to do something like that? Is there any way in the code you can load and unload the dependency on a need basis?
I have forgotten most of compiler theory. And I haven't dealt much with dependency management. So excuse any ignorance showing through. It's probably genuine!
You can use OSGi or some other framework that manages multiple class-loaders so that the conflicting versions don't end up in the same class loader.
You can try to do the same thing yourself on a small scale by creating class loaders.
You can use the maven-shade-plugin to rename the packages in one or more copies to avoid the conflict.
So I'm writing a bunch of components (that will be packaged as JARs), and they are all using Guice for DI. These components are just reusable, "commons"-type JARs that will be used by other downstream projects.
My understanding with Guice is that you implement a concrete Module and use that to bind objects together and, in effect, configure all of your DI. It is also my understanding that you should then have a single "bootstrapping" phase where the Guice injector is created, and then all dependencies the module is configured with are then fetched from that injector with injector.getInstance(SomeClass.class).
That would work great in standalone application, that had some entry point, where you could invoke an init()-style method to then bootstrap Guice with, but in a headless JAR that has no entry point, I'm struggling with trying to determine when/where/how to bootstrap Guice.
These will be JARs living on the classpath and, at any point in time, an external entity could invoke and class and any method inside of them. I thought about using up a "lazy initialization" set up, where a method checks to see if its dependencies have been configured yet, and, if so, kicks off a bootstrap method.
But that's a really terrible solution! Partly, because that would require every class to have its own Module (which is ridiculous), and it would also pollute my entire codebase with DI-related code.
I'm clearly missing some Guice fundamentals here, otherwise I don't see how Guice could be used in anything other than an app where execution from start to finished is known and controlled. Any code samples are a huge plus! Thanks in advance.
If other code wants to configure your classes without using Guice, it should be able to. However, you should provide a Guice module which binds everything in a reasonable way so that other code (perhaps other modules) can install your module, and then inject the dependencies into their own classes.
Of course, you don't need to expose a module yourself at all - you can leave it up to others to perform all the binding. However, you may wish to provide a module to avoid exposing your implementation details - you can expose a public interface and a public module, but then keep the implementation package-private. The module can bind the interface to the implementation without the caller knowing anything about it.
You may also want to investigate private modules, so that you can bind dependencies that your code needs, without exposing them more widely.
Something, somewhere is going to have to create an injector - but if your code is just "library" code, then it almost certainly shouldn't be you. You shouldn't be performing the injection yourself - you should just be making your code amenable to injection.
I am writing an application that will ship in several different versions (initially around 10 variations of the code base will exist, and will need to be maintained). Of course, 98% or so of the code will be the same amongst the different systems, and it makes sense to keep the code base intact.
My question is - what would be the preferred way to do this? If I for instance have a class (MyClass) that is different in some versions (MyClassDifferent), and that class is referenced at a couple of places. I would like for that reference to change depending on what version of the application I am compiling, rather than having to split all the classes referring to MyClassDifferent too. Preprocessor macros would be nice, but they bloat the code and afaik there are only proof of concept implementations available?
I am considering something like a factory-pattern, coupled with a configuration file for each application. Does anyone have any tips or pointers?
You are on the right track: Factory patterns, configuration etc.
You could also put the system specific features in separate jar files and then you would only need to include the appropriate jar alongside your core jar file.
I'd second your factory approach and you should have a closer look at maven or ant (depending on what you are using).
You can deploy the different configuration files that determine which classes are used based on parameters/profiles.
Preprocessor makros like C/C++ have are not available directly for java. Although maybe it's possible to emulate this via build scripts. But I'd not go down that road. My suggestion is stick with the factory approach.
fortunately you have several options
1) ServiceLoader (builtin in java6) put your API class like MyClass in a jar, the compile your application against this API. Then put a separate implementation of MyClass in a separate jar with /META-INF/services/com.foo.MyClass. . Then you can maintain several version of your application simply keeping a "distribution" of jars. Your "main" class is just a bunch of ServiceLoader calls
2) same architecture of 1) but replacing META-INF services with Spring or Guice config
3) OSGI
4) your solution
Look up the AbstractFactory design pattern, "Dependency Injection", and "Inversion of Control". Martin Fowler writes about these here.
Briefly, you ship JAR files with all the needed components. For each service point that can be customized, you define an Interface for the service. Then you write one or more implementations of that Interface. To create a service object, you ask an AbstractFactory for it, eg:
AbstractFactory factory = new AbstractFactory();
...
ServiceXYZ s = factory.newServiceXYZ();
s.doThis();
s.doThat();
Inside your AbstractFactory you construct the appropriate ServiceXYZ object using the Java reflection method Class.classForName(), and SomeClassObject.newInstance(). (Doing it this way means you don't have to have the ServiceXYZ class in the jar files unless it makes sense. You can also build the objects normally.)
The actual class names are read in from a properties file unique to each site.
You can roll your own solution easily enough, or use a framework like Spring, Guice, or Pico.
I often read about dependency injection and I did research on google and I understand in theory what it can do and how it works, but I'd like to see an actual code base using it (Java/guice would be preferred).
Can anyone point me to an open source project, where I can see, how it's really used? I think browsing the code and seeing the whole setup shows me more than the ususal snippets in the introduction articles you find around the web. Thanks in advance!
The Wave Protocol Server is my favourite example app.
I struggled a bit with this exact issue. It's so abstract and simple I was always worried I was "doing it wrong".
I've had been using it in the main project which has dependencies on other projects because the Guice module which sets the bindings was part of the main project.
I finally realized the libraries should be supplying the Modules themselves. At that point you can depend only on an instance of a Module (not a specific one), and the interfaces that are bound by it.
Taking it one step better, you can use the new ServiceLoader mechanism in Java 6 to automatically locate and install all Guice modules available on the classpath. Then you can swap in dependencies just by changing class path (db-real.jar vs. db-mock.jar).
I understand you're in Java-land, but in the .NET space the are several open-source apps written using an inversion of control container. Check out CodeCampServer, in which the UI module doesn't have a reference to the dependency resolution module. There is an HttpModule that does the work. (an HttpModule is just a external library you can plug in that handles events in ASP.NET, in CodeCampServer the UI project loads this DependencyRegistrarModule at run time, without any compile time reference to it.)
I think dependency injection has a way of disappearing from view if used properly, it will be just a way of initializing/wiring your application -- if it looks more fancy than that you are probably looking at extra features of the framework at hand, and not at the bare-bones dependency injection.
Edit: I'd recommend actually starting to use it instead of trying to find examples, and then come back and post questions here if you can't get stuff to work like you'd think it should :-)