2

In my Mojolicious Controller, I have:

my @promise;
foreach my $code (\&doit1, \&doit2,) {
    my $prom = Mojo::Promise->new;
    Mojo::IOLoop->subprocess(
    sub {
        my $r = $code->("Hello");
        return $r;
    },
    sub {
        my ($subprocess, $err, @res) = @_;
        return $prom->reject($err) if $err;
        $prom->resolve(@res);
    },
    );
    push @promise, $prom;
}

Mojo::Promise
    ->all(@promise)
    ->then(
    sub {
    my ($result1, $result2) = map {$_->[0]} @_;
    });

This works, and I can pass arguments (e.g. Hello) to my sub.

Now I converted doti1() and doit2() as helpers. So the code looks like:

foreach my $code (sub {$self->myhelper->doit1("Goodbye")},
                  sub {$self->myhelper->doit2("Good night")},
    ) {
    my $prom = Mojo::Promise->new;
    Mojo::IOLoop->subprocess(
    sub {
        my $r = $code->("Hello"); # this is ignored?
        return $r;
    },
    sub {
        my ($subprocess, $err, @res) = @_;
        return $prom->reject($err) if $err;
        $prom->resolve(@res);
    },
    );
    push @promise, $prom;
}

How can I continue to pass the same set of arguments inside the loop (e.g. Hello), without having to specify them in each code ref (i.e. avoid Goodbye & Good night)? I like the idea of passing the same arguments for each code ref: $code->("Hello")

h q
  • 1,168
  • 2
  • 10
  • 23

2 Answers2

5

Now I converted doti1() and doit2() as helpers. So the code looks like:

foreach my $code (sub {$self->myhelper->doit1("Goodbye")},
                  sub {$self->myhelper->doit2("Good night")},
    ) {
    #....
}

Yes but you are calling the helpers from another anonymous sub,

How can I continue to pass the same set of arguments inside the loop (e.g. Hello), without having to specify them in each code ref

so to recover the argument and pass it on the the helper, you just do:

foreach my $code (sub {my $arg = shift; $self->myhelper->doit1($arg)},
                  sub {my $arg = shift; $self->myhelper->doit2($arg)},
) {...}

or more generally as @Dada pointed out in the comments:

foreach my $code (sub {$self->myhelper->doit1(@_)},
                  sub {$self->myhelper->doit2(@_)},
) {...}
Håkon Hægland
  • 39,012
  • 21
  • 81
  • 174
3

Just a comment...

The following was previously suggested:

for my $code (
   sub { $self->myhelper->doit1( @_ ) },
   sub { $self->myhelper->doit2( @_ ) },
) {
   ...
   $code->( "Hello" )
   ...
}

It could also be written as follows:

for my $method (qw( doit1 doit2 )) {
   ...
   $self->myhelper->$method( "Hello" )
   ...
}

It's a less general solution, but it's simpler and faster.

You might even want to factor out obtaining the helper.

my $myhelper = $self->myhelper;

for my $method (qw( doit1 doit2 )) {
   ...
   $myhelper->$method( "Hello" )
   ...
}
ikegami
  • 367,544
  • 15
  • 269
  • 518