0

I am trying to test the overridden toString() in groovy (I know it is trivial but that is what you get after reading kent beck's TDD book). I assertSame on the expected string and the actual

Here is the code block:

    @Test void testToString(){  
     def study = new Study(identifier:"default-study", OID:"S_DEFAULTS1", name:"Default Study") 
     def expected = "org.foo.oc.model.bar(OID:S_DEFAULTS1, name:Default Study, identifier:default-study)"   
     assertSame "Should be equal", expected, study.toString()
    }
   

Here is the stack trace for the failed test:

     junit.framework.AssertionFailedError: Should be equal expected same:org.foo.oc.model.bar(OID:S_DEFAULTS1, name:Default Study, identifier:default-study) was not:org.foo.oc.model.bar(OID:S_DEFAULTS1, name:Default Study, identifier:default-study)
        at junit.framework.Assert.fail(Assert.java:47)
        at junit.framework.Assert.failNotSame(Assert.java:273)
        at junit.framework.Assert.assertSame(Assert.java:236)
    

Just to add that assertEquals works well with the same parameters. I know it is no biggie but I want to understand why it fails.

Thanks

2 Answers2

3

Why aren't you using assertEquals which uses .equals()? assertSame compares object references (== operator). Even though the strings are the same, they are two different objects, hence the assertion is failing.

UPDATE: This is a very common mistake in Java: String.equals() and == operator work differently. This has been discussed several times:

I know you are using Groovy which does not suffer this problem, but JUnit is written in Java and behaves according to the rules above.

UPDATE: actually, your string are different:

org.foo.oc.model.bar(OID:S_DEFAULTS1,  name:Default Study, identifier:default-study)
org.foo.oc.model.bar(OID:S_DEFAULTS1, name:Default Study, identifier:default-study)

Community
  • 1
  • 1
Tomasz Nurkiewicz
  • 334,321
  • 69
  • 703
  • 674
  • Sorry about the disparity in the strings. It was an edit issue and not the real compiler output. AssertEquals works well for me but I want to understand why assertSame does not work. I thought Strings in this instances are object references - please correct me. –  Oct 21 '11 at 11:56
  • Thanks so much. Your references helped me a lot. I will ask to confirm before accepting your answer, I just did a small test with assertSame, "should be same", "equal", "equal" and it worked. Do you mean to say that assertSame will only work on object references? –  Oct 21 '11 at 12:08
  • assertSame is actually convenient when you want to confirm that **exactly** the same object was returned, not an equal copy. But most of the time `assertEquals()` is a better choice. – Tomasz Nurkiewicz Oct 21 '11 at 12:09
  • You are right, I tested assertSame on the objects and it worked. Thanks again. –  Oct 21 '11 at 12:12
0

Your original uses lowercase d in "default Study" but your expected string does not.

EDIT: when comparing strings you should always use equals() rather than comparing references. Two strings that pass the equals() test may or may not also be the same object.

BTW, in Groovy == is the same as equals().

erturne
  • 1,799
  • 1
  • 15
  • 29
  • Thanks for the == tip! I just tried it out and it worked. I think Tomasz's (hard name) answer covered it well. But thanks for the heads up anyway. –  Oct 21 '11 at 12:20
  • If you want to compare references in Groovy, use the is() function. For example: def sameObject = a.is(b) – erturne Oct 21 '11 at 19:21
  • The naming of that function scares me. Probably it should have been named 'like()' other than 'is()'. It confuses me when am reading the code. –  Feb 28 '12 at 08:32