We have a bunch of classes that listen for events from the server and then respond to them. For example:
class EventManager {
private Set<Event> cache = new HashSet<Event>();
private EventListener eventListener = new EventListener() {
void onEvent(Event e) {
if (e instanceof MyEvent || e instanceof YourEvent) {
handleEvent(e);
}
}
}
public EventManager(ServerCommunication serverComm) {
serverComm.addListener(eventListener);
}
private handleEvent(Event e) {
// handle the event...
// ...
cache.add(cache);
// ...
}
}
Here's a made-up example of the kind of thing we are doing. Here are the problems I see:
I'd like to test handleEvent to make sure it's doing what it is supposed to but I can't because it's private.
I'd also like to check that something got added to the cache too but that also seems difficult since cache is a private member and I don't want to add a needless getter method.
I'd also like to test the code inside the anonymous class's onEvent method.
For now, what I did was move all logic from the anonymous class to the handleEvent method, and I made handleEvent package private (my unit test is in the same package). I'm not checking the contents of the cache although I want to.
Does anyone have any suggestion for a better design that is more testable?
I would probably extract a EventCache component. You can replace this for your test with an implementation that counts the cached events or records whatever is of interest.
I probably would not change the visibility of handleEvent. You could implement a ServerCommunication that just raises the event from the test case.
Well, there are two approaches here: black box and white box.
Black box testing suggests you should only test the publicly visible changes. Does this method have any observable effect? (Some things don't - caches being an obvious example where they improve performance but may otherwise be invisible.) If so, test that. If not, test that it isn't having a negative effect - this may well just be a case of beefing up other tests.
White box testing suggests that maybe you could add a package-level method for the sake of testing, e.g.
Cache getCacheForTesting()
By putting "for testing" in the name, you're making it obvious to everyone that they shouldn't call this from production code. You could use an annotation to indicate the same thing, and perhaps even have some build rules to make sure that nothing from production does call such a method.
This ends up being more brittle - more tied to the implementation - but it does make it easier to test the code thoroughly, IMO. Personally I err on the side of white box testing for unit tests, whereas integration tests should definitely be more black box. Others are rather more dogmatic about only testing the public API.
I assume your EventManager is a singleton, or you have access to the particular instance of the class you're testing.
1 - I suppose you can send events to your class. Your method is private, and nobody else can call it, then sending an event should be enough.
2 - You can access that through reflection, if you really need to. Your test would depend on a particular implementation.
3 - What would you like to test, actually? If you want to be sure that this method is called, you can replace the EventListener with another EventListener object through reflection (and eventually call the onEvent method of the first listener from your new listener). But your question seems to be more about code coverage than actual unit-testing.
Sometimes, when coming across private methods that I want to test... they are simply screaming to be public methods on another object.
If you believe that HandleEvent is worth testing in isolation (and not through onEvent processing), one approach would be to expose HandleEvent as a public method on new/different object.
Use this opportunity to break the code up into smaller more focussed (default access) classes. A test is just another client for the code.
Note that the anonymous inner class' onEvent method is actually accessible, so calling it should not be a problem.
Related
I'm working in a Project with a Service class and some sort of a Client that acts as a facade (don't know if it's the right term in the Design Patterns's world, but I'll try to make myself clear). Service's methods can be very expensive as they may be communicating with one or more databases, long checkings and so on, so every Client method should call one and only one Service method.
Service class structure is something like
public class Service {
public void serviceA(){...}
public SomeObject serviceB(){...}
// can grow in the future
}
And Client should be something like
public class Client {
private Service myService; // Injected somehow
public void callServiceA() {
// some preparation
myService.serviceA();
// something else
}
public boolean callServiceB(){...}
}
And in the test class for Client I want to have something like
public class ClientTest{
private Client client; // Injected or instantiated in #Before method
private Service serviceMock = mock(Service.class);
#Test
public void callServiceA_onlyCallsServiceA() {
client.callServiceA();
????
}
}
In the ???? section I want something like verifyOnly(serviceMock).serviceA() saying "verify that serviceMock.serviceA() was called only once and no other method from the Service class was called". Is there something like that in Mockito or in some other mocking library? I don't want to use verify(serviceMock, never()).serviceXXX() for every method because, as I said, Service class may grow in the future and I will have to be adding verification to every test (not a happy task for me) so I need something more general.
Thanks in advance for your answers.
EDIT #1
The difference between this post and the possible duplicate is that the answer adds boiler plate code which is not desired in my case because it's a very big project and I must add as few code as posible.
Also, verifyNoMoreInteractions can be a good option even when it's discouraged for every test, no extra boiler plate code needed.
To sumarize, the possible duplicate didn't solved my problem.
There's another issue: I'm writing test for code made by another team, not following a TDD proccess myself, so my test should be extra defensive, as stated in this article quoted in the mockito documentation for verifyNoMoreInteractions. The methods I'm testing are often very longs so I need to check that the method under test calls ONLY the necesary services and no other (because they're expensive, as I said). Maybe verifyNoMoreInteractions is good enough for now but I'd like to see something not being discouraged for every test by the very same API creator team!
Hope this helps to clarify my point and the problem. Best regards.
verify(serviceMock, times(1)).serviceA();
verifyNoMoreInteractions(serviceMock);
From Mockito's javadoc on verifyNoMoreInteractions:
You can use this method after you verified your mocks - to make sure that nothing else was invoked on your mocks.
Also:
A word of warning: Some users who did a lot of classic, expect-run-verify mocking tend to use verifyNoMoreInteractions() very often, even in every test method. verifyNoMoreInteractions() is not recommended to use in every test method. verifyNoMoreInteractions() is a handy assertion from the interaction testing toolkit. Use it only when it's relevant. Abusing it leads to overspecified, less maintainable tests.
The only way you can reliably verify that your service is only ever called once and only once from the method you specify and not from any other method, is to test every single method and assert that your serviceA method is never invoked. But you're testing every other method anyway, so this shouldn't be that much of a lift...
// In other test cases...
verify(serviceMock, never()).serviceA();
While this is undesirable from a code writing standpoint, it opens the door to separating out your service into smaller, more responsible chunks so that you guarantee that only one specific service is called. From there, your test cases and guarantees around your code become smaller and more ironclad.
I think what you are looking for is the Mockito.verify and Mockito.times
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
verify(mockObject, atLeast(2)).someMethod("was called at least twice");
verify(mockObject, times(3)).someMethod("was called exactly three times");
Here another thread with the same question:
Mockito: How to verify a method was called only once with exact parameters ignoring calls to other methods?
I have tried doing a search for this but I fear I may not be wording what I want to do very well.
Currently, we have about a hundred action classes in our application with each determining if a user has access to it. I would like to make a class that can figure out the calling method, what permissions are required for it, and if the user has those permissions. Unfortunately, I don't really know how to even get started with this as each class may have slightly different requirements.
I'm happy to add more explanation if needed but as I said, I'm not sure I'm wording what I'm trying to do very well so if anyone has a better way of putting it that gets me some google results or a link to a related question here that's already been answered, I know I'd appreciate it.
current permissions checks look like below. This is a simple implementation, there are usually multiple profile checks in one if block.
If (scc.getUser().getCurrentProfile().getSystemAdmin() != 1) {
logIllegalAccess(log);
break;
}
IMHO the most elegant solution would make use of annotation processing. The idea is that you would annotate action classes with a custom annotation, something like:
#RequiredPermission(Permissions.SYSADM)
class ActionA {
public ActionA newInstance() {
return new ActionA_Gen(new ActionA());
}
private ActionA() {...}
...
}
Action classes would have to have a newInstance() method to be used to create instances instead of calling new. The method would create an instance of a class by the same name with _Gen extension. This class would have one method for each method in the original action class, which would perform a permission check and call the corresponding method in the original class instance that was passed to its constructor.
The _Gen class would be generated by an annotation processor.
Note that by using reflection it might be possible to move the newInstance() method in a common superclass.
So let's say I have a simple activity as follows. Assume all of the the lifecycle events etc. are correctly created there's no exception in creating an activity.
public class ButtonClickActivity extends Activity implements OnClickListener {
... onCreate etc. ...
#Override
public void onClick(View v) {
logInfo();
}
protected void logInfo() {
Log log = new Logger();
log.log('foo');
...
}
}
How exactly would you test that the onClickMethod calls on callMyOtherMethod? How also would you test that logInfo makes a new Logger and .log('foo')? Let's assume you have all frameworks at your disposal.
I've tried to use Robolectric (which is fine for high level testing, but really doesn't seem to let you get down into detail like to test if a method calls another method).
It seems that you have to use that in conjunction with a mocking framework / injection in order to verify at least injected object behavior. It doesn't to be able to test 'new Construction' so you're forced to use a factory always for every single object, even for objects you use from other frameworks etc.
I've given a shot with JMockIt (which allows you to verify every single new construction etc.) but it seems there is a problem there also with ByteCode manipulation and it basically will fail if it tries to rewrite bytecode for Android Activities and Views especially, along with other problems.
So my question for folks is what strategy have they been going with other than 'it's a implementation detail' or 'doesn't need to be tested'? I'm sure of course you don't want to test every little detail method call but letting important method calls go unverified doesn't seem like a good solution either.
So I have an interesting conundrum I was curious to get some feedback from other Webdriver framework architects. Currently I follow a pretty standard execution model:
baseobject
pageobject (extends baseobject)
Junit testobject (references one or multiple pageobjects)
Within my pageobjects I chose to define my findBy UI mappings as variables, and in-turn reference them within the various methods I write for that pageobject. I find this works very well. However, one item I am waffling on is how to handle method design for pages (and their respective pageobject) when there exist potentially 50 separate hyperlinks.
My inclination and design thus far has been to create methods (I think of them as services really) for each link on most pageobjects I've created so that #Test I can simply call the method I want and be done with it. This eliminates the potential for test maintenance...standard practice I know. But I am now trying to decide...does it make sense to create 50 methods, one for each link for a page object, or do I go against my wishes and pass in linktext from the test itself, feeding into a single method that builds the findBy using that passed in parameter.
On one hand there is way less code within the pageobject, but on the other, tests become more brittle. There is potential for these links to be references in hundreds of tests.
Here is a brief example of my model:
classname extends baseobject{
By someLocator = By.linkText("some text");
By someOtherLocator = By.linkText("some other text");
By andAnotherLocator = By.id("someid");
public void someLinkMethod(){
driver.findElement(someLocator).click();
}
public void someOtherLinkMethod(){
driver.findElement(someOtherLocator).click();
}
public void someidMethod(){
driver.findElement(andAnotherLocator).click();
}
}
Thus we come to the end of the question. This model works great for test design. My services (methods) are insulated and easily maintainable. But what would I do if there were 50 UI mappings for links instead of 2 as I have shown above? I toyed with the following design, but really dislike it #Test:
public void selectFromLeftBar(String barItem){
driver.findElement(by.linkText(barItem)).click();
}
Any thoughts would be greatly appreciated!
Do it in your page object class. Here are the reasons:
What does your code do if your page changes the link text? You have to go into each test and change that text, even if the link does the same thing.
What happens if your page removes that link? You are stuck with the same problem, namely, having to find each time you call that link. If its a method...then you delete the method, and your IDE notifies you of each instance that you used it.
Finally, you are providing a standard interface for the test. If you make an exception here, what would stop you from passing other things into your page?
As a side note, I would recommend only mapping elements that you are going to use. I've found that if I map out every element I could possibly ever need then I end up with a massive class filled with fluff and less time on my hands.
How can I call a method from a class that is not an object within another class, and has nothing in common with this other class?
In my case:
class GridUI {
com.google.gwt.user.cellview.client.DataGrid grid;
public void refresh() {
dataGrid.redraw();
}
}
class SomeBackendService() {
public foo() {
//have to trigger refresh of a specific grid
}
}
One possibility might be to make the refresh() and grid static. But that's bad design, and I cannot use this approach as I want to use several implementations of GridUI.
So, how can I refresh a certain gridclass in my app from any service that does not contain this grid as an object??
Just create and fire an Event for it in your service and make your grid register for that Event. It's probably best to use an EventBus.
Using a static Map<String, Grid> as was suggested in the accepted answer will work but it's not proper. You risk making mistakes and it's not as easy to manage when the number of grids increases.
The EventBus approach is more work upfront but in the end it's a better approach. You'll be able to reuse the EventBus throughout your application. It really helps keep your coupling down. You'll also easily be able to get different objects act on the same Event with little effort.
Alternatively create a components registry (basically a Map<String,Grid>), then fetch the grid from SomeBackendService using its id as key in the registry. (I guess you know which grid you want to refresh, right?)
Be careful with registries though:
make sure they are thread safe if need be (probably true in an UI app)
they tend to fill up and leak memory if not properly handled
Sorry for not answering that long time, i was in vacation.
Interfaces are some kind of classes.
But they do not implement any method, they have empty method bodies.
Each class, which implements an interface usually MUST implement its methods.
In C# You would Do :
enter code here
interface IMyInterface
{
void PleaseImplementMe();
}
class clMyInterface :IMyInterface
{
void IMyInterface.PleaseImplementMe()
{
MessageBox.Show("One implementation");
}
}
end
Please let me know, whether this is what can help You or not.