TL;DR: If you `use builtin ...` multiple times in a row, do they count?
Or are they idempotent? This matters when you `no builtin ...` again.
-----
The `builtin` module performs exports lexically, not symbolically. This
means it inserts named functions in the lexical scope of its `use`
import, rather than just into the calling package. This is good for a
variety of reasons. E.g.
use builtin 'true';
We then added unimport, which removes them again, which is handy for a
few cornercases, and in particular useful if you want to remove *one*
awkward name from the overall version bundle, if you e.g. `use v5.40`.
use v5.40;
no builtin 'blessed';
All's good so far.
The implementation of hiding things in the pad again (the newly-added
"TOMBSTONE" flag) isn't currently very good, as it hides the names too
well. For example, most people would agree that combined, the two lines
like
use builtin 'true';
no builtin 'true';
should in effect do nothing, and in particular if a prior `true()`
function had been lexically visible, it should now remain so.
So, I've been working on a branch to make the implementation better. I
now have things like this working fine:
my sub true() { return "yes" }
use builtin 'true';
no builtin 'true';
is(true(), "yes");
But now I have hit a snag. There's a question around what it means to
import the same name multiple times in a row. For example:
use builtin 'true';
use builtin 'true';
What does this even mean? Has it been imported twice, or just once?
At this point, what would a single unimport operation do? Does it hide
both of the imports, or just one? What would people expect the
following to do?
my sub true() { return "yes" }
use builtin 'true';
use builtin 'true';
no builtin 'true';
say "TRUE is now " . true();
Does it print "yes", or "1"?
--
Paul "LeoNerd" Evans
leonerd@leonerd.org.uk | https://metacpan.org/author/PEVANS
http://www.leonerd.org.uk/ | https://www.tindie.com/stores/leonerd/
Or are they idempotent? This matters when you `no builtin ...` again.
-----
The `builtin` module performs exports lexically, not symbolically. This
means it inserts named functions in the lexical scope of its `use`
import, rather than just into the calling package. This is good for a
variety of reasons. E.g.
use builtin 'true';
We then added unimport, which removes them again, which is handy for a
few cornercases, and in particular useful if you want to remove *one*
awkward name from the overall version bundle, if you e.g. `use v5.40`.
use v5.40;
no builtin 'blessed';
All's good so far.
The implementation of hiding things in the pad again (the newly-added
"TOMBSTONE" flag) isn't currently very good, as it hides the names too
well. For example, most people would agree that combined, the two lines
like
use builtin 'true';
no builtin 'true';
should in effect do nothing, and in particular if a prior `true()`
function had been lexically visible, it should now remain so.
So, I've been working on a branch to make the implementation better. I
now have things like this working fine:
my sub true() { return "yes" }
use builtin 'true';
no builtin 'true';
is(true(), "yes");
But now I have hit a snag. There's a question around what it means to
import the same name multiple times in a row. For example:
use builtin 'true';
use builtin 'true';
What does this even mean? Has it been imported twice, or just once?
At this point, what would a single unimport operation do? Does it hide
both of the imports, or just one? What would people expect the
following to do?
my sub true() { return "yes" }
use builtin 'true';
use builtin 'true';
no builtin 'true';
say "TRUE is now " . true();
Does it print "yes", or "1"?
--
Paul "LeoNerd" Evans
leonerd@leonerd.org.uk | https://metacpan.org/author/PEVANS
http://www.leonerd.org.uk/ | https://www.tindie.com/stores/leonerd/