if ( instance().spawnConditionHandlers.get( id ) == null || instance().spawnConditionHandlers.get( id ).typeIsValidForVillager( villager, rand ) )
Let me see if I can point out the stupid even more obviously:

    if ( instance().spawnConditionHandlers.get( id ) == null || instance().spawnConditionHandlers.get( id ) == a || instance().spawnConditionHandlers.get( id ) == b || instance().spawnConditionHandlers.get( id ) == c || instance().spawnConditionHandlers.get( id ) == d || instance().spawnConditionHandlers.get( id ) == instance().spawnConditionHandlers.get( id ) )

.....
Not only do you repeatidly call instance() within a function of the same damn class.
You also repeatidly call get() with THE SAME INPUT. 
This is just prone to race condition issues.
Which can be the cause of NPE's in your else that you're trying to protect from NPE's.
Not to mention it looks like ass.

Simple:
    IHandler handler = getSpawnHandler(id); //Could be a new function that never returns null!
    if handler.canSpawn(world, position, whatever_the_fuck) spawn_that_shit();

Also making the list the direct interface.. not sure about that, and the names.... what exactly should the be checked in that handler, what information is given to it. What is used with the return value? Your documentation tells me nothing.

What should probably be done it looks like in this case.
Is each village object should be given a 'possible villagers' list. Which is populated when the village is initially generated {or the world loaded} so that whatever conditions can be checked. 

Depends on how people intend to use this.