Schrödinger's cat

And that's what really matters here: To someone observing or using the object, and not looking at the implementation details in the class, the object looks immutable. This is Schrödinger's cat. There is no way to know whether the object is immutable until we look inside the class. To an observer looking at only the API, the mutable and immutable versions of the Library class are indistinguishable, and that's all that matters.

If mutable and immutable objects are indistinguishable to anyone using the object and no side effects are present, then is the object mutable or not?

The object looks immutable to anyone looking at the API but mutable to anyone looking at the code inside the class. Is the object both mutable and immutable at the same time depending on who you ask?

Probably not. I'd argue that it only matters to the person looking at the API. The reason we strive for immutable objects is that mutable ones have negative side effects. I'm not interested in meeting an arbitrary definition of immutability, I'm interested in removing the negative side-effects caused by mutability.

Immutability is skin deep. It only matters to an observer. If internal mutability is never exposed in any way outside the object, then the object is immutable.

Don't look at immutability from the perspective of do any properties in the class ever change? but instead from the perspective of can an observer of an object see changes caused by mutability inside the class?.