Search code examples
javaunit-testingcollectionstdd

How to test if a List<? extends Object> is an UnmodifableList?


I'm looking for a way to test if some given List is an unmodifiable one.

I have an object that has a List<NoMatter>, in order to offer methods such as addNoMatter(NoMatter nm) instead of allowing the API client to simply do .getNoMatters().add(nm); I always return an unmodifiable version of this list, so the client is still able to have the list. I do it as follows:

public List<NoMatter> getNoMatters() {
    return Collections.unmodifiableList(this.noMatters);
}

The problem is that when I'm doing my tests I simply cant check if this object is of type UnmodifiableList. My first try was doing:

@Test
public void checkIfListIsImmutable(){
    assertTrue("List is not immutable", this.myObj.getNoMatters() instanceof UnmodifiableList);
}

Happens that I cant seem to be able to import the type UnmodifiableList neither java.util.Collections$UnmodifiableRandomAccessList that is what I get when I try System.out.println(myObj.getNoMatters().getClass().getName()); at the console.

So how can I achieve it???

PS.: I know I can pass this test by doing:

@Test(expected = UnsupportedOperationException.class)
public void checkIfListIsImmutable(){
     this.myObj.getNoMatters().add(null);
}

EDIT: The above test doesn't grants me that the list Im dealing with isn't immutable as I would need to have tests to every method that may modify my original list, including .remove(), .clear(), .shuffle(), etc! thats why I do not think this is a nice way to proceed.

>>> But I still believe that its not even close to an elegant solution! <<<


Solution

  • I actually think that is your best bet. Your alternative (less elegant) way is to check the name of the class.

    this.myObj.getNoMatters().getClass().getSimpleName().equals("UnmodifiableCollection")
    

    The issue for you is the wrapped UnmodifiableCollection is package-private.

    I don't see anything wrong with expecting an exception there, but that's just me.