You can also pass a "return value" to the next step via the delay callback (e.g. $end->($rows) => my ($delay, $rows) = @_). But the first argument is left out unless you pass a 0 to $delay->begin, this is because most non-blocking methods will pass their object as the first parameter. I tend to use the delay data() more for things like timer IDs, or data not specific to one step; you could store the timer ID this way after creating the recurring timer. This is all just stylistic and for clarity of course.
On Wed, Apr 22, 2015 at 12:32 PM, hammondos <[email protected]> wrote: > Thank you! For the record, this appears to do the job: > > my $r_id; > $self->delay( > sub { > my $delay = shift; > my $end = $delay->begin; > $r_id = Mojo::IOLoop->recurring( > 1 => sub { > if (my $results = $sc_api->check_queue($report_id)) { > my $rows = $sc_api->process_os($results); > &_insert_data({domain => $domain, path => $path, data > => {os => $rows}}); > $delay->data(rows => $rows); > $end->(); > } > } > ); > }, > sub { > my $delay = shift; > Mojo::IOLoop->remove($r_id); > $self->render(json => $delay->data('rows')); > } > ); > > > > On Wednesday, 22 April 2015 15:15:22 UTC+1, Dan Book wrote: >> >> Also, to stop the recurring timer, save the returned id (you can store it >> in the delay as well) and then remove it from the loop after a success (for >> example in the next step). >> >> On Wed, Apr 22, 2015 at 10:14 AM, Dan Book <[email protected]> wrote: >> >>> You need to save the return value of $delay->begin, that returns a >>> callback that you need to call in order to proceed to the next step, like >>> in the timer example you were looking at before. >>> >>> On Wed, Apr 22, 2015 at 3:10 AM, hammondos <[email protected]> wrote: >>> >>>> Ok so I've adapted the script to use the delay helper, and based on the >>>> documentation it seems like this should work, but still can't seem to exit >>>> from the recurring loop. >>>> >>>> Feels like the placement of $delay->begin is wrong or I'm not using the >>>> right signal to say the recurring loop should be stopped - return doesn't >>>> seem right but have also tried $loop->stop & $loop->reset with no luck. Any >>>> ideas? >>>> >>>> $self->delay( >>>> sub { >>>> my $delay = shift; >>>> $delay->begin; >>>> Mojo::IOLoop->recurring( >>>> 1 => sub { >>>> if (my $results = $sc_api->check_queue($report_id)) { >>>> my $rows = $sc_api->process_os($results); >>>> $log->info(Dumper($rows)); >>>> &_insert_data({domain => $domain, path => $path, >>>> data => {os => $rows}}); >>>> $delay->data(rows => $rows); >>>> return; >>>> } >>>> } >>>> ); >>>> }, >>>> sub { >>>> my $delay = shift; >>>> $self->render(json => $delay->data('rows')); >>>> } >>>> ); >>>> >>>> >>>> >>>> On Tuesday, 21 April 2015 22:17:35 UTC+1, hammondos wrote: >>>>> >>>>> Ok cool, thanks for pointing me in the right direction >>>>> >>>>> On Tuesday, 21 April 2015 22:10:36 UTC+1, Dan Book wrote: >>>>>> >>>>>> Sort of. You want the delay helper here: >>>>>> https://metacpan.org/pod/Mojolicious::Plugin::DefaultHelpers#delay >>>>>> >>>>>> That creates a Mojo::IOLoop delay as well, but also does all the >>>>>> things I described before relevant to rendering. You won't be able to do >>>>>> a >>>>>> recurring timer exactly the same way, as you can't set up begin() >>>>>> callbacks >>>>>> in advance since you don't know how many there will be. You will want to >>>>>> just create a recurring timer in the first step, get the callback from >>>>>> $delay->begin, and you can have that call $end->() to proceed to the next >>>>>> step when you get a success. >>>>>> >>>>>> On Tue, Apr 21, 2015 at 4:58 PM, hammondos <[email protected]> >>>>>> wrote: >>>>>> >>>>>>> Great, thanks - so something like the code example from here >>>>>>> <http://mojolicio.us/perldoc/Mojo/IOLoop#delay>? Not sure how to >>>>>>> replace the timer with recurring logic though >>>>>>> >>>>>>> # Synchronize multiple eventsmy $delay = Mojo::IOLoop->delay(sub { say >>>>>>> 'BOOM!' });for my $i (1 .. 10) { >>>>>>> my $end = $delay->begin; >>>>>>> Mojo::IOLoop->timer($i => sub { >>>>>>> say 10 - $i; >>>>>>> $end->(); >>>>>>> });} >>>>>>> $delay->wait; >>>>>>> >>>>>>> >>>>>>> >>>>>>> >>>>>>> On Tuesday, 21 April 2015 21:41:48 UTC+1, Dan Book wrote: >>>>>>>> >>>>>>>> The finish event of the controller is not really appropriate here. >>>>>>>> It will not fire until the transaction is finished, which doesn't >>>>>>>> happen >>>>>>>> until you render a response. So once a success happens you want to call >>>>>>>> something that will render a response from there. You probably want to >>>>>>>> use >>>>>>>> the delay helper which will turn off automatic rendering, keep a >>>>>>>> reference >>>>>>>> to the transaction, and handle exceptions. >>>>>>>> >>>>>>>> On Tue, Apr 21, 2015 at 3:39 PM, hammondos <[email protected]> >>>>>>>> wrote: >>>>>>>> >>>>>>>>> Hi, >>>>>>>>> >>>>>>>>> I'm trying to run an AJAX call that needs to check an external API >>>>>>>>> queue for a response every second, then generate a chart based on >>>>>>>>> that data >>>>>>>>> using JSON. >>>>>>>>> >>>>>>>>> The code sample from the module I'm using to connect to the API >>>>>>>>> suggests using a for...sleep loop, however clearly this doesn't work >>>>>>>>> with >>>>>>>>> Mojolicious. >>>>>>>>> >>>>>>>>> I've tried several different permutations of using a recurring >>>>>>>>> loop with varying degrees of success, but just can't get it to work - >>>>>>>>> latest example below. This example never exits, even when there is >>>>>>>>> data >>>>>>>>> returned. >>>>>>>>> >>>>>>>>> I'm aware that the $success parameter is probably not helping the >>>>>>>>> situation, but would really appreciate any guidance on where to go >>>>>>>>> next to >>>>>>>>> stop the loop once a successful response has been received, and >>>>>>>>> render a >>>>>>>>> JSON response. >>>>>>>>> >>>>>>>>> my $success = 0; >>>>>>>>> my $id = Mojo::IOLoop->recurring( >>>>>>>>> 1 => sub { >>>>>>>>> $self->finish if $success == 1; >>>>>>>>> if (my $results = $sc_api->check_queue($report_id)) { >>>>>>>>> my $rows = $sc_api->process_os($results); >>>>>>>>> $log->info(Dumper($rows)); >>>>>>>>> &_insert_data({domain => $domain, path => $path, data >>>>>>>>> => {os => $rows}}); >>>>>>>>> $success = 1; >>>>>>>>> } >>>>>>>>> } >>>>>>>>> ); >>>>>>>>> >>>>>>>>> # need to wait >>>>>>>>> $self->on(finish => sub { >>>>>>>>> # remove ioloop >>>>>>>>> Mojo::IOLoop->remove($id); >>>>>>>>> >>>>>>>>> my $db = $self->db; >>>>>>>>> my $analytics = $db->get_collection('analytics'); >>>>>>>>> my $rows = $analytics->find({id => $url}); >>>>>>>>> my $doc = $rows->next; >>>>>>>>> $self->render(json => $doc->{'analytics'}->{'os'}); >>>>>>>>> }); >>>>>>>>> >>>>>>>>> >>>>>>>>> -- >>>>>>>>> You received this message because you are subscribed to the Google >>>>>>>>> Groups "Mojolicious" group. >>>>>>>>> To unsubscribe from this group and stop receiving emails from it, >>>>>>>>> send an email to [email protected]. >>>>>>>>> To post to this group, send email to [email protected]. >>>>>>>>> Visit this group at http://groups.google.com/group/mojolicious. >>>>>>>>> For more options, visit https://groups.google.com/d/optout. >>>>>>>>> >>>>>>>> >>>>>>>> -- >>>>>>> You received this message because you are subscribed to the Google >>>>>>> Groups "Mojolicious" group. >>>>>>> To unsubscribe from this group and stop receiving emails from it, >>>>>>> send an email to [email protected]. >>>>>>> To post to this group, send email to [email protected]. >>>>>>> Visit this group at http://groups.google.com/group/mojolicious. >>>>>>> For more options, visit https://groups.google.com/d/optout. >>>>>>> >>>>>> >>>>>> -- >>>> You received this message because you are subscribed to the Google >>>> Groups "Mojolicious" group. >>>> To unsubscribe from this group and stop receiving emails from it, send >>>> an email to [email protected]. >>>> To post to this group, send email to [email protected]. >>>> Visit this group at http://groups.google.com/group/mojolicious. >>>> For more options, visit https://groups.google.com/d/optout. >>>> >>> >>> >> -- > You received this message because you are subscribed to the Google Groups > "Mojolicious" group. > To unsubscribe from this group and stop receiving emails from it, send an > email to [email protected]. > To post to this group, send email to [email protected]. > Visit this group at http://groups.google.com/group/mojolicious. > For more options, visit https://groups.google.com/d/optout. > -- You received this message because you are subscribed to the Google Groups "Mojolicious" group. To unsubscribe from this group and stop receiving emails from it, send an email to [email protected]. To post to this group, send email to [email protected]. Visit this group at http://groups.google.com/group/mojolicious. For more options, visit https://groups.google.com/d/optout.
