Yet another readonly module
I’m done with Readonly. It has served it’s purpose but I’m frustrated to the point of writing a replacement. I still think it’s a good idea to declare variables readonly, but as an implementation I find Readonly unworkable. The problem is two-fold.
Readonly hasn’t been updated in 6 years. It has collected quite a list of bugs. Not all of them can be fixed, but most that can be are either trivial or already have patches. Fact is it hasn’t been done and I have my doubts on whether it will be done.
Broken by design
Readonly has a number of design issues. It uses ties for its implementation. This is not only slow, but also rather buggy. There are lots of subtle corner cases to ties, and Readonly has probably run into a lot of them, though I suspect there may be more waiting to be discovered. Most of its bugs are related to this. There are some more issues but they are relatively minor compared to this. Your variable shouldn’t have unexpected behavior simply because it’s readonly, that’s madness.
The sad part is that ties aren’t really necessary here. Perl 5 has always supported real readonly variables, and though this functionality wasn’t exposed for Perl code until 5.8. It makes a lot more sense to use the real thing. The optional Readonly::XS tries to do that for scalars, but in the most common use case of Readonly (using sub Readonly on a scalar) it isn’t actually used (this is probably a bug).
So I’ve written my own module, Const::Fast. It does not use ties or XS. It has one function
const, that simply makes a scalar, array or hash recursively readonly. Without the speed penalty of ties and without the bizarre class of bugs that they bring.