mojo


From Sebastian Riedel

perl -Mojo -E'say g("mojolicio.us")->dom("*")->pluck("type")->uniq'

perl -Mojo -E'g("metacpan.org/search?q=mojo")->dom("big a")
->pluck("text")->join("\n")->spurt("m.txt")'

perl -Mojo -E'say g("reddit.com")->dom("*")->pluck(attrs => "href")
->grep(qr/^http/)->uniq'

perl -Mojo -E'say r g("search.twitter.com/search.json?q=perl")->json'

perl -Mojo -E'a({json => {foo => ["bar"]}})->start' get / /foo/0

perl -Mojo -E'g("mojolicio.us")->dom("h1, h2, h3")->map(sub { $_->text })
->shuffle->join("\n")->say'

mojo get www.reddit.com/r/perl/ 'p.title > a.title' text

perl -Mojo -E'say a->text_field("foo", value => "bar")'

perl -Mojo -E'a("/:name" => {inline => "Hi !"})->start' get -v /foo

perl -Mojo -E 'a(sub { shift->render(json => {time => time}) })
->start' daemon

(See mojolicio.us/perldoc/ojo for more, and also the mailing list archives.)

Advertisements

Authenticate user

From Ben van Staveren

validate_user => sub {
  my ($c, $username, $password, $extra) = (@_);

  if(MyUsers->login($username, $password) == 1) {
    return $username;
  } else {
    $c->stash(login_error_message => 'Invalid credentials');
    return undef;
  }
};

load_user => sub {
   my ($c, $uid) = (@_);

   return MyUsers->get_user_data_for_username($uid);
};

And then you want to:

my $r = $self->routes->bridge('/')->to('login#check');
$r->get('/protected')->to('....');

The 'check' method in login can simply do this:

sub check {
  my $self = shift;

  return 1 if $self->is_user_authenticated;
  $self->render('login_form') and return 0;
}

Anything now routed under $r goes through the login check. If you want "public" and "private" bits, do it like this:

my $public = $self->routes->any('/')->to('public_site#index);
my $private = $public->bridge('/')->to('login#check');

$private->get('/')->to('private_site#index');

Async page prep

From s at bykov.odessa.ua

$app->hook(
    around_dispatch => sub {
      my ($next, $c) = @_;

      # grab a title from mojolicio.us
      $c->ua->get(
        'http://mojolicio.us' => sub {
          my ($ua, $tx) = @_;

          my $res = $tx->success;
          my $mytitle = $res ? $res->dom->at("title")->text : "Error";

          # stash
          $c->stash(mytitle => $mytitle);

          # Now we are ready
          $next->();
        }
      );


    }
  );

Render pdf from memory

From Pavel Goloborodko

$self->res->headers
    ->content_disposition("attachment;filename=${name}.pdf");
$self->res->headers->content_type('application/pdf');
$self->render_data( $pdf );

When debugging code that uses attributes, as provided by Mojo::Base, it sometimes helps to visualise what its getter/setter actually looks like.

A getter/setter with defined default.

{
package MyClass;
sub my_attr {
  if (@_ == 1) {
    return $_[0]{'my_attr'} if exists $_[0]{'my_attr'};
    return $_[0]{'my_attr'} = $default->($_[0]);
  }
  $_[0]{'my_attr'} = $_[1];
  $_[0];
}
1;
}

A getter/setter without default.

{
package MyClass;
sub my_attr {
  if (@_ == 1) {
    return $_[0]{'my_attr'};
  }
  $_[0]{'my_attr'} = $_[1];
  $_[0];
}
1;
}

You can see your own attribute definitions via

export MOJO_BASE_DEBUG=1
./my_script eval 1
unset MOJO_BASE_DEBUG

Obviously there is a lot of advocacy at mojocasts and mojolicio.us, but there are a lot of useful posts outside those channels, for example in PerlMonks and StackOverflow.

Security

Beginner apps with database

 

 

When a director gives you a line reading that doesn’t feel right for your character, nod and agree with him or her, then do it the way you know your character would do it. If you’re an actor, always be true to your character; if you’re not an actor, have character, and always be true to yourself… Whatever you do, wherever you go, do something real, make a real product, provide a real service, do something of value. Create something of beauty. — Robert De Niro at Bates

A nice example of Mojolicious code as a proxy service. This is thanks to xaka at gist.


use Mojo::UserAgent;
use Mojo::Server::Daemon;

my $ua = Mojo::UserAgent->new;
my $daemon = Mojo::Server::Daemon->new(
  listen => ['https://*:443']
)->unsubscribe('request');
$daemon->on(request => sub {
  my ($daemon, $tx) = @_;

  my $req = $tx->req->clone;
  $req->url->scheme("https")->host("10.3.199.40");

  $ua->start(Mojo::Transaction::HTTP->new(req => $req) => sub {
    my ($ua, $proxy_tx) = @_;
    $tx->res($proxy_tx->res)->resume;
  });
});
$daemon->run;

If you are in the habit of setting Mojolicious environment variables in your shell, you should remember to unset them (at least MOJO_LOG_LEVEL) before upgrading your Mojolicious framework, otherwise it can fail its tests and fail to install.

unset MOJO_LOG_LEVEL
HARNESS_OPTIONS=j9 cpanm -l /srv/mojo Mojolicious Mojoliciuos::Plugin::Authentication

There are a handful of variables that can be handy when working with Mojolicious, so I decided to collect them together.

Installing CPAN modules

HARNESS_OPTIONS=j9 cpanm -l /srv/mojo Mojolicious

… specifies the degree of concurrency for the perl tests when building.

User agent

MOJO_USERAGENT_DEBUG=1 ./my_useragent.pl

… turns on debugging so it outputs request-response messages.

Daemon

MOJO_NO_IPV6=1 morbo -v -l 'http://*:8088' -w mod -w tmpl myapp

… turns off ipv6 support.

MOJO_NO_TLS=1 /srv/mojo/bin/hypnotoad myapp

… turns off TLS support.

MOJO_MODE=production …

… sets the run mode.

MOJO_LOG_LEVEL=debug …

… sets the debug level.

Commands

MOJO_NO_DETECT=1

… disables deployment environment detection.

Next Page »