Showing posts with label Programming. Show all posts
Showing posts with label Programming. Show all posts

Tuesday, May 5, 2009

Do you really want moist test ?

Moist tests are the test cases that do not follow DRY(Don't repeat yourself) principle. According to this philosophy, the setup and any other private method in the test class is a smell. It advocates that having all the test code in test method itself, improves readability and makes it easy to maintain. I recently joined a project team which follows this concept, and it was pretty surprising for me.

The test acts as a documentation for the object it tests. If i have to understand the job of a class, I will go to the test and read test methods. And thanks to the concept of moist test, I end up reading 5 lines of code duplicated in all the tests which creates object of system under test, creates mock objects, set expectations, inject dependency and do other setup stuff. So reader has to skip a chunk of code to get to the crux of the test. This is definitely not improving the readability of test.

The readability and maintainability of the test is more important than deciding whether to be moist or DRY in your tests. I agree that we should not be obsessive about strictly adhering to DRY in the test code, but in the same way, we should not be intentionally 'wet' and duplicate the code everywhere.

Lets look at the reasons people gives to write 'Moist' tests. I have taken most of the reasons from the Jay field's and Shane Harvie's post.

- When a test fails, I want to fix it quickly
How will duplicating the code in all test methods will allow you to fix the code quickly ? Suppose you add one more parameter to the constructor of your object, changing it in at one place in setup method will be much quicker than changing it in every test method.

Obviously, if you want to initialize your object differently, you have to instantiate it in your test method. But that's a special case, may be one of the ten test methods will need a different object and that method will instantiate it. Other methods in the test class will continue using the object that is instantiated in the setup method. If all the test methods needs different objects, then you don't need instance variable at all and all the test will have their own local variable. By doing so, you are breaking DRY principle, but it is necessary to make sure that your test is not forced to execute unnecessary code from setup method.

- I have to search around a large test class for extracted methods, or instance variables that may be modified throughout the class, this costs me time
Why would you have a large test class ? You will have a large test class only if the object your testing has multiple jobs and you have to test all that behavior. If you follow the Single responsibility principle and write classes that has only one job, you will have only one behavior to test (with alternate flows) and you will end up with small test classes.
So, if you have large class, its a smell that your object is doing too many things. You need to fix that first by segregate the responsibility into separate classes. Once you move the responsibilities to the different classes, you have to move the tests to separate test classes as well and you will end up with small test class.If doing so is impossible for some reason, you could extract test cases into separate files each testing a part of object's behavior.

Still even if your test class is large, I do not understand how searching for a method will take much time.(In most of the IDEs, you just have to do Ctrl+B(or other similar shortcut) to go to the method definition). The purpose of extracting methods is not only to group a block of code together, the more important purpose is to create abstraction. By giving descriptive method name to the extracted method and using that method in your test, you are creating an abstraction over a block of code and thereby increasing the readability of the test.

In few test, instance variable that is initialized in setup method will be modified by the test. However, this should not affect other tests. Ideally, you will create the instance of system-under-test (the object which you are testing) in the setup method and then use it in your test. The changes made by other objects to the instance variable will not affect your test as object is getting initialized in setup method for every test.

- Some developers don't know that setup method is getting executed/ they may not notice that setup method exists in test
This is probably the most lame excuse. Even a developer who learned JUnit today will know that the setup method gets executed before every test. And if your developer don't have this basic understanding, you should stop writing any code and educate them first. Their ignorance can't be the reason why you don't want to have setup methods in test class.

- Separating the test code in setup and test method decreases readability
Writing the code in setup method will reduce the readability only if you are not using the setup method properly. i.e. if we have any test specific code in setup method. However, if we have test environment setup code in setup and test and assertion code in test method, then it follows the natural flow of the test and should increase the readability. Though it depends on the reader as well. If the person is used to reading the code with small modular methods,reading the tests with setup methods should come naturally for him.

- Tests should be independent, so why should all of them use common setup (or any other common) method ?
When we say that tests should be independent, it doesn't mean that they should be lexically separate. It means that we should be able to run tests individually and the outcome of one test should not impact other tests. The setup method is executed before every test, so the objects are initialized freshly for every test. If setup method is too big and it contains some code that is not required for all the tests, then you have to extract the test specific code in your test method or write private methods.

- If you have to write large code to setup your test, you have to rethink about your object model instead of putting all the code in setup method
This is definitely true. Big setup code is a smell that your class has too many dependencies. In this case, we should definitely try to minimize it by breaking the class into different classes. But duplicating the chunk of code in all the tests is not the solution.


The ultimate core aim is the readability of test. Readability of the test is more important than applying DRY(this holds almost true for production code as well). We should not apply DRY principle stringently for test code. But it doesn't mean that we should go entirely other way round, write duplicate code and make our test moist purposefully.

IMHO, test method should have the code to invoke the method to test and do the state/behavior verification. It may also have code to set the expectations on the mock objects. The code for initializing the system-under-test (probably by injecting some mock objects) should go in the setup, which is the right place for it. Obviously, if all the test methods needs different setup, then the common setup method doesn't make sense and we have to duplicate some code in test methods. If you notice that changes are required in the common extracted methods and the changes are affecting other test, its time to get rid of extracted method and copy the code in all tests. So, you may end up with a test method which has all the code for setup, test and assertion. Its OK to violate DRY principle in your test code if it is required but this should be an exception. Naturally, we should try to keep our tests DRY and introduce 'moistness' only if required. We shouldn't intentionally make it 'wet' by duplicating the code everywhere.

Wednesday, April 22, 2009

Using field level access for hibernate entities

Hibernate allows you to configure the access mechanism for attributes in the entity object. It can access the attributes directly or through the accessors. The field or property access type is decided by hibernate based on the location of @Id or @EmbeddedId.

@Entity
public class Item {
@Id
public String id;
public long itemNumber;
}

@Entity
public class FoodItem {
private String id;
private long foodId;

@Id
public String getId(){
return id;
}
public long getFoodId(){
return foodId;
}
}

In the above code, Item class uses field access and FoodItem class uses property access.

Using property access mechanism allows classes to hide the internal data structure from the external world and it enables class to perform validations while setting the value or while accessing it. It is useful when we want to perform some calculation before returning the result or setting the value.

However, mostly we end up directly accessing the variable from the getter and setter methods. In that case, property access is overkill. It makes us write lot of getter - setters which are not used anywhere else in the code. It also exposes setters if when we don't want anyone to set the value of fields like 'id'. We can mark the accessors private or protected and avoid this problem, but we will still have the code.

IMHO, while creating the entity, we should start with field level access. Doing so will reduce the unnecessary code which is used only by hibernate. We should keep the fields private and provide accessor methods only when required. So our entity object will be modeled by the needs of the application and not by the hibernate. In future, if we need to validate or manipulate the values set on the object (which mostly won't happen), we can then switch to property access, but we shouldn't start with it.

Adding static @BeforeClass method in the test class

I was looking at a integration test in project that takes 10 seconds to execute. Its a integration test in a for a class that connects to the FTP server and performs some operations. The test uses a in-memory mock ftp server. The issue is that it starts, initializes the mock file system for every test and then stops the server after each test. The initialization code is written as a part of @Before method and server is stopped in @After method. The fact that the server was getting started and closed for every test was the reason why test was so slow. I want to start and initialize it only once for the all the tests my my class. The way to achieve this is to use @BeforeClass annotation. The method marked with @BeforeClass runs only once for all the test. The corresponding tear down method is @AfterClass. By using @BeforeClass instead of @Before and with some other changes, I was able to reduce the time required to run the test to 3 seconds.

However, using @BeforeClass instead of @Before may make tests dependent on each other and on the order of execution. As all the tests will use the same objects, changes made by one test will be affecting others. So @BeforeClass method should be used to initialize objects which are not modified by the tests. The methods should be used to setup the environment for the test and not for creating the objects that will be directly consumed by the tests.

@BeforeClass (and @AfterClass) method has to be static, which means all the variables that are accessed in this method has to be maked as static. This puts up restrictions on the ways in which @BeforeClass can be used, but this makes it explicit that the @BeforeClass method should be used to set only the environment for the test and objects under test itself.

Tuesday, April 7, 2009

Improved modularity with Superpackages in Java7

JSR 294 talks about introducing improved modularity support with Superpackages.
Right now modularity is supported at various levels in Java language. Modularity provides encapsulation and information hiding at various levels. Method encapsulates certain program logic and local variables. Class encapsulates instance variables and methods and a package provides a module to group related classes. All these modules helps us to understand and change the system locally, within the module space without worrying about its effect outside the module.

However, the modularity supported by packages is inefficient in some cases. The problem is that packages supports hierarchy, file system also stores classes in the hierarchy, but the accessing member of the package is not hierarchical. There is no special relationship between packages and their children or parents. We create packages like com.domain and com.domain.validators. Clearly, there is some kind of hierarchical relationship between the classes in two packages. You may want to access some classes or methods of com.domain from com.domain.validators package, but you don't want to expose them to the whole world by making them public. The scenario is very well explained by Neal Grafter at http://www.infoq.com/interviews/gafter-closures-language-features-optional-typing. Currently, there is no way to achieve this directly.

We can use default member access so that it becomes public within the same package, but stays inaccessible to the outside world. Classes in the subpackages also can not access it. So we end up putting classes in the same package as we want to access members with the default access. This leads to packages with large number of classes, the classes which should ideally go in the sub packages.

The other option is to make the members public. Doing this may expose unwanted API. We will end up relying on the official documentation of the API and prays that no one comes to know about the class and invoke its 'public' method. The issue is public is too public.

We need a module entity that is bigger than a package but narrower than public. The solution is to introduce one more level of modularity called Superpackages. Superpackages contains classes from one or more packages or superpackages. Its a new construct which is put into super-package.java file and compiled by the Java compiler. The types can be exposed to the outside world by exporting them. Only the exported types are visible outside the superpackage. Public types that are not exported can not be accessed outside of superpackage.
e.g. A superpackage which encapsulates types in com.domain and com.domain.validators is defined as -

superpackage domain {
// member packages
member package com.domain;
member package com.domain.validators;

// exported types
export com.domain.*;
}

Here, only classes from com.domain package is visible outside superpackage, classes from com.domain.validators are not.Note that Java classes doesn't specify the superpackage they belongs to. It is specified in the super-package.java file only.
Superpackages can encapsulate other superpackages as well. Only the public types in exported superpackage will be accessible from outside.

Superpackages is coming up with Java 7 and going to be an effective mechanism for information hiding in Java.

Wednesday, March 25, 2009

Java 7:Multiple exception catch block

Java 7 proposes a new syntax for catching multiple exceptions in a single catch block (http://www.javac.info/Multicatch.html). It looks like a neat feature to have and the new syntax is definately better than having multiple catch blocks with the same exception handling code.
So instead of -

try{
// Some code that throws ServiceException and WebsiteException
}
catch(ServiceException exception) {
Logger.Log(exception);
throw ApplicationException(exception);
}
catch(WebsiteException exception){
Logger.Log(exception);
throw ApplicationException(exception);
}

we will be able to write -

try{
// Some code that throws ServiceException and WebsiteException
}
catch(WebsiteException | ServiceException exception) {
Logger.Log(exception);
throw ApplicationException(exception);
}

So, we will be able to get rid of duplicate exception handling code and will make our code little simpler. Its a pretty obvious change and ideally it should have been identified and fixed before.

This new feature is useful, but how much ? I think this is trying to solve the problem that should not exist. In most of the cases, you should not be throwing more than one checked exception.It will happen if we are exposing the implementation of method and rethrowing the exceptions from called methods.
Even if we have more than one exceptions, we may want to handle them in different ways. So we can not combine multiple catch blocks.
Apart from that, whole lot people in java devs community, including me, believes that checked exceptions should not be used at all. Checked exceptions forces developer to write the exception handling code even when it is not required. Exception handling code gets mixed up with the business logic. This leads to cluttered and unreadable code. Worst part is that checked exceptions create dependency between a method that throws exception and all other methods that directly or indirectly calls that. It makes caller of the method depends on the implementation details of the method. And after coding in C# (which doesn't have checked exceptions) for 2 years, i doubt whether checked exceptions are required in language at all.
Looks like this is nice to have but not so useful (lame?) features in Java 7.

Tuesday, March 24, 2009

Following SRP on grounds

Single responsibility principle is probably the simplest OO coding principle. It says "A class should have only one responsibility and thereby, only one reason to change." Isn't it very straightforward ?
But when I look at the code of my application, I see that very few classes in my app follows this principles. Why is that ? The principle is very simple and so it should be simple to implement as well. Its relatively easy to make sure that our class doesn't have any method that doesn't belong to the job of class. I think the difficult part is to know when we are adding additional responsibilities to the class. We do incremental development, start with only what is required and then add up behavior in methods and methods to class as required by the failing test. During this process, we somehow manage to sneak in the logic that is not the part of class's responsibility.
For example, we have mapper classes in our code which maps domain object to data contracts. The job of mapper classes is just to copy the fields from domain objects to contact. The mapper should only do this job of mapping. Consider the following example. In this, Booking object is loaded from the database. This class will map Booking to BookingData object.

public class BookingMapper{

public BookingData Map(Booking booking)
{
BookingData bookingData = new BookingData();
bookingData. Id = booking.Id;
// Other fields
bookingData.BookingFee = CalculateBookingFee (booking.StationCode, booking.TotalCost);

return bookingData;
}

private decimal CalculateBookingFee (StationCode stationCode, decimal totalCost){
// some complex logic to calculate booking fee based on station code and total cost,
// may be, the method will read some values from database.
}
}

The class BookingMapper has only one Map() method. From outside the class, it looks like the class has only one responsibility. However, apart from mapping the data, the class is also calculating the booking fee. It has 2 jobs - to map the data and to calculate the value of booking fee.

The mapper class should do only mapping and we have to move the responsibility of calculating booking fee to other class. If the fee calculation depends only on data present in booking object (like station code and total cost), then the obvious place for CalculateBookingFee method is Booking class itself. We can have a read-only property on Booking class called BookingFee which will calculate the fee.If the calculation of fee involves reading the values from database and/or from some other service, then we don't want our domain object to access services or database. In this case, we can calculate the booking fee (and any other required values) before invoking the mapper and pass it to Map() method. Either way, the fee calculation logic will move out of BookingMapper.

Sunday, March 22, 2009

Using extension methods

How many times you have seen your project having a StringUtils or a similar Helper class ? Most of the helper and util classes has pure procedural code. e.g StringUtils may contain a method IsNumaricString() or ToTitleCase( ) which takes a string as parameter.
Ideally all these methods should go in String class itself but we cann't extend String class as it is sealed. However, with the extension methods in C# 3.0, we can 'open' the classes and add methods to it.

So, instead of
string name = StringUtil.ToTitleCase("foo bar");
we can say -
"foo bar".ToTitleCase()

The extension method is defined as -

public static class StringX {
public static string ToTitleCase(this string str)
{
return string.IsNullOrEmpty(str) ? string.Empty : Thread.CurrentThread.CurrentCulture.TextInfo.ToTitleCase(str.ToLower());
}
}

The extension method is defined as a static method, in a static class. The first argument to the method is the type which we went to extend, preceded with 'this' modifier. When we call the extension method, we don't need to specify this first argument.
Isn't it neat ? The example I have used is the simplest one. There are many other cases when you can extend the functionality of the .Net system classes. Like, we can add Serialize() as the extension method in the Object class.

When I first came across this feature, I thought its the way to open classes in Ruby style. But well, its not exactly the same.
In extension method, we cann't access the private (or protected) members of the class that the method extends. We cann't use extension methods to override a method in the class.
The method defined in the actual type has precedence over the extension methods.So there is no way you can change the behavior of existing method with extension method.

One more good thing with extension methods is that they are available only on classes which refers to them. We need to import the classes that contains the extension methods.

The compiler translates the extension method call to the call on static method. So, its just a syntactic sugar to make your code look better. You cann't do 'effective' monkey patching with it as you cann't shadow a method defined in the actual type, neither you can access (and change the value of) any private member of the object.

However, we shouldn't use the extension methods haphazardly for extending the class behavior. Its definitely not the alternative for subclassing.

The MSDN says to use extension methods seriously and only when we have to. Well, my take is to use extension methods when its appropriate.
We can use it when its not possible or not appropriate to extend the class .e.g if we are using some class from the third party code.
Another best place to use extension methods is when you want to add a functionality to your data contract. Consider a scenario where you are getting a Booking object from some service. You want to check if the booking is valid based on some properties of the object. So your code will be something like this...

if(booking.BookingDate > DateTime.Now && booking.NumberofPassengers > 0 && booking.BookingCost > 1)
// then booking is valid

Here, we are accessing properties from the booking object to decide if the booking is valid. This is clear violation of "Tell, Don't Ask" principle (http://c2.com/cgi/wiki?TellDontAsk). The
best place for this logic is Booking class itself. But Booking is a data contract and we cann't add methods to it.So we can add an extension method IsValid() in a static class called
BookingX.

public static bool IsValid(this Booking booking){
return booking.BookingDate > DateTime.Now && booking.NumberofPassengers > 0 && booking.BookingCost > 1;
}

Now, by importing the BookingX class, instead of all the above code, we can say -
booking.IsValid()

So, extension methods helps you to keep the behavior in the correct class.

Thursday, June 5, 2008

Delegates in C#

Delegate is a type in C# that references a block of code. This block of code can be named or anonymous method or lambdas (in C# 3.0). They are like function pointers in C++. Though they are not purely function pointers as they are 'type safe'. Return value and parameters of code block are defined in the delegate declaration.

e.g. public delegate void Print(string message);

This delegate is named as execute which can refer to any method (or code block) which will take one string argument and returns void.

Delegates allows us to use a block of code as data object. As delegate is just a data type like others, it can be passed around to methods and called whenever required. They be default extends System.MulticastDelegate, which means a delegate can refer to more than one methods or code blocks.

Delegate objects can refer to both static and instance methods. Also, Delegates can refer to anonymous methods as follows.

public delegate void Print(string message);

Print print = delegate(string message){
Console.writeline("Message : " + message);
}

In C# 3.0, the same can be written much cleanly using lambdas as -

public delegate void Print(string message);
Print print = message => Console.writeline("Message : " + message);

C# Delegates which uses anonymous methods and lambdas are essentially closures. However, they are not exactly same as closures in pure functional languages like ML. Anonymous methods or lambdas do not capture the variable values when they are definied. The variables used in the anonymous methods are used in the moved to heap and shared between anonymous methods and outer scope. The value of outer variables are modified if they are changed by the delegate. So the changes made by the delegate in the lexical environment propogates back to parent scope.

Delegates with anonymous methods and lambdas are not 'true' closures if we consider the closures in pure functional languages like ML as the lexical environment of delegate is not closed and changes made by delegate are visible in the outer scope. But there are ways to get around this. In C#, we have a name-variable binding instead of name-value binding(which is used in pure functional languages where variables are immutable).

Wednesday, December 5, 2007

What is Metaobject protocol ?

In traditional programming languages like C, C++, Java, programming language designer works at different level of abstraction than programming language users. Language designers writes programmers that decides how the elements of programming languages works and how the features in the languages such as method dispatch, inheritance are implemented. And the programming language users work on writing the primary application classes without having the flexibility of changing the way language itself works.

However, in some languages like Common Lisp Object System (CLOS), Groovy and Ruby, the programming language provide interface to alter and enhance the core features of programming language. This allows changing the way language throws certain exception or implementing multiple inheritance in language that does not allow it by default.

Metaobject protocol is a interface to programming language using which programmer can add and modify the features to programming language. Here, programming language users play with the Meta objects. These objects decides how features like inheritance, method invocation, scope resolution behaves. These objects are called as Meta Objects simply because they holds information about object like methods, fields, super class etc.These objects also controls run time behavior of program and how the primary objects in the actual system works. We can say that Metaobject protocol makes features of compiler/interpreter available to the programmers.

Metaobject protocol is an important feature for meta programming (However, some programming languages like smalltalk allows to do elegant metaprogramming without MOP). It also allows programmers to adjust language according to their needs.
For example, Common Lisp Object System (CLOS) adds object oriented and dynamic language features to LISP using Metaobject protocols. The implementation of language is done by implementing classes as objects of a metaclass and allowing programmer to change behavior of base class and also allow defining new metaclasses.

Groovy, a dynamic scripting language for JVM, implements Metaobject protocol. Metaobject protocol in Groovy decides how the core language functionality like method dispatch, scope resolution for attributes works. It gives more flexible control of language in programmer's hand. And Ruby has many features that allows programmer to do amazing things like changing the behavior of class on run time, defining methods dynamically etc. The AOP implementation for Java called AspectJ is also implemented with Metaobject protocol.

In short, Metaobject protocol gives some amazing power and flexibility to the programmer which can be used with little caution to create amazing programs !

Wednesday, November 28, 2007

Dynamic typed languages rocks ?

Throughout my programming career, I have been using Java and C# which are statically typed languages. But personally I have always been a fan of languages like LISP, Perl, Ruby. And my one of the most favorite feature of these languages is their Dynamic typing capability.

Lets first look at what are Static typed languages.

Static typing is when the the type of variable is known before running a program. In other words, in static typed languages, you have to declare the type of variable before it is used. In such languages, variable is bind to a specific type.
Most of the 'industry standard' languages like Java, C, C++, Pascal are statically typed languages.

There are some obvious advantage of using the static typing.

  • Statically typed languages are potentially more secure as they can catch the typing errors during compile type only, before actually running the program.
  • The performance of statically typed languages can be better. The compiler has the type information of a variable and it can potentially use it for improving performance. There are more opportunities for compiler optimization which can make it run effectively.
  • Code written in static typed languages is easier to understand. The type specification acts as a implicit code documentation in the program. And unlike code comments, this documentation don't have danger of getting outdated. So, in turn, this leads to self documented code.
  • Better IDE support is available. As the type of the variable is already determined, a intelligent IDE like Eclipse or IntelliJ can provide features such as auto completion.

In Dynamic typing, the type of the variable is determined at run time. In such languages, you don't need to declare a variable before it is used. Languages like Smalltalk, Lisp, Perl, Python, PHP, Javascript, Ruby are dynamic languages.

The advantages offered by dynamic typed languages are much attractive.

  • First and foremost (according to me), Programming is more fun in dynamically typed language. You don't need to keep on declaring although you know that there is no value in it and its only required by your programming language, just for the understanding of compiler.
  • A program can be written much concisely in dynamic programming languages. The decrease in the amount of code is not achieved only by omitting the variable declaration but the reusability and flexibility of the code increases greatly because of dynamic typing.

    Lets look at the implementation of method that checks if the object is null or empty in Java

    boolean isNullOrEmpty(String string) {
    return ( string==null ) || (string.length() == 0 );
    }

    The problem with this method is that only objects of type String can access it. If you want to implement same method for any different object, you need to duplicate the method with different parameter.

    And the same method in Ruby..

    def isNullOrEmpty? object
    object == nil or object.length == 0
    end

    As the type of the parameter is not specified, you can use this same method for any object that has length method, including any custom objects.
    This feature is also called as Duck Typing in the ruby lingo. Duck typing suggests that Object type is determined by the behavior. That means, rather than checking for the type
    of object, we just check if the object supports required operation.


However, advocates of static typing criticize of dynamic typing for some reason. Lets look the issues and see if we can resolve them.

  • Dynamic typing can make code difficult to understand. The type of variable or the return type of method is not declared in code. So, it can be difficult to imagine what will be in a variable during runtime.

    This problem is mostly faced by newcomers or people who are coming from the static typed programming background. However, some real application code can be enough
    complex to confuse most experienced programmers also. The problem can be partially solved by proper naming conventions and also by witting unit tests. Properly designed Units tests helps to revel the purpose of code.Informative coding convention (like suffixing the method names with ? when the return type is boolean) and unit tests can help in understanding the code without the using verbose nature of static typed languages.
  • Dynamic typed languages are more error prone as they dont perform the type checking before running the program. The program gives run time exception in case of typing errors which could be caught at compile time by static typed language compilers.

    The frequency of run time errors due to typing issues is itself questionable. Although there is a possibility of such errors, the occourance of such events is rare even in complex system. And again, the practice of TDD or writting unit tests helps to capture the type errors.
    In fact, statically typed languages are also not totally type safe. The type casts can fail at run time. Thats the reason we have ClassCastException in Java. The down casting - casting a object downwords in class hierarchy can be error prone.
  • Dynamic typed languages are not suited for enterprise products and applications. Because of the lack of type checking and (so called)slower performance as compared to static typed languages, dynamic typed languages are good for fun programming but not for developing serious applications.

    The company where I work, ThoughtWorks, is one of the industry leader in developing Ruby apps. If anyone has doubt if Ruby, one of the newest dynamic typing language is
    enterprise-ready, I will suggest them to check out Mingle (http://studios.thoughtworks.com/mingle-project-intelligence), a project management tool developed in Ruby using rails and Oracle mix (https://mix.oracle.com/) which is a first public JRuby on Rails site. The performance and stability of these products is really good.


My personal choice is dynamic typing cause the programming with them is more fun for me. The ability of these languages to produce concise, reusable code has really amazed me. Although the features of static typed languages like ability to run code faster and checking for type errors before run time are nice to have, but these features comes with cost. So for me, languages with dynamic typing rocks ! :-)