I am fully aware that this might not be a good idea in general, but I am wondering if there is a way to access Weld-internal classes from my deployed application-war.
E.g. org.jboss.weld.resources.ClassTransformer
This is not for a production-app but rather for a side-projected related to testing and loading some CDI beans on the fly and performing proper cleanup.
The code I have is working under Wildfly, but fails with java.lang.NoClassDefFoundError: org.jboss.weld.resources.ClassTransformer. I am certain that the weld implementation/feature has this class.
For sure, this is by design, but I am wondering if there is still a way to achieve it; maybe via configuration to not enforce this strict classloader isolation...
Again, this is only for a very specific testing/development scenario.
Thanks,
Daniel
Related
I'm new to spring 5 and my question is why does spring use DI and IOC? I mean why do we have to write the beans in an XML (legacy) and then create it where we need it? Why don't we use one method instead that gives us that object, until we want to use this complex mechanism that happens in the spring container?
And another question is, does not reading XML slow down the program? Because we are reading from the hard disk anyway.
Note: It is true that we can use annotations, but for now I want to ask a question about reading from xml.
Spring IoC Container is the core of Spring Framework. It creates the objects, configures and assembles their dependencies, manages their entire life cycle. The Container uses Dependency Injection(DI) to manage the components that make up the application. It gets the information about the objects from a configuration file(XML) or Java Code or Java Annotations and Java POJO class. These objects are called Beans. Since the Controlling of Java objects and their lifecycle is not done by the developers, hence the name Inversion Of Control.
More on link HERE
As for your first part of the question.
why does spring use DI
To allow the developer to keep his code loose, and not entagle classes, it keeps your code clean.
In object oriented design, the amount of coupling refers to how much the design of one class depends on the design of another class. In other words, how often do changes in class A force related changes in class B? Tight coupling means the two classes often change together, loose coupling means they are mostly independent. In general, loose coupling is recommended because it's easier to test and maintain.
You may find this paper by Martin Fowler (PDF) helpful.
I mean why do we have to write the beans in an XML (legacy) and then create it where we need it
Note: We write the bean in XML and it is created when application starts when it looks at bean defintion, techinally you are never creating a bean, you are fetching only created bean from Spring Container(IOC) that Spring created for you when you started your application.
We are writing bean blueprint, or just bean, so that it can be constructed, placed in the Spring Container when the application starts, and then we have it at our disposal that we can fetch it using getBean method.
The whole point of "why", is because by default all beans are scoped as singleton, that means, when you fetch a bean, and do with it whatever you want, you do not worry about memory or anything, Spring takes care of the beans for you if they are scoped as a Singleton.
Second question:
And another question is, does not reading XML slow down the program? Because we are reading from the hard disk anyway.
There is no difference in performance between annotation or XML, it is just a different approach, I am not sure what you mean by "reading from hard disk", but one way or another you will have to configure your application, yes, many forums prefer to run away from XML, but in my honest opinion the only reason for that is because when you write a bad configuration in XML it is lot harder to find it compared to configuration in Java that will throw an exception.
XML, application.properties files require a redeployment of the application, while annotation and java configuration require recompilation of your project, so both of them have "flaws", but it is normal and quite understandable to me.
But in the end I believe that it is a matter of preference, I know personally quite a few people that combine annotations with XML configuration and they know lot more about Spring compared to me.
So in summary, it is pain to write beans and their configuration, same as you can write a class with methods without creating an interface for it since the result will be the same, but it will help you in the long run since you do not have to worry about memory or if you destroyed that bean or if you did not.
It would be nice that you read about
1.Lazy initialization of beans
2.Eager initialization of beans
3.Singleton scope of beans
4.Prototype scope of beans
I have read that dependency injection is good for testing, in that a class can be tested without its dependencies, but the question comes to my mind if Class A depends on Class B or C or any class, testing Class A independent of some class is yielding a test result of zero, not a failed or past test.
Class A was created to do something and if it is not fed anything whether using new key word or setting up the extra files in Spring, Class A won't do any work.
About the idea of making code modular, readable and maintainable: so business classes became cleaner, but all we did was shift confusion from dirty Java business classes to convoluted XML files and having to delete interfaces used to inject to our loosened objects.
In short, it seems we have to make edits and changes to a file somewhere,right?
Please feel free to put me in my place if my understanding is lacking, just a little irritated with learning Spring because I see the same amount of work just rearranged.
Dependency injection is good for unit testing because you can individually test each method without that method depending on anything else. That way each unit test can test exactly one method.
I would say that if the xml is what’s annoying you check out Spring boot. It’s based on a java configuration so no xml and it simplifies a lot of configuration for you based on your class path. When I first started spring I found the xml very daunting coming from a java background but the annotation based configuration and the auto configuring done by spring boot is extremely helpful for quickly getting applications working.
IMO biggest advantage of using the spring is dependency injection which makes your life easy. For example if you would like to create a new service with three dependencies, then you can create a class very easily using Spring. But without spring, you will end up writing different factory methods which will return you the instances you are looking for. This makes your code very verbose with static method calls. You may want to take a look at the code repositories before spring era.
Again if you would like to use Spring or not is your personal call based on project complexity. But it's other features/advantages cant be overlooked.
And XML files or Java configs are the ways of achieving spring configuration - where you would like to add your business logic is personal flavour. Only thing is you should be consistent all across your project.
I would suggest that you read Martin Fowler's great article on Inversion of Control and Dependency Injection to gain a better understanding of why frameworks like Spring can be really useful to solve a well known set of common dependency injection problems when writing software.
As others have mentioned, there is no obligation to use Spring; and whatever you can do with Spring, you can probably do it by other means like abstract factories, factory methods, or service locators.
If your project is small enough, then you probably wouldn't mind solving the dependency injection issues on your own using some design patterns like those mentioned above. However, depending on the size of your project, many would prefer to use a framework or a library that already packs a bunch of solutions to these recurrent head scratchers.
In regards to the advantages of dependency injection frameworks when doing unit testing is the idea that you don't need to test the dependencies of your class, but only your class.
For example, most likely your application has a layered design. It is very common to have a data access class or a repository that you use to retrieve data from a datasource. Logically, you also have a class where you use that DAO.
Evidently, you already wrote unit testing for your DAO, and therefore, when you're testing your business class (where the DAO is being used) you don't care about testing your DAO again.
Fortunately, since Spring requires some form of dependency injection for your DAO, this means your class must provide a constructor or a setter method through which we can inject that DAO into our business class, right?
Well, then during unit testing of your business class, you can conveniently use those injection points to inject your own fake DAO (i.e. a mock object). That way, you can focus on the testing of your business class and forget about retesting the DAO again.
Now compare this idea with other solutions you may have done on your own:
You inject the dependency directly by instantiating the DAO within your business class.
You use a static factory method within your code to gain access to the DAO.
You use a static method from a service locator within your code to gain access to the DAO.
None of these solutions would make your code easy to test because there is no simple manner to get in the way of choosing exactly what dependency I want injected into my business class while testing it (e.g. how do you change the static factory method to use a fake DAO for testing purposes?).
So, in Spring, using XML configuration or annotations, you can easily have different dependencies being injected into your service object based on a number of conditions. For example, you may have some configurations for testing that evidently would be different than those used in production. And if you have a staging environment, you may even have different XML configurations of dependencies for your application depending on whether it is running in production or integration environments.
This pluggability of dependencies is the key winning factor here in my opinion.
So, as I was saying, my suggestion to you is that you first expand your understanding of what problems Spring core (and in general all dependency injection frameworks) is trying to solve and why it matters, and that will give you a broader perspective and understanding of these problems in a way that you could to determine when it is a good idea to use Spring and when it is not.
I'm currently working on an OSGi application running under apache Karaf that uses JPA and QueryDSL.
I was wondering if I could use Spring Data with QueryDSL instead of the current approach.
The reason for this is that I find Spring repositories to be quite useful and having a template for NoSQL database accesses might be useful in the future.
I have tried to start a normal spring application without a web context with OSGi but I get a ClassNoutFoundException when it tries to load the applicationContext.xml or the ApplicationContext.class.
I don't want to use Spring DM since it is discontinued.
Basically the sole reason for wanting to try this integration is for the Spring Repositories, but if you think this is not necessary please tell me. Any information regarding how to achive this or if it's ok to persue this would be more than welcome.
Thank you
Update
I've managed to make spring work by starting the application context with org.eclipse.gemini.blueprint.context.support.OsgiBundleXmlApplicationContext. The applicationContext is exported in OSGi as a service and I can get all the beans that I need by calling it.
The problem I'm having right now is that when I declare <jpa:repositories base-package="x.y.z" /> I get the following exception:
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor#0' defined in URL [bundle://251.13:0/META-INF/spring/applicationContext.xml]: Initialization of bean failed; nested exception is java.lang.IllegalStateException: No persistence exception translators found in bean factory. Cannot perform exception translation.
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:527)[185:org.springframework.beans:3.1.4.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:456)[185:org.springframework.beans:3.1.4.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:294)[185:org.springframework.beans:3.1.4.RELEASE]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:225)[185:org.springframework.beans:3.1.4.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:291)[185:org.springframework.beans:3.1.4.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:197)[185:org.springframework.beans:3.1.4.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.getBean(AbstractApplicationContext.java:1109)[187:org.springframework.context:3.1.4.RELEASE]
at org.eclipse.gemini.blueprint.context.support.AbstractDelegatedExecutionApplicationContext.registerBeanPostProcessors(AbstractDelegatedExecutionApplicationContext.java:502)[193:org.eclipse.gemini.blueprint.core:1.0.0.RELEASE]
at org.eclipse.gemini.blueprint.context.support.AbstractDelegatedExecutionApplicationContext.registerBeanPostProcessors(AbstractDelegatedExecutionApplicationContext.java:451)[193:org.eclipse.gemini.blueprint.core:1.0.0.RELEASE]
at org.eclipse.gemini.blueprint.context.support.AbstractDelegatedExecutionApplicationContext$4.run(AbstractDelegatedExecutionApplicationContext.java:306)[193:org.eclipse.gemini.blueprint.core:1.0.0.RELEASE]
at org.eclipse.gemini.blueprint.util.internal.PrivilegedUtils.executeWithCustomTCCL(PrivilegedUtils.java:85)[193:org.eclipse.gemini.blueprint.core:1.0.0.RELEASE]
at org.eclipse.gemini.blueprint.context.support.AbstractDelegatedExecutionApplicationContext.completeRefresh(AbstractDelegatedExecutionApplicationContext.java:290)[193:org.eclipse.gemini.blueprint.core:1.0.0.RELEASE]
at org.eclipse.gemini.blueprint.extender.internal.dependencies.startup.DependencyWaiterApplicationContextExecutor$CompleteRefreshTask.run(DependencyWaiterApplicationContextExecutor.java:137)[194:org.eclipse.gemini.blueprint.extender:1.0.0.RELEASE]
at java.lang.Thread.run(Thread.java:662)[:1.6.0_37]
Caused by: java.lang.IllegalStateException: No persistence exception translators found in bean factory. Cannot perform exception translation.
at org.springframework.dao.support.PersistenceExceptionTranslationInterceptor.detectPersistenceExceptionTranslators(PersistenceExceptionTranslationInterceptor.java:142)[195:org.springframework.transaction:3.1.4.RELEASE]
at org.springframework.dao.support.PersistenceExceptionTranslationInterceptor.<init>(PersistenceExceptionTranslationInterceptor.java:79)[195:org.springframework.transaction:3.1.4.RELEASE]
at org.springframework.dao.annotation.PersistenceExceptionTranslationAdvisor.<init>(PersistenceExceptionTranslationAdvisor.java:70)[195:org.springframework.transaction:3.1.4.RELEASE]
at org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor.setBeanFactory(PersistenceExceptionTranslationPostProcessor.java:103)[195:org.springframework.transaction:3.1.4.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeAwareMethods(AbstractAutowireCapableBeanFactory.java:1475)[185:org.springframework.beans:3.1.4.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1443)[185:org.springframework.beans:3.1.4.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:519)[185:org.springframework.beans:3.1.4.RELEASE]
As a JPA provider I'm using OpenJPA. The entityManagerFactory is a service which I can get by using the blueprint. I think I need to reference it in <jpa:repositories base-package="x.y.z" />, but how do I do that since the applicationContext.xml is read by spring and not the blueprint?
I would really appreciate any hint in the right direction.
Thank you
Use Querydsl-SQL directly in your code and
it will work well within OSGi as it does not use class loading, weaving, enhancing, caching and other tricks that sound really good but causes chaos
your code will run much faster than with any of the "cache-enhanced" JPA engines
others will be able to understand your code (not like JPA Criteria API queries)
you will know exactly what SQL commands run on the Database Server that minimizes problem-solving time
your code will be as database independent as with any ORM tool
Do not use Spring, spring-data, JPA and other monoholitic technologies together with OSGi as
they were designed to work within monoholitic systems where everything is in one application context, not in separate bundles
by using these technologies together with OSGi you will spend most of your time to fix bugs like this and looking for workarounds
People who argue with this, already spent lots of time on finding such workarounds. They managed to implement some business logic. They hope that they now truly found workarounds for every conceptual issue and they do not have to spend the same amount of work next time. They are in a bidding fee auction. Be honest guys! Somewhere deep you know I am right ;-).
I am saying this with the experience that I
tried the perfect stack based on Hibernate and Don't repeat the DAO article of IBM (much before Spring-Data hype began). Twice
wrote hibernate-osgi-adapter for Hibernate 4.1.x
Re-implemented the complete JPA chapter of OSGi Enterprise specification
Well you have a couple of choices here, try to get it to run with blueprint (probably the hardest - since you need to call spring beans, but I think could still be done), use Karaf 3.0.0.RC1 it also supports Blueprint Geminin which does have a tighter support for Spring and last but not least use Spring-DM, even if it is discontinued you are able to use and probable the best approach is to use spring-dm for certain Spring specific parts and std. Blueprint for the rest. Because you just use services through both frameworks everything will work, just don't mix the spring and blueprint descriptors in one bundle.
So this is a rather "big" question, but what I'm trying to accomplish is the following:
I have a Spring application, MVC, JDBC (MySQL) and JSP running on tomcat.
My objective is to test the entire "stack" using a proper method.
What I have so far is Junit using Selenium to simulate an actual user interacting with the application (requires a dummy account for that), and performing different validations such as, see if element is present in the page, see if the database has a specific value or if a value matches the database.
1st concern is that this is actually using the database so it's hard to test certain scenarios. I would really like to be able to mock the database. Have it emulate specific account configs, data states etc
2nd concern is that given the fact that I use what is in the database, and data is continuously changing, it is hard to predict behavior, and therefore properly asserting
I looked at Spring Test but it allows for testing outside a servlet container, so no JSP and no Javascript testing possible.
I saw DBUtils documentation but not sure if it will help me in this case
So, to my fellow developers, I would like to ask for tips to:
Run selenium tests on top of a mocked database
Allow different configs per test
Keep compatibility with Maven/Gradle
I have started with an ordered autowire feature to support this kind of stubbing.
It's basically an idea that i took over from the Seam framework i was working with in the past but i couldnt find yet a similar thing in spring.
The idea is to have a precedence annotation (fw, app,mock,...) that will be used to resolve the current implementation of an autowired bean. This is easy already in xml but not with java config.
So we have our normal repository beans in with app precedence and a test package stubbing these classes with mock precedence.
If both are in the classpath spring would normally fail with a duplicate bean found exception. In our case the extended beanfactory simply takes the bean with the highest precedence.
Im not sure if the order annotation of spring could be used directly but i prefered to have "well defined" precedence scopes anyway, so it will be clear for our developers what this is about.
! While this is a nice approach to stub so beans for testing i would not use it to replace a database definition but rather go with an inmemory database like hsql, like some previous answers mentionned already. !
If you have a library containing Spring beans that need to be wired together before an application can use them, does it make sense to include any sort of bean configuration file in the JAR (such as the /META-INF directory)? The idea is to give the application the option of importing this into its master Spring context configuration.
There may be more than one way to wire these beans, so I could provide a bean configuration file for each of the standard ways in which you'd typically wire them together.
Or, do I force the application to wire these up explicitly?
If it helps, the specifics of my problem involve a library I created to encapsulate our product's persistence layer. It contains Service, DAO and model beans. The DAO implementations currently use Hibernate (this probably won't change). Some of the DAO implementations need different kinds of Strategy beans injected into them (database encryption logic), depending on the type of database we are deploying on (MySQL vs SQL Server, etc). So we have potentially a few different configuration scenarios. I could also provide datasource bean configurations, relying on property substitution at the app level to inject all the particulars needed by the datasource.
Thanks for your input!
In this case, it's a good idea to provide some beans files, either as examples for documentation purposes, or as fully-fledged files ready for including into a wider context.
If your beans' wiring can get complex, then you shouldn't really leave it entirely up to the library client to figure it out.
This is more of a documentation and education task, really.