If you are like me, who does programming for living, if you are very passionate about one language and would never ever think of switching to any other language?
Then this blog post if for you.
During my early years as programmer, I was very passionate about Java and only Java (does not mean that, I am any less passionate about Java today). I wanted to do programming only in Java. I thought I can do anything and everything in Java (which is true even today).
I was very apprehensive to do programming in any other language.
Then due to a project requirement I had to work on C++. Because of that, I started appreciating Java even more.
How elegantly it does memory allocation and garbage collection etc. I started appreciating the high productivity I could get using Java.
After that, I got an opportunity to work on Ruby on Rails. I started admiring all the dynamic feature of Ruby language. Started appreciating closures in Ruby and learned how a few lines of code can be expressed in just on single line. Started admiring how simple, a modern web framework could be.
Then came along .Net. In .Net we had used a dependency injection framework called Castle. I had used Spring framework from the Java world in the past, because of this I could apply same concepts in Castle framework. This meant, I was productive from Day 1. Effectively no learning curve involved!
I realized that as time passed, C# and Java have converged to each other. Both these languages have learned from each other and implemented some very good features.
Then, I started working on Grails. I was amazed to see that, Grails and Ruby on Rails are almost 90% similar. They are so similar to each other in concepts and implementation that, I find the only difference is the syntax!
Again, was able to apply the concepts, that I had learned while doing the Ruby on Rails project in Grails. End result productive from Day 1.
After all these years, I have learned one thing and that is, all these languages be it Java, Ruby, Groovy, C# etc. be it anything, they implement same concepts over and over and over again.
Now I feel, If someone is a good programmer it actually does not matter which language they use to achieve a given task.
Language and Framework are just tools to achieve a particular task.
In the olden days car manufactures used old tools to manufacture cars and now as the tools and technologies improve they use better tools and manufacture wonderful cars!
Applying similar analogy we just have to keep updating the tools that we use so that we can create good efficient software.
That's why I keep saying to programmers, don't be in love with one language, be in love with the concepts!
Showing posts with label grails. Show all posts
Showing posts with label grails. Show all posts
Thursday, September 30, 2010
Sunday, April 25, 2010
How to stub message method in a controller
Hello Gang! Based on the feedback from all you guys, here's a post about how easily can we stub the message method while writing controller Unit tests.
Lets take the example of my good old friend, YES the PersonController
Requirement:
After saving a person user should be redirected to show view, with a flash message indicating user was saved successfully.
Controller Code:
We have seen similar code in the past lets look at it again
We are not interested in code showing the action required if errors are returned while saving a person (As we had already covered that here)
Only different between the earlier code and this one is the flash.message and the use of message method.
How will we test it - How do they do it!:
In the grails environment, a method called message is dynamically added to the instance of PersonController, but how do we write a unit test for this?
All our controller test cases have been extending ControllerUnitTestCase which adds a lot of utility methods and fields to the controller instance. But unfortunately it does not stub out the message method. Hence, to test the above code we will have to stub out the message method manually. How? remember metaClass technique from my earlier post we will apply it here as well.
Test code looks like this:
If you notice we didn't use removeMetaClass for the controller instance. Why? because our test case extends ControllerUnitTestCase which creates a new instance of the controller class under test (in this case PersonController)before every test case is run. And hence we don't bother to use the removeMetaClass for the controller instance.
That's all folks! As we can see metaClass is a real boon for unit testing
As uaual feedback, comments and complaints are welcome as always!
Lets take the example of my good old friend, YES the PersonController
Requirement:
After saving a person user should be redirected to show view, with a flash message indicating user was saved successfully.
Controller Code:
We have seen similar code in the past lets look at it again
We are not interested in code showing the action required if errors are returned while saving a person (As we had already covered that here)
Only different between the earlier code and this one is the flash.message and the use of message method.
How will we test it - How do they do it!:
In the grails environment, a method called message is dynamically added to the instance of PersonController, but how do we write a unit test for this?
All our controller test cases have been extending ControllerUnitTestCase which adds a lot of utility methods and fields to the controller instance. But unfortunately it does not stub out the message method. Hence, to test the above code we will have to stub out the message method manually. How? remember metaClass technique from my earlier post we will apply it here as well.
- Stub out the save method (on the person instance ) to return true, using the metaClass of Person
- Add a dummy message method on the controller instance, again using the metaClass of controller
- Assert that flash.message was correctly set by the PersonController
- Remember to remove the metaClass of Person using which we stubbed the save method using the GroovySystem class. (For explanation on why is this necessary see this post)
Test code looks like this:
If you notice we didn't use removeMetaClass for the controller instance. Why? because our test case extends ControllerUnitTestCase which creates a new instance of the controller class under test (in this case PersonController)before every test case is run. And hence we don't bother to use the removeMetaClass for the controller instance.
That's all folks! As we can see metaClass is a real boon for unit testing
As uaual feedback, comments and complaints are welcome as always!
Labels:
controller,
flash,
grails,
howto,
message,
removeMetaClass,
stub,
unit testing
Unit testing Grails Controller - Part - 3
Alright folks this is the third and final installment of Unit Testing Grails Controller series.
In the last post I explained how we could write a test case where controller returns a model that could be used by view to render itself.
In this post we will see how we could write tests for situations in which controller has to render a view (may be to show validation errors while saving a instance of domain class)
Tired of repeating, but will say it again anyways, taking an example of a controller that performs CRUD on Person domain class lets call it PersonController
Requirement:
If an error occurs while saving a person, controller should re-render the create view showing the error so that user can rectify the error and try again.
Controller Code:
The controller code that will do the job for us looks like
How will we test it - How do they do it!:
Again, in the grails environment, save method on a person instance will actually fire an insert statement, but do we really want to do that while writing a unit test for PersonController? The right answer is NO. 10 Points if you get that right!
So what are we doing in the above code sample.
We already know how to write test case for step 4 from the first post
Lets focus on the first three steps. There are two ways in which we can test the above code. A longer and a shorter way! And yes you guessed it, I will show the longer way first :)
Method 1:
Although we should have written another test case to assert that the model was correctly populate by the controller but for the sake of this blog I have shown the assert in single test case.
Now that you have the Grails power, don't go anywhere! I promise, will not bore you for long. Here's the Method 2 of testing the above code.
Method 2:
See its pretty easy to randomly add/stub methods using the metaClass. Its a really powerful tool but as Spider Man's uncle Ben once said
Here, I conclude the three part series to demonstrate art of Unit Testing the grails controller.
I hope you liked reading it as much as I liked writing it. Feedback, Comments and Complaints are welcome as always!
In the last post I explained how we could write a test case where controller returns a model that could be used by view to render itself.
In this post we will see how we could write tests for situations in which controller has to render a view (may be to show validation errors while saving a instance of domain class)
Tired of repeating, but will say it again anyways, taking an example of a controller that performs CRUD on Person domain class lets call it PersonController
Requirement:
If an error occurs while saving a person, controller should re-render the create view showing the error so that user can rectify the error and try again.
Controller Code:
The controller code that will do the job for us looks like
How will we test it - How do they do it!:
Again, in the grails environment, save method on a person instance will actually fire an insert statement, but do we really want to do that while writing a unit test for PersonController? The right answer is NO. 10 Points if you get that right!
So what are we doing in the above code sample.
- Creating a person instance using the request parameters
- Try to save the person created in the previous step
- If save fails render the create view and return from there (Guard clause is an import pattern which deserves a post for itself)
- If save succeeds redirect user to show view.
We already know how to write test case for step 4 from the first post
Lets focus on the first three steps. There are two ways in which we can test the above code. A longer and a shorter way! And yes you guessed it, I will show the longer way first :)
Method 1:
- use mockDomain(Person) to add the save dynamic method to person instance
- From the test code, we could populate the params map with invalid values
- Those params would be used to construct the Person instance
- While saving the person instance constraints will be fired, which will fail because of invalid values
- This will cause the save method to return false and hence if condition will be satisfied causing the render to execute.
- ControllerUnitTestCase class provides us a convenient property called modelAndView using which we can assert that controller actually renders to the create view
Although we should have written another test case to assert that the model was correctly populate by the controller but for the sake of this blog I have shown the assert in single test case.
Now that you have the Grails power, don't go anywhere! I promise, will not bore you for long. Here's the Method 2 of testing the above code.
Method 2:
- Stub out the save method (on the person instance) to return false manually, using the metaClass of Person
- use the modelAndView property to assert that controller actually renders the create view
- Remember to remove the metaClass using which we stubbed the save method using the GroovySystem class. If you don't do this then the metaClass setting will interfere with other tests that use the save method. Because of this, some test cases could misteriously start failing when, run along with other tests and pass when run individually. Such a situation is extremely difficult to debug and fix. This is the single most common mistake people do while using metaClass. Take my advice, Dont do it!
See its pretty easy to randomly add/stub methods using the metaClass. Its a really powerful tool but as Spider Man's uncle Ben once said
With great power comes great responsibility!use it responsibly!
Here, I conclude the three part series to demonstrate art of Unit Testing the grails controller.
I hope you liked reading it as much as I liked writing it. Feedback, Comments and Complaints are welcome as always!
Labels:
controller,
grails,
howto,
mock,
modelAndView,
removeMetaClass,
stub,
unit testing
Unit testing Grails Controller - Part - 2
As promised to my readers here's the second installment of Unit testing grails controller.
In my previous post we had seen how can we test a situation where grails controller redirects user to a different action.
In the post we will focus on how we could test a situation where controller returns a model, which can be used by a view to render itself.
Again, as in the previous post for simplicity I am taking an example of a controller that performs CRUD on Person domain class lets call it PersonController
Requirement:
When user tries to view person's data, controller should retrieve requested person's information and return it so that view can render itself.
Controller Code:
The controller code would look like
For simplicity I have not shown the code to handle a situations when person with the given id is not found.
How will we test it - How do they do it!:
Clearly, when above code is run in the Grails environment Person.get(personId) will actually fire a database query to get the person. But when we are unit testing the controller we dont want to fire a database query. Basically we want to test the PersonController in isolation.
Fortunately, grails provides a method called mockDomain. This is an extremely powerful method added by the GrailsUnitTestCase class. As the name suggests, it mock's any grails domain class (as simple as that :)). This method adds dynamic methods such as save, get, various finder's etc. to Grails domain class. For e.g.
will add previously mentioned dynamic methods to Person class. Which effectively means that we can simulate the behaviour of these methods without actually firing queries agains our database. Which is what we wanted in the first place!
There are two overloaded versions of mockDomain method
This version behaves as if there are no records in the Person table.
Second version is
This version behaves as if, each person instance found in the [List of people] represents one record in the person table. Hence when you call Person.get(123) if the list contained a person with id 123, that person will be returned.
Enough Said! Show me the code damn it!
The Test case class:
The test case can be written as
Thats all folks! This is all we need to tests the controller method.
Stay tuned for next installment of Unit Testing Grails Controller!
In this post I have changed my style a little. Explanation comes before the actual code. Do give me feedback about this approach which one do you like and why?
In my previous post we had seen how can we test a situation where grails controller redirects user to a different action.
In the post we will focus on how we could test a situation where controller returns a model, which can be used by a view to render itself.
Again, as in the previous post for simplicity I am taking an example of a controller that performs CRUD on Person domain class lets call it PersonController
Requirement:
When user tries to view person's data, controller should retrieve requested person's information and return it so that view can render itself.
Controller Code:
The controller code would look like
For simplicity I have not shown the code to handle a situations when person with the given id is not found.
How will we test it - How do they do it!:
Clearly, when above code is run in the Grails environment Person.get(personId) will actually fire a database query to get the person. But when we are unit testing the controller we dont want to fire a database query. Basically we want to test the PersonController in isolation.
Fortunately, grails provides a method called mockDomain. This is an extremely powerful method added by the GrailsUnitTestCase class. As the name suggests, it mock's any grails domain class (as simple as that :)). This method adds dynamic methods such as save, get, various finder's etc. to Grails domain class. For e.g.
will add previously mentioned dynamic methods to Person class. Which effectively means that we can simulate the behaviour of these methods without actually firing queries agains our database. Which is what we wanted in the first place!
There are two overloaded versions of mockDomain method
This version behaves as if there are no records in the Person table.
Second version is
This version behaves as if, each person instance found in the [List of people] represents one record in the person table. Hence when you call Person.get(123) if the list contained a person with id 123, that person will be returned.
Enough Said! Show me the code damn it!
The Test case class:
The test case can be written as
Thats all folks! This is all we need to tests the controller method.
Stay tuned for next installment of Unit Testing Grails Controller!
In this post I have changed my style a little. Explanation comes before the actual code. Do give me feedback about this approach which one do you like and why?
Labels:
controller,
grails,
howto,
mock,
mockDomain,
stub,
unit testing
Tuesday, April 13, 2010
Unit testing Grails Controller - Part - 1
Recently I have been experimenting a lot with grails.
One most import language/framework feature that attracts me is "how easily can we right good unit tests". As the quality of unit tests will in turn determine the quality of production code.
Hence, here's my attempt to explain how one can write good Grails Controller tests.
In a grails controller mostly we would be doing any of the following things
One most import language/framework feature that attracts me is "how easily can we right good unit tests". As the quality of unit tests will in turn determine the quality of production code.
Hence, here's my attempt to explain how one can write good Grails Controller tests.
In a grails controller mostly we would be doing any of the following things
- Redirect a user to a different action
- Return a model object, that view can use to render itself
- Render a view with domain model validation errors
For simplicity I am taking an example of a controller that performs CRUD on Person domain object lets call it PersonController
Requirement:
Whenever user tries to view the index action on PersonController he should be redirected to list action (which shows the list of people)
Controller Code:
Controller code that does the job for us is as follows
Test case class:
Grails Testing Plugin provides excellent support to test controller methods. Unit test for the above method could be written as follows
Explanation:
Grails is a framework that makes heavily use of Convention over Configuration. This principal is applied to unit test cases as well. There are a few things special about the above unit test case.
- Name of the test case PersonControllerTests
- This means that the name of controller class under test is PersonController.
- Although we could have named the test class anything and explicitly mention the controller class under test is PersonController. However, I am not going to show how that's done in this post as I want to keep this post as simple as possible.
- It extends from ControllerUnitTestCase
- This automatically initializes controller property of the ControllerUnitTestCase. This property will be initialized with an instance of PersonController class.
- Base class also adds dummy dynamic methods like "render" and "redirect" to the PersonController class. These methods are usually available only in Grails environment
- Base class also adds members like "params", "redirectArgs", "flash", "modelAndView" etc. to the controller instance
- Base class tearDown method removes the dummy dynamic render and redirect methods from the PersonController class.
As explained earlier the base class ControllerUnitTestCase adds dummy dynamic redirect method to the PersonController class. The dummy redirect method simply inserts all arguments passed as key value pairs in the redirectArgs map. redirectArgs is a Map member property added by ControllerUnitTestCase to the PersonController.
Hence the statement that asserts "index action redirect to list action" would look like
We can easily make out that writing good Unit test is extremely easy in Grails. We did not have to deal with mocked HTTP requests or responses to test the redirect behavior.
In next blogs I would show how easily we could write unit tests for the following
As usual your feedback/comments are highly appreciated.
Labels:
controller,
convention over configuration,
grails,
Grails 1.2,
howto,
redirect,
unit testing
Subscribe to:
Posts (Atom)