6

Sometimes I don't want multiples files, especially if I'm playing around with an idea that I want to keep a nice structure that can turn into something later. I'd like to do something like this:

module Foo {
    sub foo ( Int:D $number ) is export {
        say "In Foo";
        }
    }

foo( 137 );

Running this, I get a compilation error (which I think is a bit odd for a dynamic language):

===SORRY!=== Error while compiling /Users/brian/Desktop/multi.pl
Undeclared routine:
    foo used at line 9

Reading the Perl 6 "Modules" documentation, I don't see any way to do this since the various verbs want to look in a particular file.

Scimon Proctor
  • 4,558
  • 23
  • 22
brian d foy
  • 129,424
  • 31
  • 207
  • 592
  • > I get a compilation error (which I think is a bit odd for a dynamic language) Have you glanced thru jnthn's excellent PDF [Getting beyond static vs. dynamic](http://www.jnthn.net/papers/2015-fosdem-static-dynamic.pdf)? (jnthn was ill at the time and there are other minor issues so [his live presentation](https://www.youtube.com/watch?v=id4pDstMu1s&index=19&list=PLRuESFRW2Fa77XObvk7-BYVFwobZHdXdK) isn't great but it's OK.) – raiph Jan 09 '16 at 03:30
  • @raiph I read that a long time ago, but I think you'll have to say more to make a point. – brian d foy Jan 09 '16 at 03:40
  • Aiui Perl 6 is in part a static language, eg being generally able to do type checking and dispatch resolution for multisubs (eg operators) and private methods at compile-time. I took your "odd" comment to mean you did not see things that way and wondered if you'd seen jnthn's presentation. – raiph Jan 09 '16 at 06:06

1 Answers1

7

Subroutine declarations are lexical, so &foo is invisible outside of the module's body. You need to add an import statement to the mainline code to make it visible:

module Foo {
    sub foo ( Int:D $number ) is export { ... }
}

import Foo;
foo( 137 );

Just for the record, you could also manually declare a &foo variable in the mainline and assign to that from within the module:

my &foo;

module Foo {
    sub foo ( Int:D $number ) { ... } # no export necessary

    &OUTER::foo = &foo;
}

foo( 137 );
Christoph
  • 164,997
  • 36
  • 182
  • 240
  • 1
    The `import` is what I'm looking for. Where is that documented? – brian d foy Jan 09 '16 at 01:40
  • 2
    there's the [design docs](http://design.perl6.org/S11.html#Importing_without_loading) and the [user documentation](http://doc.perl6.org/language/modules); for this specific case, the design docs are more clear – Christoph Jan 09 '16 at 01:44
  • 3
    note that the design docs do not correspond to the reality of 6.c: `import` does not support positional symbol names without an explicit `&EXPORT` sub, just tags via named `:adverbs` – Christoph Jan 09 '16 at 01:48