What I know till now:
Instance of Servlet is first created by container via reflection and no argument constructor gets used.
Then parameterized init method gets called.
Also it is suggested that we should not create a constructor in servlet class as it is of no use. And I agree with that.
Lets say, I have created a no argument constructor in servlet class and from within that I am calling a parameterized constructor. My question is, will it be called by the container?
public class DemoServlet extends HttpServlet{
public DemoServlet() {
this(1);
}
public DemoServlet(int someParam) {
//Do something with parameter
}
}
Will DemoServlet() be called by the container and if we put some initializing stuff inside it, it will be executed? My guess is yes but it's just a guess based on my understanding.
This might be pretty useless, I am asking out of curiosity.
DemoServlet() will be called (as you are overriding the defined no-arg constructor in HttpServlet (which is a no-op constructor).
However the other DemoServlet(int arg) will not be called.
You are correct with your guess. DemoServlet() would be called by the container and any initialization code within it would be executed - even if that initialization is done through constructor-chaining And as a matter of fact this is a good way to have dependency injection and create a thread-safe servlet which is testable Typically it would be written this way
public class DemoServlet extends HttpServlet
{
private final someParam; //someParam is final once set cannot be changed
//default constructor called by the runtime.
public DemoServlet()
{
//constructor-chained to the paramaterized constructor
this(1);
}
//observe carefully that this paramaterized constructor has only
//package-level visibility. This is useful for being invoked through your
// unit and functional tests which would typically reside within the same
//package. Would also allow your test code to inject required values to
//verify behavior while testing.
DemoServlet(int someParam)
{
this.param = param
}
//... Other class code...
}
Related
I need to write a test for this class. I need to verify that when the size of the list is exactly 2 then the modelService.save is called. Is it also possible to get to the object productModel?
I don't know where to start.
public class SoldMaterialPrepareInterceptor implements PrepareInterceptor<SoldMaterialModel> {
#Resource
private ModelService modelService;
#Override
public void onPrepare(SoldMaterialModel soldMaterialModel, InterceptorContext interceptorContext) throws InterceptorException {
setSAPSubstance(soldMaterialModel);
}
private void setSAPSubstance(SoldMaterialModel soldMaterialModel) {
ProductModel productModel = soldMaterialModel.getBaseProduct();
Set superCatagoriesList = [....]// gets the list somehow
if (superCatagoriesList.size() == 2) {
productModel.setSupercategories(superCatagoriesList);
modelService.save(productModel);
}
}
}
It is not a problem that the modelService field is private, it is a class field for which private access modifier is usually expected. You need to check the invocation of its save() method, which in turn cannot be private, otherwise it would not be possible to call it from the interceptor class.
As for the test, assuming the superCatagoriesList (which is actually a Set and not a List and also should be generic) gets its content directly or indirectly (e.g. through productModel) from the soldMaterialModel parameter, your task is to write a test, which populates soldMaterialModel with such values so that superCatagoriesList.size() will be 2, and then you can verify that the modelService.save() method was called exactly once with e.g. something like
Mockito.verify(modelService).save(any(ProductModel.class));
I found that when it is difficult to test a method most often there is a design problem of the code I am testing. I suggest a minor to refactoring first: move setSAPSubstance to SoldMaterialModel class and make it public. That is where that method needs to be (see feature envy). Of course modelService.save(productModel); will stay in the interceptor and it will be called only if needed.
Then you will only have to test the two public methods
Is that the whole class? Then I think I see the issue. There are no non-private ways to set the ModelService. When the whole app runs, the dependency injection framework uses reflection to set the ModelService. When you run the test, you don't have anyway to inject a mock. You have a few options.
You can add a constructor to SoldMaterialPrepareInterceptor which takes the ModelService as a parameter. Then you can use that in your test. You would probably also have to add a no-argument constructor because that's how your dependency injection framework creates it. Better yet, you could figure out how to configure the framework to use the new constructor that takes the ModelService.
public class SoldMaterialPrepareInterceptor {
// Public constructor if needed for dependency injection
public SoldMaterialPrepareInterceptor () { }
// If just used for test use protected or package private
// If used with dependency injection, use public.
protected SoldMaterialPrepareInterceptor(ModelService modelService){
this.modelService = modelService
}
The test class is usually in the same package as the actual class, so package private or protected scope is enough. Then the test looks something like this (Assuming Mockito and Junit. Logically, Spock and other frameworks would be similar):
ModelService modelService = Mockito.mock(ModelService.class);
SoldMaterialPrepareInterceptor interceptor = new SoldMaterialPrepareInterceptor(modelService);
// setup SoldMaterialModel and InterceptorContext
interceptor.onPrepare(soldMaterialModel, interceptorContext);
Mockito.verify(modelService, Mockito.times(0)).save(soldMaterialModel);
I have a class, which has an Initialize method, which creates a bunch of tables in a database. This class looks like this:
public class MyClass
{
private bool initialized = false;
public void Initialize()
{
if(!initialized)
{
//Install Database tables
initialized = true;
}
}
public void DoSomething()
{
//Some code which depends on the database tables being created
}
public void DoSomethingElse()
{
//Some other code which depends on the database tables being created
}
}
The two methods DoSomething and DoSomethingElse need to make sure that the Initialize method has been called before proceeding because they depend on having the tables in the database. I have two choices:
Call the Initialize method in the constructor of the class - this does not seem like a good idea because constructors should now call methods, which are non-trivial and could cause an exception.
Call the Initialize method in each of the two methods - this does not seem like a great solution either especially if there are more than a handful of methods.
Is there a design pattern which could solve this in a more elegant way?
I would use a static factory method in which Initialize is invoked, and make the constructor private, to force use of the static factory method:
public class MyClass
{
private MyClass() { ... }
public static MyClass createInstance() {
MyClass instance = new MyClass();
instance.Initialize();
return instance;
}
}
Also, I would remove the initialized variable - in part because you don't need it any more - but also because it requires some means of guaranteeing visibility (e.g. synchronization, volatile or AtomicBoolean) for thread safety.
I think that Miško Hevery's blog post on (not) doing work in constructors is an interesting read.
I would separate the installation of the database from the definition of tasks that depends on it:
static factory could be used for the database installation as pointed out by #andy-turner
and the repository pattern to do work on the database
I suggest this solution because if i understand correctly, you are concerned about the high number of tasks that depends on the database.
Using the dependency injection pattern the repository can get a reference to the database, so in your bootstrapping code you can execute the database installation once and then inject the reference to the database in all the repositories that depends on it.
I would recommend using a collaborator that does the initialisation. That way MyClass can easily be tested by substituting a mock for the initialiser collaborator. For example:
public class MyClass {
public MyClass(MyClassInitialiser initialiser) {
initialiser.initialize();
}
public void DoSomething() {
//Some code which depends on the database tables being created
}
public void DoSomethingElse() {
//Some other code which depends on the database tables being created
}
}
Or an alternative solution, the idea here is that you're breaking the single responsibility principle in MyClass. There is non-trivial initialisation behaviour (installing database tables) and behaviour on those tables in the same class. So you should separate those responsibilities into two different classes and pass one in as a collaborator to the other.
public class MyClass {
DatabaseCollaborator collaborator;
public MyClass(DatabaseCollaborator collaborator) {
this.collaborator = collaborator;
}
public void DoSomething() {
//Some code which depends on the database tables being created
collaborator.someMethod();
}
public void DoSomethingElse() {
//Some other code which depends on the database tables being created
collaborator.anotherMethod();
}
}
public class DatabaseCollaborator {
DatabaseConfig config;
public DatabaseCollaborator(DatabaseConfig config) {
this.config = config;
}
public void someMethod() {
}
public void anotherMethod() {
}
}
public class DatabaseConfig {
public DatabaseConfig() {
// initialize
}
}
When I want a class whose instances must be initialized exactly once but I want to defer initialization until right before it's necessary (at which point the caller may fail to call an Initialize function, find it inconvenient to do so, or etc.), I do it similar to how you've started out with your code, but I make the initialization method private and name it something like "EnsureInitialized". It uses a flag to track and early exit if initialization has already been done, and all functions which depend on initialization already having happened just call that function as their first line (after argument-checking).
If I expect the caller to control when this instance's initialization is done, I make the method public, name it "Init", track whether it has been run with a flag, handle idempotence or max-run-once inside the Init method however is appropriate for that class, and all methods which depend on Init having already been run will call a different, private method named "AssertIsInitialized" which will throw an exception with text like "Must call init on {class name} instance before using this function".
My goal with these different patterns is to be unambiguous about each method's expectations and operation regarding initialization within the class instance lifecycle, and provide discoverability (of the design or code bugs using it) and automatic behavior (in the case of the self-initializing class in my first paragraph) wherever I think each is most appropriate to what the rest of the application is doing.
I have an abstract class that a child class extends. My abstract class has an #Activate method, so does the child class. When OSGi creates my service, it invokes the child class activate method but never the abstract class's activate. Is there any way to force the abstract class's activate to be called by OSGi rather than having the child class manually call the parent activate method?
Here is some code to help elaborate on what I am asking.
#Component(componentAbstract=true, inherit=true)
#Service(value=ISomeInterface)
public abstract class AbstractHello implements ISomeInterface{
#Activate
public void activate(){
System.out.print("Hello ");
}
}
#Component
#Service(Value=ISomeInterface)
public class World extends AbstractHello{
#Activate
public void activate(){
System.out.println("World!");
}
}
The result of the code above would be "World!", rather than "Hello World!".
Initially I thought maybe the child activate method name was clobbering the abstract activate method of the same name. The result is the same even if the abstract class's activate method is given a unique name. Is there any way to have OSGi call the abstract class's activate method for me?
The DS annotation processors only look at the concrete class decorated with #Component. Super classes are not examined. Since the annotation processing is done at build time, super types may come from imported packages which are not chosen until runtime.
Also, the annotation processor generates component description XML from the annotations. So there can only be one activate="methodName" attribute in the XML. If you need the superclass' method called, then you need to call it from the subclass' method.
This has nothing to do with Apache Felix and OSGi, this is caused by poor understanding of Class Inheritance and Method Overriding in Java.
Your World class extends AbstractHello class and overrides its activate() method. If you want the AbstractHello.activate() method to be called then you must call it in
// Annotations excluded for readability.
public class World extends AbstractHello {
public void activate() {
super.activate();
System.out.println("World!");
}
}
OSGi can't help here.
UPDATE
Since the base class is abstract, and you don't have an instance of it, you can't call its method. Neither can OSGi container.
I'm digging through a web application in an effort to fix some problems. The application uses Tomcat, Jersey and Guice. One of the issues is occurring in a MethodInterceptor used for authorization purposes. Here's the method, trimmed to the relevant part:
public Object invoke(MethodInvocation invoc) throws Throwable {
// ...
//Check that the annotation actually exists
if(! invoc.getMethod().getDeclaringClass().isAnnotationPresent(Tool.class))
{
throw new BaseException("...");
}
// ...
}
Now the problem is that some of the "web-facing" methods are inherited from a parent class without being overridden in the child. If I understand getDeclaringClass() correctly, it will return the parent class in this case, but what we really want here is the child class. Some testing seems to confirm this--if I override the method in the child class everything is fine, but if I don't put in the override the exception is thrown.
So, given a MethodInvocation object, is there a way to trace it back to the "actual" class instantiated, rather than the class where the method was declared? Or is some other approach necessary? Worst-case, I could just annotate each method as necessary rather than annotating the class.
Sorry if this is a long-winded question for an easy answer - my Java is pretty rusty.
Simple enough, needed to use getThis().getClass() on the MethodInvocation instead of getMethod().getDeclaringClass():
if(! invoc.getThis().getClass().isAnnotationPresent(Tool.class))
{
throw new BaseException("...");
}
Although in my case, Guice complicated things a bit by putting in an auto-generated child class (e.g., a class name ending in "$$EnhancerByGuice..." That was fixed by moving one up the tree with getSuperclass():
if(! invoc.getThis().getClass().getSuperclass().isAnnotationPresent(Tool.class))
{
throw new BaseException("...");
}
It looks like that the answer is No. I created simple test to check it:
class Run implements Runnable {
#Override
public void run() {
}
}
class Run2 extends Run{}
Method method = Run2.class.getMethods()[0];
System.out.println(method);
As we can see in debug window method doesn't have any information of class Run2:
I guess it would be better to stick on actual methods with its annotations rather then on actual class instances where these methods get invoked.
I'm trying to unit-test some classes that make use of a Singleton class whose constructor does some things I can't (and shouldn't) do from the unit-test environment. My ideal scenario would be to end up with the constructor completely suppressed and then stub out the other member methods that my test classes invoke. My problem is that I can't seem to get the constructor suppressed.
My understanding of a way to solve this would be something like the following:
public class MySingleton extends AbstractSingletonParent {
public final static MySingleton Only = new MySingleton();
private MySingleton(){
super(someVar); // I want the super-class constructor to not be called
//
//more code I want to avoid
}
public Object stubbedMethod() {}
}
public class ClassToBeTested {
public void SomeMethod(){
Object o = MySingleton.Only.stubbedMethod();
}
}
#RunWith(PowerMockRunner.class)
#PrepareForTest(MySingleton.class)
public class TestClass {
#Test
public void SomeTest() {
suppress(constructor(MySingleton.class));
mockStatic(MySingleton.class);
PowerMock.replay(MySingleton.class);
// invoke ClassToBeTested, etc
PowerMock.verify(MySingleton.class);
//make some assertions
}
}
Unfortunately during the createMock invocation, the MySingleton constructor is hit, and it still calls the super constructor.
Am I doing something silly? I found an example on the web doing almost exactly this, but it was using a deprecated suppressConstructor method. Despite the deprecation I tried that, too, to no avail...
Is what I'm trying to do possible? If so, what am I doing wrong?
*Edited version now works.
You need to annotate TestClass with the #PrepareForTest annotation so it has a chance to manipulate the bytecode of the singletons.
Also, the superclass ctor supression signature should include somevar's class; right now you're just suppressing the default ctor.
See the #PrepareForTest API docs. Here's a blog post with some more details as well.
FWIW, it's working for me:
#RunWith(PowerMockRunner.class)
#PrepareForTest({EvilBase.class, NicerSingleton.class})
public class TestEvil {
#Test
public void testEvil() {
suppress(constructor(EvilBase.class));
assertEquals(69, EvilBase.getInstance().theMethod());
}
#Test
public void testNice() {
suppress(constructor(EvilBase.class));
suppress(constructor(NicerSingleton.class));
assertEquals(42, NicerSingleton.getInstance().theMethod());
}
}
How about you set the instance field ('only' in your code) of your Singleton with an instance instantiated with the constructor you want (you can do all of this with the Reflection API or dp4j).
The motivating example of a dp4j publication discusses that.
I am not sure what is it that you are doing wrong. But on the design side, i can suggest you look into dependency injection i.e. DI.
For making your code testable, make use of DI. With DI you would pass the singleton class as an constructor argument to your test class. And now since you pass an argument, inside your test case you can create a custom implementation of the AbstractSingleton class and your test case should work fine.
With DI, your code will become more testable.