Mojolicious

 view release on metacpan or  search on metacpan

lib/Mojolicious/Guides/Growing.pod  view on Meta::CPAN


  # Test if the HTML login form exists
  $t->get_ok('/')
    ->status_is(200)
    ->element_exists('form input[name="user"]')
    ->element_exists('form input[name="pass"]')
    ->element_exists('form input[type="submit"]');

  # Test login with valid credentials
  $t->post_ok('/' => form => {user => 'sebastian', pass => 'secr3t'})
    ->status_is(200)
    ->text_like('html body' => qr/Welcome sebastian/);

  # Test accessing a protected page
  $t->get_ok('/protected')->status_is(200)->text_like('a' => qr/Logout/);

  # Test if HTML login form shows up again after logout
  $t->get_ok('/logout')
    ->status_is(200)
    ->element_exists('form input[name="user"]')
    ->element_exists('form input[name="pass"]')
    ->element_exists('form input[type="submit"]');

  done_testing();

Your application won't pass these tests, but from now on you can use them to check your progress.

  $ prove -l
  $ prove -l t/login.t
  $ prove -l -v t/login.t

Or perform quick requests right from the command line with L<Mojolicious::Command::get>.

  $ ./myapp.pl get /
  Wrong username or password.

  $ ./myapp.pl get -v '/?user=sebastian&pass=secr3t'
  GET /?user=sebastian&pass=secr3t HTTP/1.1
  User-Agent: Mojolicious (Perl)
  Accept-Encoding: gzip
  Content-Length: 0
  Host: localhost:59472

  HTTP/1.1 200 OK
  Date: Sun, 18 Jul 2010 13:09:58 GMT
  Server: Mojolicious (Perl)
  Content-Length: 12
  Content-Type: text/plain

  Welcome sebastian.

=head2 State keeping

Sessions in L<Mojolicious> pretty much just work out of the box once you start using the method
L<Mojolicious::Controller/"session">, there is no setup required, but we suggest setting a more secure passphrase with
L<Mojolicious/"secrets">.

  app->secrets(['Mojolicious rocks']);

This passphrase is used by the HMAC-SHA256 algorithm to make signed cookies tamper resistant and can be changed at any
time to invalidate all existing sessions.

  $c->session(user => 'sebastian');
  my $user = $c->session('user');

By default all sessions expire after one hour, for more control you can use the C<expiration> session value to set an
expiration date in seconds from now.

  $c->session(expiration => 3600);

And the whole session can be deleted by using the C<expires> session value to set an absolute expiration date in the
past.

  $c->session(expires => 1);

For data that should only be visible on the next request, like a confirmation message after a C<302> redirect performed
with L<Mojolicious::Plugin::DefaultHelpers/"redirect_to">, you can use the flash, accessible through
L<Mojolicious::Plugin::DefaultHelpers/"flash">.

  $c->flash(message => 'Everything is fine.');
  $c->redirect_to('goodbye');

Just remember that all session data gets serialized with L<Mojo::JSON> and stored in HMAC-SHA256 signed cookies, which
usually have a C<4096> byte (4KiB) limit, depending on browser.

=head2 Final prototype

A final C<myapp.pl> prototype passing all of the tests above could look like this.

  #!/usr/bin/env perl
  use Mojolicious::Lite -signatures;

  use lib qw(lib);
  use MyApp::Model::Users;

  # Make signed cookies tamper resistant
  app->secrets(['Mojolicious rocks']);

  helper users => sub { state $users = MyApp::Model::Users->new };

  # Main login action
  any '/' => sub ($c) {

    # Query or POST parameters
    my $user = $c->param('user') || '';
    my $pass = $c->param('pass') || '';

    # Check password and render "index.html.ep" if necessary
    return $c->render unless $c->users->check($user, $pass);

    # Store username in session
    $c->session(user => $user);

    # Store a friendly message for the next page in flash
    $c->flash(message => 'Thanks for logging in.');

    # Redirect to protected page with a 302 response
    $c->redirect_to('protected');
  } => 'index';

  # Make sure user is logged in for actions in this group



( run in 2.363 seconds using v1.01-cache-2.11-cpan-39bf76dae61 )