"Making illegal states unrepresentable" is one of the worst possible pieces of advice I ever encountered. It sounds very reasonable, but as soon as you face the issue of communicating to the user or other components the fact that something is wrong and what is wrong, you'll discover that it is very hard to inform about illegal states if you cannot represent them.
Let's say you're trying to parse a user object. Let's further say users always have to have a last name - a user without last name would be illegal state.
Now if you're parsing some data for a user that really doesn't have a last name for some reason, there's two approaches to this problem - either you return a User with a null last name (which is essentially giving incorrect information to the caller). Or you make it impossible to set User.lastName to null (for example by making it an Optional) and fail with an error about what went wrong.
Of course you wouldn't NEED to restrict User.lastName to never be null - but if you always fail with an error in that case anyways, why not? That way any consumer of the User object knows that the lastName will always be there and valid.