SlideShare ist ein Scribd-Unternehmen logo
1 von 152
Downloaden Sie, um offline zu lesen
Perl 6
in Production
15 years of development
Ready December 2015
This December
Start using?
Perl 6 for
Web
Development
What’s wrong
with Perl 6?
What’s wrong
with today’s Perl 6?
Not that it is too late
Rather that it is too mature
Lots of blog posts
Lots of documentation
Lots of code examples
Lots of errors
Everything
has been googled
Not easy to find how
this or that works
Most of code examples
and modules are outdated
Outdated before
the release!
Nothing works!
Even if it used to work
===SORRY!===	
  
Error	
  while	
  compiling	
  	
  
!
Undeclared	
  routine:	
  
	
  	
  	
  eval	
  used	
  at	
  line	
  7.	
  
	
  	
  	
  Did	
  you	
  mean	
  'val'?
===SORRY!===	
  
Error	
  while	
  compiling	
  	
  
!
Undeclared	
  routine:	
  
	
  	
  	
  eval	
  used	
  at	
  line	
  7.	
  
	
  	
  	
  Did	
  you	
  mean	
  'val'?
(useEVAL)
A bit of history
2000
Perl 6 announced
First implementations
Parrot
Parrot with Perl 6 compiler
Pugs
Pugs, the Perl 6 compiler
Rakudo
Rakudo Star
Past
2004
real.perl6.ru
http://web.archive.org/web/*/real.perl6.ru
Some examples
of the code of 2004
Reading
environment variables
my	
  @keys	
  =	
  ('SERVER_NAME',	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  'REMOTE_ADDR',	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  'HTTP_USER_AGENT');	
  
!
my	
  $key;	
  
foreach	
  $key	
  (@keys){	
  
	
  	
  print	
  "$key=%ENV{$key}<br	
  />n";	
  
}
Looks almost like Perl 5
my	
  @keys	
  =	
  ('SERVER_NAME',	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  'REMOTE_ADDR',	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  'HTTP_USER_AGENT');	
  
!
my	
  $key;	
  
foreach	
  $key	
  (@keys){	
  
	
  	
  print	
  "$key=%ENV{$key}<br	
  />n";	
  
}
You could learn Perl 6
in a few hours
Setting/getting cookies
print	
  "Content-­‐Type:	
  text/htmln"	
  
print	
  'Set-­‐Cookie:	
  cookie-­‐
name=test-­‐value;	
  path=/;nn';	
  
!
print	
  %ENV{'HTTP_COOKIE'};
URL GET parameters
read_params	
  (	
  
	
  	
  	
  	
  %ENV{'QUERY_STRING'},	
  	
  
	
  	
  	
  	
  @params_key,	
  
	
  	
  	
  	
  @params_value	
  
);
sub	
  read_params	
  ($query,	
  @params_key,	
  
@params_value){	
  
	
  	
  	
  my	
  $pos	
  =	
  0;	
  
	
  	
  	
  loop	
  (my	
  $c	
  =	
  0;	
  1;	
  $c++)	
  {	
  
	
  	
  	
  	
  	
  	
  my	
  $newpos	
  =	
  index	
  ($query,	
  '&',	
  $pos);	
  
	
  	
  	
  	
  	
  	
  my	
  @keyvalue;	
  
	
  	
  	
  	
  	
  	
  my	
  $pair	
  =	
  substr	
  ($query,	
  $pos,	
  $newpos	
  
==	
  -­‐1	
  ??	
  length	
  ($query)	
  ::	
  $newpos	
  -­‐	
  $pos);	
  
	
  	
  	
  	
  	
  	
  split_pair	
  ($pair,	
  @keyvalue);	
  
	
  	
  	
  	
  	
  	
  @params_key[$c]	
  =	
  @keyvalue[0];	
  
	
  	
  	
  	
  	
  	
  @params_value[$c]	
  =	
  @keyvalue[1];	
  
	
  	
  	
  	
  	
  	
  last	
  if	
  $newpos	
  ==	
  -­‐1;	
  
	
  	
  	
  	
  	
  	
  $pos	
  =	
  $newpos	
  +	
  1;	
  
	
  	
  	
  }	
  
}
sub	
  read_params	
  ($query,	
  @params_key,	
  
@params_value){	
  
	
  	
  	
  my	
  $pos	
  =	
  0;	
  
	
  	
  	
  loop	
  (my	
  $c	
  =	
  0;	
  1;	
  $c++)	
  {	
  
	
  	
  	
  	
  	
  	
  my	
  $newpos	
  =	
  index	
  ($query,	
  '&',	
  $pos);	
  
	
  	
  	
  	
  	
  	
  my	
  @keyvalue;	
  
	
  	
  	
  	
  	
  	
  my	
  $pair	
  =	
  substr	
  ($query,	
  $pos,	
  $newpos	
  
==	
  -­‐1	
  ??	
  length	
  ($query)	
  ::	
  $newpos	
  -­‐	
  $pos);	
  
	
  	
  	
  	
  	
  	
  split_pair	
  ($pair,	
  @keyvalue);	
  
	
  	
  	
  	
  	
  	
  @params_key[$c]	
  =	
  @keyvalue[0];	
  
	
  	
  	
  	
  	
  	
  @params_value[$c]	
  =	
  @keyvalue[1];	
  
	
  	
  	
  	
  	
  	
  last	
  if	
  $newpos	
  ==	
  -­‐1;	
  
	
  	
  	
  	
  	
  	
  $pos	
  =	
  $newpos	
  +	
  1;	
  
	
  	
  	
  }	
  
}
sub	
  split_pair	
  ($pair,	
  @keyvalue){	
  
	
  	
  	
  my	
  $pos	
  =	
  index	
  ($pair,	
  '=');	
  
	
  	
  	
  if	
  ($pos	
  ==	
  -­‐1){	
  
	
  	
  	
  	
  	
  	
  @keyvalue[0]	
  =	
  $pair;	
  
	
  	
  	
  	
  	
  	
  @keyvalue[1]	
  =	
  '';	
  
	
  	
  	
  }	
  
	
  	
  	
  else{	
  
	
  	
  	
  	
  	
  	
  @keyvalue[0]	
  =	
  substr	
  ($pair,	
  0,	
  $pos);	
  
	
  	
  	
  	
  	
  	
  @keyvalue[1]	
  =	
  substr	
  ($pair,	
  $pos	
  +	
  1);	
  
	
  	
  	
  }	
  
}	
  
URL GET parameters
using hashes
sub	
  params2hash	
  (%params,	
  @params_key,	
  
@params_value){	
  
	
  	
  	
  for	
  0	
  ..	
  @params_key	
  -­‐>	
  $c{	
  
	
  	
  	
  	
  	
  	
  %params{@params_key[$c]}	
  =	
  
	
  	
  	
  	
  	
  	
  @params_value[$c];	
  
	
  	
  	
  }	
  
}	
  
!
read_params	
  (%ENV{'QUERY_STRING'},	
  @params_key,	
  
@params_value);	
  
my	
  %params;	
  
params2hash	
  (%params,	
  @params_key,	
  
@params_value);
To speed it up
Compiling to bytecode
.pasm
.imc
100% compatible
2007/2008
november-wiki.org
https://github.com/viklund/november
November::CGI
class	
  November::CGI	
  {	
  
	
  	
  	
  	
  has	
  %.params;	
  
	
  	
  	
  	
  has	
  %.cookie;	
  
	
  	
  	
  	
  has	
  @.keywords;	
  
	
  	
  	
  	
  has	
  November::URI	
  $.uri;
self.parse_params(%*ENV<QUERY_STRING>	
  //	
  '');
has	
  $!crlf	
  =	
  "x[0D]x[0A]";	
  	
  	
  	
  
	
  	
  	
  	
  .	
  .	
  .	
  
!
print	
  "Status:	
  $status$!crlf";	
  
print	
  "Location:	
  $uri";	
  
print	
  "$!crlf$!crlf";
has	
  $!crlf	
  =	
  "x[0D]x[0A]";	
  	
  	
  	
  
	
  	
  	
  	
  .	
  .	
  .	
  
!
print	
  "Status:	
  $status$!crlf";	
  
print	
  "Location:	
  $uri";	
  
print	
  "$!crlf$!crlf";
Compare
https://p6weekly.wordpress.com/2015/11/09/2015-46-
production-today/
Smartmatch and junctions
method	
  add_param	
  (	
  Str	
  $key,	
  $value	
  )	
  {	
  
	
  	
  	
  	
  	
  	
  if	
  %.params{$key}	
  :exists	
  {	
  
	
  	
  	
  	
  	
  	
  #	
  RAKUDO:	
  ~~	
  Scalar	
  
	
  	
  	
  	
  	
  	
  if	
  %.params{$key}	
  ~~	
  Str	
  |	
  Int	
  {	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  my	
  $old_param	
  =	
  %.params{$key};	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  %!params{$key}	
  =	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  [	
  $old_param,	
  $value	
  ];	
  
	
  	
  	
  	
  	
  	
  }	
  
	
  	
  	
  	
  	
  	
  elsif	
  %.params{$key}	
  ~~	
  Array	
  {	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  %!params{$key}.push(	
  $value	
  );	
  
	
  	
  	
  	
  	
  	
  }	
  
	
  	
  	
  	
  	
  	
  }	
  
	
  	
  	
  	
  	
  	
  else	
  {	
  
	
  	
  	
  	
  	
  	
  %!params{$key}	
  =	
  $value;	
  
	
  	
  	
  	
  	
  	
  }	
  
}	
  
Compiler incompatibilities
method	
  add_param	
  (	
  Str	
  $key,	
  $value	
  )	
  {	
  
	
  	
  	
  	
  	
  	
  if	
  %.params{$key}	
  :exists	
  {	
  
	
  	
  	
  	
  	
  	
  #	
  RAKUDO:	
  ~~	
  Scalar	
  
	
  	
  	
  	
  	
  	
  if	
  %.params{$key}	
  ~~	
  Str	
  |	
  Int	
  {	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  my	
  $old_param	
  =	
  %.params{$key};	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  %!params{$key}	
  =	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  [	
  $old_param,	
  $value	
  ];	
  
	
  	
  	
  	
  	
  	
  }	
  
	
  	
  	
  	
  	
  	
  elsif	
  %.params{$key}	
  ~~	
  Array	
  {	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  %!params{$key}.push(	
  $value	
  );	
  
	
  	
  	
  	
  	
  	
  }	
  
	
  	
  	
  	
  	
  	
  }	
  
	
  	
  	
  	
  	
  	
  else	
  {	
  
	
  	
  	
  	
  	
  	
  %!params{$key}	
  =	
  $value;	
  
	
  	
  	
  	
  	
  	
  }	
  
}	
  
if	
  %*ENV<MODPERL6>	
  {	
  
	
  	
  	
  	
  	
  my	
  $r	
  =	
  Apache::RequestRec.new();	
  
	
  	
  	
  	
  	
  my	
  $len	
  =	
  $r.read($input,	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  %*ENV<CONTENT_LENGTH>);	
  
}	
  
else	
  {	
  
	
  	
  	
  	
  	
  	
  #	
  Maybe	
  check	
  content_length	
  here	
  	
  
	
  	
  	
  	
  	
  	
  #	
  and	
  only	
  take	
  that	
  many	
  bytes?	
  
	
  	
  	
  	
  	
  	
  $input	
  =	
  $*IN.slurp;	
  
}	
  
!
(I never managed
to install mod_parrot)
Grammar for URL parsing
grammar	
  November::URI::Grammar	
  {	
  
	
  	
  	
  	
  token	
  TOP	
  	
  	
  	
  	
  	
  	
  	
  {	
  ^	
  [<scheme>	
  ':']?	
  	
  
	
  	
  	
  	
  	
  	
  	
  [	
  '//'	
  <authority>]?	
  	
  
	
  	
  	
  	
  	
  	
  	
  <path>	
  ['?'	
  <query>]?	
  ['#'	
  <fragment>]?	
  $	
  };	
  
	
  	
  	
  	
  token	
  scheme	
  	
  	
  	
  	
  {	
  <-­‐[:/&?#]>+	
  };	
  
	
  	
  	
  	
  token	
  authority	
  	
  {	
  <host>	
  [':'	
  <port>]?	
  };	
  
	
  	
  	
  	
  token	
  host	
  	
  	
  	
  	
  	
  	
  {	
  <-­‐[/&?#:]>*	
  };	
  
	
  	
  	
  	
  token	
  port	
  	
  	
  	
  	
  	
  	
  {	
  (d**1..5)	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  <?{	
  $0	
  <	
  2	
  **	
  16	
  }>	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  <!before	
  d>	
  };	
  
	
  	
  	
  	
  token	
  path	
  	
  	
  	
  	
  	
  	
  {	
  <slash>?	
  [	
  <chunk>	
  '/'?]*	
  };	
  
	
  	
  	
  	
  token	
  slash	
  	
  	
  	
  	
  	
  {	
  '/'	
  };	
  
	
  	
  	
  	
  token	
  chunk	
  	
  	
  	
  	
  	
  {	
  <-­‐[/?#]>+	
  };	
  
	
  	
  	
  	
  token	
  query	
  	
  	
  	
  	
  	
  {	
  <-­‐[#]>*	
  };	
  
	
  	
  	
  	
  token	
  fragment	
  	
  	
  {	
  .*	
  };	
  
}
#	
  Official	
  regexp	
  (p5):	
  
#	
  my($scheme,	
  $authority,	
  $path,	
  $query,	
  $fragment)	
  =	
  
#	
  $uri	
  =~	
  m/	
  
#	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  (?:([^:/?#]+):)?	
  
#	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  (?://([^/?#]*))?	
  
#	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  ([^?#]*)	
  
#	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  (?:?([^#]*))?	
  
#	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  (?:#(.*))?	
  
#	
  	
  	
  	
  	
  	
  	
  	
  	
  /x;
Not like Perl 5 any more :-)
2011
Plackdo
https://github.com/lopnor/p6-plackdo
Plack-like web interface
on Perl 6
my	
  $app	
  =	
  sub	
  (%env)	
  {	
  
	
  	
  	
  	
  return	
  (	
  
	
  	
  	
  	
  	
  	
  	
  	
  200,	
  
	
  	
  	
  	
  	
  	
  	
  	
  [	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  Content-­‐Type	
  =>	
  'text/plain',	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  Content-­‐Length	
  =>	
  %env.perl.bytes,	
  
	
  	
  	
  	
  	
  	
  	
  	
  ],	
  
	
  	
  	
  	
  	
  	
  	
  	
  [	
  %env.perl	
  ]	
  
	
  	
  	
  	
  );	
  
};
HTTP status code
my	
  $app	
  =	
  sub	
  (%env)	
  {	
  
	
  	
  	
  	
  return	
  (	
  
	
  	
  	
  	
  	
  	
  	
  	
  200,	
  
	
  	
  	
  	
  	
  	
  	
  	
  [	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  Content-­‐Type	
  =>	
  'text/plain',	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  Content-­‐Length	
  =>	
  %env.perl.bytes,	
  
	
  	
  	
  	
  	
  	
  	
  	
  ],	
  
	
  	
  	
  	
  	
  	
  	
  	
  [	
  %env.perl	
  ]	
  
	
  	
  	
  	
  );	
  
};
HTTP headers
my	
  $app	
  =	
  sub	
  (%env)	
  {	
  
	
  	
  	
  	
  return	
  (	
  
	
  	
  	
  	
  	
  	
  	
  	
  200,	
  
	
  	
  	
  	
  	
  	
  	
  	
  [	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  Content-­‐Type	
  =>	
  'text/plain',	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  Content-­‐Length	
  =>	
  %env.perl.bytes,	
  
	
  	
  	
  	
  	
  	
  	
  	
  ],	
  
	
  	
  	
  	
  	
  	
  	
  	
  [	
  %env.perl	
  ]	
  
	
  	
  	
  	
  );	
  
};
Response body
my	
  $builder	
  =	
  Plackdo::Builder.new;	
  
$builder.add_middleware(	
  
	
  	
  	
  	
  Plackdo::Middleware::XFramework.new(	
  
	
  	
  	
  	
  	
  	
  	
  framework	
  =>	
  'foobar')	
  
);	
  
$builder.to_app($app);
~2014
wee6
https://github.com/vti/wee6
Present
Rakudo Star
http://rakudo.org
+
modules.perl6.org
Installing Rakudo*
perl	
  Configure.pl	
  	
  	
  
	
  	
  	
  	
  -­‐-­‐backend=moar	
  	
  
	
  	
  	
  	
  -­‐-­‐gen-­‐moar	
  	
  
!
make	
  
!
make	
  install
MoarVM
http://moarvm.org
Managing modules
“Ecosystem”
https://github.com/perl6/ecosystem
Panda
!
for installing Perl 6 modules
modules/panda/bootstrap.pl
panda	
  install	
  Module::X
Distribution modules live in
install/share/perl6/lib
Panda puts modules to
install/share/perl6/site
BTW,
Rakudo’s “make install”
compiles modules
to .moarvm
OK, Perl.
Let’s build a web server
HTTP::Easy
Core’s
HTTP::Easy::PSGI
Core’s
use	
  HTTP::Easy::PSGI;	
  
my	
  $http	
  =	
  HTTP::Easy::PSGI.new(	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  :port(8080)	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  );	
  
my	
  $app	
  =	
  sub	
  (%env)	
  {	
  
	
  	
  	
  	
  	
  .	
  .	
  .	
  	
  
}	
  
my	
  $app	
  =	
  sub	
  (%env)	
  {	
  
	
  	
  	
  	
  	
  .	
  .	
  .	
  	
  
}	
  
!
$http.handle($app);
my	
  $app	
  =	
  sub	
  (%env)	
  {	
  	
  	
  	
  
	
  	
  	
  	
  return	
  [	
  
	
  	
  	
  	
  	
  	
  	
  	
  200,	
  
	
  	
  	
  	
  	
  	
  	
  	
  [	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  'Content-­‐Type'	
  =>	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  'text/plain'	
  
	
  	
  	
  	
  	
  	
  	
  	
  ],	
  
	
  	
  	
  	
  	
  	
  	
  	
  [	
  
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  'Hello,	
  World!’	
  
	
  	
  	
  	
  	
  	
  	
  	
  ]	
  
	
  	
  	
  	
  ];	
  
}
use	
  HTTP::Easy::PSGI;	
  
my	
  $http	
  =	
  
HTTP::Easy::PSGI.new(:port(8080));	
  
!
my	
  $app	
  =	
  sub	
  (%env)	
  {	
  
	
  	
  	
  	
  my	
  $name	
  =	
  %env<QUERY_STRING>	
  
||	
  "World";	
  
	
  	
  	
  	
  return	
  [	
  200,	
  [	
  'Content-­‐Type'	
  
=>	
  'text/plain'	
  ],	
  [	
  "Hello	
  
$name"	
  ]	
  ];	
  
}	
  
!
!
Web::App module set
Explore
Bailador
Bailador
(Dancer)
Available in the Rakudo*
distribution
(Does not instantly work
in the 2015.09 distribution)
use	
  Bailador;
use	
  Bailador;	
  
!
get	
  '/'	
  =>	
  sub	
  {	
  
!
}	
  
use	
  Bailador;	
  
!
get	
  '/'	
  =>	
  sub	
  {	
  
	
  	
  	
  	
  return	
  "Hin";	
  
}	
  
!
use	
  Bailador;	
  
!
get	
  '/'	
  =>	
  sub	
  {	
  
	
  	
  	
  	
  return	
  "Hin";	
  
}	
  
!
baile;
use	
  Bailador;	
  
!
get	
  '/'	
  =>	
  sub	
  {	
  
	
  	
  	
  	
  "Hin"	
  
}	
  
!
baile;
$	
  perl6	
  test.pl	
  
!
Entering	
  the	
  development	
  dance	
  
floor:	
  http://0.0.0.0:3000	
  
[2015-­‐11-­‐17T13:41:08Z]	
  Started	
  HTTP
server.	
  
Started…
!
Then open it in a browser
Method	
  'send'	
  not	
  found	
  for	
  
invocant	
  of	
  class	
  
'IO::Socket::INET'	
  
	
  	
  in	
  method	
  run	
  at	
  /home/ash/p/
rakudo-­‐star-­‐2015.09/install/share/
perl6/lib/HTTP/Easy.pm6:193	
  
	
  	
  in	
  sub	
  baile	
  at	
  /home/ash/p/
rakudo-­‐star-­‐2015.09/install/share/
perl6/lib/Bailador.pm:153	
  
	
  	
  in	
  block	
  <unit>	
  at	
  test.pl:8
Update HTTP::Easy
using panda
git	
  clone	
  ...	
  
panda	
  install	
  ./Bailador
!
-­‐	
  connection.send($res.Str);	
  
!
+	
  connection.print($res.Str);	
  
use	
  Bailador;	
  
!
get	
  '/'	
  =>	
  sub	
  {	
  
	
  	
  	
  	
  return	
  "Hin";	
  
}	
  
!
get	
  '/hello/:name'	
  =>	
  sub	
  ($name)	
  {
	
  	
  	
  	
  return	
  "Hi,	
  $namen";	
  
}	
  
!
baile;
use	
  Bailador;	
  
!
get	
  '/'	
  =>	
  sub	
  {	
  
	
  	
  	
  	
  return	
  "Hin";	
  
}	
  
!
get	
  '/hello/:name'	
  =>	
  sub	
  ($name)	
  {
	
  	
  	
  	
  return	
  "Hi,	
  $namen";	
  
}	
  
!
baile;
NB!
!
get	
  '/hello/:name'	
  =>	
  sub	
  ($name)	
  {
!
vs.

!
get	
  '/hello/:name'	
  =>	
  sub($name)	
  {
===SORRY!===	
  	
  
Error	
  while	
  compiling	
  test1.pl	
  
Variable	
  '$name'	
  is	
  not	
  declared	
  
at	
  test1.pl:7	
  
!
-­‐-­‐-­‐-­‐-­‐-­‐>	
  	
  
get	
  '/hello/:name'	
  =>	
  sub(⏏$name)	
  	
  
Accessing request data
get	
  '/'	
  =>	
  sub	
  {	
  
	
  	
  	
  	
  return	
  request.perl;	
  
}
Bailador::Request.new(env	
  =>	
  
{:HTTP_ACCEPT("*/
*"),	
  :HTTP_HOST("0.0.0.0:3000"),	
  :HTTP
_USER_AGENT("curl/
7.35.0"),	
  :PATH_INFO("/"),	
  :QUERY_STRI
NG(""),	
  :REQUEST_METHOD("GET"),	
  :REQUE
ST_URI("/"),	
  :SERVER_NAME("0.0.0.0"),	
  
:SERVER_PORT(3000),	
  :SERVER_PROTOCOL("
HTTP/1.1"),	
  "p6sgi.encoding"	
  =>	
  
"UTF-­‐8",	
  "p6sgi.errors"	
  =>	
  
IO::Handle.new(path	
  =>	
  
IO::Special.new(what	
  =>	
  "<STDERR>"),	
  
ins	
  =>	
  0,	
  chomp	
  =>	
  Bool::True),	
  
What is a ‘request’?
class	
  Bailador::App	
  {	
  
	
  	
  	
  	
  .	
  .	
  .	
  
	
  	
  	
  	
  method	
  request	
  {	
  
	
  	
  	
  	
  	
  	
  	
  	
  $.context.request	
  
	
  	
  	
  	
  }	
  
	
  	
  	
  	
  method	
  response	
  {	
  
	
  	
  	
  	
  	
  	
  	
  	
  $.context.response	
  
	
  	
  	
  	
  }	
  
	
  	
  	
  	
  .	
  .	
  .	
  
}
get	
  /.*/	
  =>	
  sub	
  {	
  
	
  	
  	
  	
  return	
  
	
  	
  	
  	
  	
  	
  	
  	
  request.env<REQUEST_URI>	
  
	
  	
  	
  	
  	
  	
  	
  	
  ~	
  
	
  	
  	
  	
  	
  	
  	
  	
  "n";	
  
}	
  
get	
  /.*/	
  =>	
  sub	
  {	
  
	
  	
  	
  	
  return	
  
	
  	
  	
  	
  	
  	
  	
  	
  request.env<REQUEST_URI>	
  
	
  	
  	
  	
  	
  	
  	
  	
  ~	
  
	
  	
  	
  	
  	
  	
  	
  	
  "n";	
  
}	
  
Templates
get	
  '/'	
  =>	
  sub	
  {	
  
	
  	
  	
  	
  template	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  't.tt',	
  
	
  	
  	
  	
  	
  	
  	
  	
  {	
  name	
  =>	
  'Name'	
  }	
  
}
get	
  '/'	
  =>	
  sub	
  {	
  
	
  	
  	
  	
  template	
  	
  
	
  	
  	
  	
  	
  	
  	
  	
  't.tt',	
  
	
  	
  	
  	
  	
  	
  	
  	
  {	
  name	
  =>	
  'Name'	
  }	
  
}
%	
  my	
  ($h)	
  =	
  @_;	
  
<html>	
  
<head>	
  
	
  	
  	
  	
  <title>	
  
	
  	
  	
  	
  	
  	
  Hi,	
  <%=	
  $h<name>	
  %>	
  
	
  	
  	
  	
  </title>	
  
</head>	
  
<body>	
  
	
  	
  	
  	
  <h1>Hello	
  <%=	
  $h<name>	
  %></h1>	
  
</body>	
  
</html>
%	
  my	
  ($h)	
  =	
  @_;	
  
<html>	
  
<head>	
  
	
  	
  	
  	
  <title>	
  
	
  	
  	
  	
  	
  	
  Hi,	
  <%=	
  $h<name>	
  %>	
  
	
  	
  	
  	
  </title>	
  
</head>	
  
<body>	
  
	
  	
  	
  	
  <h1>Hello	
  <%=	
  $h<name>	
  %></h1>	
  
</body>	
  
</html>
Use	
  of	
  uninitialized	
  value	
  
$_location	
  of	
  type	
  Any	
  in	
  string	
  
context	
  
Any	
  of	
  .^name,	
  .perl,	
  .gist,	
  
or	
  .say	
  can	
  stringify	
  undefined	
  
things,	
  if	
  needed.	
  	
  in	
  method	
  
template	
  at	
  /home/ash/p/rakudo-­‐
star-­‐2015.09/install/share/perl6/
site/lib/Bailador/App.pm:14	
  
Failed	
  to	
  open	
  file	
  /views/t.tt:	
  no
such	
  file	
  or	
  directory	
  
	
  	
  in	
  method	
  template	
  at	
  
my	
  $_location;	
  
!
.	
  .	
  .	
  
!
$!renderer.render(	
  
	
  	
  	
  	
  slurp(	
  
	
  	
  	
  	
  	
  	
  	
  	
  "$_location/views/$tmpl"	
  
	
  	
  	
  	
  ),	
  
	
  	
  	
  	
  @params	
  
);
lib/Bailador/App.pm
my	
  $_location;	
  
!
.	
  .	
  .	
  
!
$!renderer.render(	
  
	
  	
  	
  	
  slurp(	
  
	
  	
  	
  	
  	
  	
  	
  	
  "$_location/views/$tmpl"	
  
	
  	
  	
  	
  ),	
  
	
  	
  	
  	
  @params	
  
);
lib/Bailador/App.pm
my	
  $_location	
  =	
  '.';	
  
!
.	
  .	
  .	
  
!
$!renderer.render(	
  
	
  	
  	
  	
  slurp(	
  
	
  	
  	
  	
  	
  	
  	
  	
  "$_location/views/$tmpl"	
  
	
  	
  	
  	
  ),	
  
	
  	
  	
  	
  @params	
  
);
lib/Bailador/App.pm
OK, Perl.
What about
databases?
DBIish
panda	
  install	
  DBIish
use	
  DBIish;
use	
  DBIish;	
  
my	
  $dbh	
  =	
  DBIish.connect(	
  
	
  	
  'mysql',	
  
	
  	
  :host<example.com>,	
  
	
  	
  :port(3306),	
  
	
  	
  :database<$dbname>,	
  
	
  	
  :user<$dbuser>,	
  
	
  	
  :password<$dbpassword>);
my	
  $sth	
  =	
  $dbh.prepare(	
  
	
  	
  	
  	
  	
  "select	
  now()"	
  
);	
  
!
$sth.execute();
my	
  $arr	
  =	
  	
  
	
  	
  	
  	
  $sth.fetchall_arrayref();
my	
  $arr	
  =	
  	
  
	
  	
  	
  	
  $sth.fetchall_arrayref();	
  
!
for	
  $arr	
  -­‐>	
  $x	
  {	
  
	
  	
  	
  	
  say	
  $x;	
  
}
It works!
__END__
Cluj-Napoka 2015
!
!
Andrew Shitov | andy@shitov.ru

Weitere ähnliche Inhalte

Was ist angesagt?

Perl.Hacks.On.Vim
Perl.Hacks.On.VimPerl.Hacks.On.Vim
Perl.Hacks.On.Vim
Lin Yo-An
 
Good Evils In Perl (Yapc Asia)
Good Evils In Perl (Yapc Asia)Good Evils In Perl (Yapc Asia)
Good Evils In Perl (Yapc Asia)
Kang-min Liu
 
Good Evils In Perl
Good Evils In PerlGood Evils In Perl
Good Evils In Perl
Kang-min Liu
 

Was ist angesagt? (20)

Learning Perl 6
Learning Perl 6 Learning Perl 6
Learning Perl 6
 
Perl 6 for Concurrency and Parallel Computing
Perl 6 for Concurrency and Parallel ComputingPerl 6 for Concurrency and Parallel Computing
Perl 6 for Concurrency and Parallel Computing
 
Perl.Hacks.On.Vim
Perl.Hacks.On.VimPerl.Hacks.On.Vim
Perl.Hacks.On.Vim
 
Perl6 Regexen: Reduce the line noise in your code.
Perl6 Regexen: Reduce the line noise in your code.Perl6 Regexen: Reduce the line noise in your code.
Perl6 Regexen: Reduce the line noise in your code.
 
Learning Perl 6 (NPW 2007)
Learning Perl 6 (NPW 2007)Learning Perl 6 (NPW 2007)
Learning Perl 6 (NPW 2007)
 
Wx::Perl::Smart
Wx::Perl::SmartWx::Perl::Smart
Wx::Perl::Smart
 
Introdução ao Perl 6
Introdução ao Perl 6Introdução ao Perl 6
Introdução ao Perl 6
 
Good Evils In Perl (Yapc Asia)
Good Evils In Perl (Yapc Asia)Good Evils In Perl (Yapc Asia)
Good Evils In Perl (Yapc Asia)
 
Good Evils In Perl
Good Evils In PerlGood Evils In Perl
Good Evils In Perl
 
Electrify your code with PHP Generators
Electrify your code with PHP GeneratorsElectrify your code with PHP Generators
Electrify your code with PHP Generators
 
Php functions
Php functionsPhp functions
Php functions
 
Neatly Hashing a Tree: FP tree-fold in Perl5 & Perl6
Neatly Hashing a Tree: FP tree-fold in Perl5 & Perl6Neatly Hashing a Tree: FP tree-fold in Perl5 & Perl6
Neatly Hashing a Tree: FP tree-fold in Perl5 & Perl6
 
Adventures in Optimization
Adventures in OptimizationAdventures in Optimization
Adventures in Optimization
 
Zend Certification Preparation Tutorial
Zend Certification Preparation TutorialZend Certification Preparation Tutorial
Zend Certification Preparation Tutorial
 
Looping the Loop with SPL Iterators
Looping the Loop with SPL IteratorsLooping the Loop with SPL Iterators
Looping the Loop with SPL Iterators
 
Advanced Perl Techniques
Advanced Perl TechniquesAdvanced Perl Techniques
Advanced Perl Techniques
 
Static Optimization of PHP bytecode (PHPSC 2017)
Static Optimization of PHP bytecode (PHPSC 2017)Static Optimization of PHP bytecode (PHPSC 2017)
Static Optimization of PHP bytecode (PHPSC 2017)
 
Perl6 one-liners
Perl6 one-linersPerl6 one-liners
Perl6 one-liners
 
Nubilus Perl
Nubilus PerlNubilus Perl
Nubilus Perl
 
PHP 7 – What changed internally? (Forum PHP 2015)
PHP 7 – What changed internally? (Forum PHP 2015)PHP 7 – What changed internally? (Forum PHP 2015)
PHP 7 – What changed internally? (Forum PHP 2015)
 

Ähnlich wie Perl6 in-production

C A S Sample Php
C A S Sample PhpC A S Sample Php
C A S Sample Php
JH Lee
 
Advanced modulinos
Advanced modulinosAdvanced modulinos
Advanced modulinos
brian d foy
 
PHP and Rich Internet Applications
PHP and Rich Internet ApplicationsPHP and Rich Internet Applications
PHP and Rich Internet Applications
elliando dias
 
2014 database - course 2 - php
2014 database - course 2 - php2014 database - course 2 - php
2014 database - course 2 - php
Hung-yu Lin
 
Writing Maintainable Perl
Writing Maintainable PerlWriting Maintainable Perl
Writing Maintainable Perl
tinypigdotcom
 
Introduction to Perl - Day 2
Introduction to Perl - Day 2Introduction to Perl - Day 2
Introduction to Perl - Day 2
Dave Cross
 

Ähnlich wie Perl6 in-production (20)

C A S Sample Php
C A S Sample PhpC A S Sample Php
C A S Sample Php
 
Perl Bag of Tricks - Baltimore Perl mongers
Perl Bag of Tricks  -  Baltimore Perl mongersPerl Bag of Tricks  -  Baltimore Perl mongers
Perl Bag of Tricks - Baltimore Perl mongers
 
Advanced modulinos
Advanced modulinosAdvanced modulinos
Advanced modulinos
 
wget.pl
wget.plwget.pl
wget.pl
 
PHP and Rich Internet Applications
PHP and Rich Internet ApplicationsPHP and Rich Internet Applications
PHP and Rich Internet Applications
 
2014 database - course 2 - php
2014 database - course 2 - php2014 database - course 2 - php
2014 database - course 2 - php
 
Writing Maintainable Perl
Writing Maintainable PerlWriting Maintainable Perl
Writing Maintainable Perl
 
Web 8 | Introduction to PHP
Web 8 | Introduction to PHPWeb 8 | Introduction to PHP
Web 8 | Introduction to PHP
 
Mike King - Storytelling by Numbers MKTFEST 2014
Mike King - Storytelling by Numbers MKTFEST 2014Mike King - Storytelling by Numbers MKTFEST 2014
Mike King - Storytelling by Numbers MKTFEST 2014
 
Storytelling By Numbers
Storytelling By NumbersStorytelling By Numbers
Storytelling By Numbers
 
Introduction to Perl - Day 2
Introduction to Perl - Day 2Introduction to Perl - Day 2
Introduction to Perl - Day 2
 
Modern Perl
Modern PerlModern Perl
Modern Perl
 
Introduction to Perl
Introduction to PerlIntroduction to Perl
Introduction to Perl
 
Perl basics for Pentesters
Perl basics for PentestersPerl basics for Pentesters
Perl basics for Pentesters
 
Ae internals
Ae internalsAe internals
Ae internals
 
Beginning Perl
Beginning PerlBeginning Perl
Beginning Perl
 
How to write code you won't hate tomorrow
How to write code you won't hate tomorrowHow to write code you won't hate tomorrow
How to write code you won't hate tomorrow
 
Perl6 a whistle stop tour
Perl6 a whistle stop tourPerl6 a whistle stop tour
Perl6 a whistle stop tour
 
Perl6 a whistle stop tour
Perl6 a whistle stop tourPerl6 a whistle stop tour
Perl6 a whistle stop tour
 
Dealing with Legacy Perl Code - Peter Scott
Dealing with Legacy Perl Code - Peter ScottDealing with Legacy Perl Code - Peter Scott
Dealing with Legacy Perl Code - Peter Scott
 

Mehr von Andrew Shitov

‎Откуда узнать про Perl 6‎
‎Откуда узнать про Perl 6‎‎Откуда узнать про Perl 6‎
‎Откуда узнать про Perl 6‎
Andrew Shitov
 
‎42 £ в ойрах‎
‎42 £ в ойрах‎‎42 £ в ойрах‎
‎42 £ в ойрах‎
Andrew Shitov
 
10 мероприятий за 20 месяцев в пяти странах
10 мероприятий за 20 месяцев в пяти странах10 мероприятий за 20 месяцев в пяти странах
10 мероприятий за 20 месяцев в пяти странах
Andrew Shitov
 

Mehr von Andrew Shitov (20)

Fun with Raspberry PI (and Perl)
Fun with Raspberry PI (and Perl)Fun with Raspberry PI (and Perl)
Fun with Raspberry PI (and Perl)
 
Параллельные вычисления в Perl 6
Параллельные вычисления в Perl 6Параллельные вычисления в Perl 6
Параллельные вычисления в Perl 6
 
AllPerlBooks.com
AllPerlBooks.comAllPerlBooks.com
AllPerlBooks.com
 
YAPC::Europe 2013
YAPC::Europe 2013YAPC::Europe 2013
YAPC::Europe 2013
 
Perl 7, the story of
Perl 7, the story ofPerl 7, the story of
Perl 7, the story of
 
Язык программирования Go для Perl-программистов
Язык программирования Go для Perl-программистовЯзык программирования Go для Perl-программистов
Язык программирования Go для Perl-программистов
 
Как очистить массив
Как очистить массивКак очистить массив
Как очистить массив
 
What's new in Perl 5.14
What's new in Perl 5.14What's new in Perl 5.14
What's new in Perl 5.14
 
Что нового в Perl 5.14
Что нового в Perl 5.14Что нового в Perl 5.14
Что нового в Perl 5.14
 
There's more than one way to empty it
There's more than one way to empty itThere's more than one way to empty it
There's more than one way to empty it
 
How to clean an array
How to clean an arrayHow to clean an array
How to clean an array
 
Perl 5.10 и 5.12
Perl 5.10 и 5.12Perl 5.10 и 5.12
Perl 5.10 и 5.12
 
Say Perl на весь мир
Say Perl на весь мирSay Perl на весь мир
Say Perl на весь мир
 
Personal Perl 6 compiler
Personal Perl 6 compilerPersonal Perl 6 compiler
Personal Perl 6 compiler
 
Perl 5.10 in 2010
Perl 5.10 in 2010Perl 5.10 in 2010
Perl 5.10 in 2010
 
Perl 5.10 в 2010-м
Perl 5.10 в 2010-мPerl 5.10 в 2010-м
Perl 5.10 в 2010-м
 
Gearman and Perl
Gearman and PerlGearman and Perl
Gearman and Perl
 
‎Откуда узнать про Perl 6‎
‎Откуда узнать про Perl 6‎‎Откуда узнать про Perl 6‎
‎Откуда узнать про Perl 6‎
 
‎42 £ в ойрах‎
‎42 £ в ойрах‎‎42 £ в ойрах‎
‎42 £ в ойрах‎
 
10 мероприятий за 20 месяцев в пяти странах
10 мероприятий за 20 месяцев в пяти странах10 мероприятий за 20 месяцев в пяти странах
10 мероприятий за 20 месяцев в пяти странах
 

Kürzlich hochgeladen

Architecting Cloud Native Applications
Architecting Cloud Native ApplicationsArchitecting Cloud Native Applications
Architecting Cloud Native Applications
WSO2
 
Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024
Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024
Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024
Victor Rentea
 

Kürzlich hochgeladen (20)

"I see eyes in my soup": How Delivery Hero implemented the safety system for ...
"I see eyes in my soup": How Delivery Hero implemented the safety system for ..."I see eyes in my soup": How Delivery Hero implemented the safety system for ...
"I see eyes in my soup": How Delivery Hero implemented the safety system for ...
 
DEV meet-up UiPath Document Understanding May 7 2024 Amsterdam
DEV meet-up UiPath Document Understanding May 7 2024 AmsterdamDEV meet-up UiPath Document Understanding May 7 2024 Amsterdam
DEV meet-up UiPath Document Understanding May 7 2024 Amsterdam
 
CNIC Information System with Pakdata Cf In Pakistan
CNIC Information System with Pakdata Cf In PakistanCNIC Information System with Pakdata Cf In Pakistan
CNIC Information System with Pakdata Cf In Pakistan
 
Emergent Methods: Multi-lingual narrative tracking in the news - real-time ex...
Emergent Methods: Multi-lingual narrative tracking in the news - real-time ex...Emergent Methods: Multi-lingual narrative tracking in the news - real-time ex...
Emergent Methods: Multi-lingual narrative tracking in the news - real-time ex...
 
Manulife - Insurer Transformation Award 2024
Manulife - Insurer Transformation Award 2024Manulife - Insurer Transformation Award 2024
Manulife - Insurer Transformation Award 2024
 
Apidays New York 2024 - The value of a flexible API Management solution for O...
Apidays New York 2024 - The value of a flexible API Management solution for O...Apidays New York 2024 - The value of a flexible API Management solution for O...
Apidays New York 2024 - The value of a flexible API Management solution for O...
 
FWD Group - Insurer Innovation Award 2024
FWD Group - Insurer Innovation Award 2024FWD Group - Insurer Innovation Award 2024
FWD Group - Insurer Innovation Award 2024
 
Architecting Cloud Native Applications
Architecting Cloud Native ApplicationsArchitecting Cloud Native Applications
Architecting Cloud Native Applications
 
Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024
Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024
Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024
 
Ransomware_Q4_2023. The report. [EN].pdf
Ransomware_Q4_2023. The report. [EN].pdfRansomware_Q4_2023. The report. [EN].pdf
Ransomware_Q4_2023. The report. [EN].pdf
 
EMPOWERMENT TECHNOLOGY GRADE 11 QUARTER 2 REVIEWER
EMPOWERMENT TECHNOLOGY GRADE 11 QUARTER 2 REVIEWEREMPOWERMENT TECHNOLOGY GRADE 11 QUARTER 2 REVIEWER
EMPOWERMENT TECHNOLOGY GRADE 11 QUARTER 2 REVIEWER
 
Spring Boot vs Quarkus the ultimate battle - DevoxxUK
Spring Boot vs Quarkus the ultimate battle - DevoxxUKSpring Boot vs Quarkus the ultimate battle - DevoxxUK
Spring Boot vs Quarkus the ultimate battle - DevoxxUK
 
Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...
Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...
Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...
 
Apidays New York 2024 - APIs in 2030: The Risk of Technological Sleepwalk by ...
Apidays New York 2024 - APIs in 2030: The Risk of Technological Sleepwalk by ...Apidays New York 2024 - APIs in 2030: The Risk of Technological Sleepwalk by ...
Apidays New York 2024 - APIs in 2030: The Risk of Technological Sleepwalk by ...
 
Artificial Intelligence Chap.5 : Uncertainty
Artificial Intelligence Chap.5 : UncertaintyArtificial Intelligence Chap.5 : Uncertainty
Artificial Intelligence Chap.5 : Uncertainty
 
[BuildWithAI] Introduction to Gemini.pdf
[BuildWithAI] Introduction to Gemini.pdf[BuildWithAI] Introduction to Gemini.pdf
[BuildWithAI] Introduction to Gemini.pdf
 
Repurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost Saving
Repurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost SavingRepurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost Saving
Repurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost Saving
 
Apidays New York 2024 - Scaling API-first by Ian Reasor and Radu Cotescu, Adobe
Apidays New York 2024 - Scaling API-first by Ian Reasor and Radu Cotescu, AdobeApidays New York 2024 - Scaling API-first by Ian Reasor and Radu Cotescu, Adobe
Apidays New York 2024 - Scaling API-first by Ian Reasor and Radu Cotescu, Adobe
 
ProductAnonymous-April2024-WinProductDiscovery-MelissaKlemke
ProductAnonymous-April2024-WinProductDiscovery-MelissaKlemkeProductAnonymous-April2024-WinProductDiscovery-MelissaKlemke
ProductAnonymous-April2024-WinProductDiscovery-MelissaKlemke
 
Corporate and higher education May webinar.pptx
Corporate and higher education May webinar.pptxCorporate and higher education May webinar.pptx
Corporate and higher education May webinar.pptx
 

Perl6 in-production

  • 2. 15 years of development
  • 9. Not that it is too late
  • 10. Rather that it is too mature
  • 11.
  • 12. Lots of blog posts
  • 14. Lots of code examples
  • 17. Not easy to find how this or that works
  • 18. Most of code examples and modules are outdated
  • 21. Even if it used to work
  • 22. ===SORRY!===   Error  while  compiling     ! Undeclared  routine:        eval  used  at  line  7.        Did  you  mean  'val'?
  • 23. ===SORRY!===   Error  while  compiling     ! Undeclared  routine:        eval  used  at  line  7.        Did  you  mean  'val'?
  • 25. A bit of history
  • 29. Parrot with Perl 6 compiler
  • 30. Pugs
  • 31. Pugs, the Perl 6 compiler
  • 34. Past
  • 36.
  • 37. Some examples of the code of 2004
  • 39. my  @keys  =  ('SERVER_NAME',                                            'REMOTE_ADDR',                            'HTTP_USER_AGENT');   ! my  $key;   foreach  $key  (@keys){      print  "$key=%ENV{$key}<br  />n";   }
  • 41. my  @keys  =  ('SERVER_NAME',                                            'REMOTE_ADDR',                            'HTTP_USER_AGENT');   ! my  $key;   foreach  $key  (@keys){      print  "$key=%ENV{$key}<br  />n";   }
  • 42. You could learn Perl 6 in a few hours
  • 44. print  "Content-­‐Type:  text/htmln"   print  'Set-­‐Cookie:  cookie-­‐ name=test-­‐value;  path=/;nn';   ! print  %ENV{'HTTP_COOKIE'};
  • 46. read_params  (          %ENV{'QUERY_STRING'},            @params_key,          @params_value   );
  • 47. sub  read_params  ($query,  @params_key,   @params_value){        my  $pos  =  0;        loop  (my  $c  =  0;  1;  $c++)  {              my  $newpos  =  index  ($query,  '&',  $pos);              my  @keyvalue;              my  $pair  =  substr  ($query,  $pos,  $newpos   ==  -­‐1  ??  length  ($query)  ::  $newpos  -­‐  $pos);              split_pair  ($pair,  @keyvalue);              @params_key[$c]  =  @keyvalue[0];              @params_value[$c]  =  @keyvalue[1];              last  if  $newpos  ==  -­‐1;              $pos  =  $newpos  +  1;        }   }
  • 48. sub  read_params  ($query,  @params_key,   @params_value){        my  $pos  =  0;        loop  (my  $c  =  0;  1;  $c++)  {              my  $newpos  =  index  ($query,  '&',  $pos);              my  @keyvalue;              my  $pair  =  substr  ($query,  $pos,  $newpos   ==  -­‐1  ??  length  ($query)  ::  $newpos  -­‐  $pos);              split_pair  ($pair,  @keyvalue);              @params_key[$c]  =  @keyvalue[0];              @params_value[$c]  =  @keyvalue[1];              last  if  $newpos  ==  -­‐1;              $pos  =  $newpos  +  1;        }   }
  • 49. sub  split_pair  ($pair,  @keyvalue){        my  $pos  =  index  ($pair,  '=');        if  ($pos  ==  -­‐1){              @keyvalue[0]  =  $pair;              @keyvalue[1]  =  '';        }        else{              @keyvalue[0]  =  substr  ($pair,  0,  $pos);              @keyvalue[1]  =  substr  ($pair,  $pos  +  1);        }   }  
  • 51. sub  params2hash  (%params,  @params_key,   @params_value){        for  0  ..  @params_key  -­‐>  $c{              %params{@params_key[$c]}  =              @params_value[$c];        }   }   ! read_params  (%ENV{'QUERY_STRING'},  @params_key,   @params_value);   my  %params;   params2hash  (%params,  @params_key,   @params_value);
  • 57.
  • 59. class  November::CGI  {          has  %.params;          has  %.cookie;          has  @.keywords;          has  November::URI  $.uri;
  • 61. has  $!crlf  =  "x[0D]x[0A]";                .  .  .   ! print  "Status:  $status$!crlf";   print  "Location:  $uri";   print  "$!crlf$!crlf";
  • 62. has  $!crlf  =  "x[0D]x[0A]";                .  .  .   ! print  "Status:  $status$!crlf";   print  "Location:  $uri";   print  "$!crlf$!crlf"; Compare https://p6weekly.wordpress.com/2015/11/09/2015-46- production-today/
  • 64. method  add_param  (  Str  $key,  $value  )  {              if  %.params{$key}  :exists  {              #  RAKUDO:  ~~  Scalar              if  %.params{$key}  ~~  Str  |  Int  {                          my  $old_param  =  %.params{$key};                          %!params{$key}  =                                    [  $old_param,  $value  ];              }              elsif  %.params{$key}  ~~  Array  {                          %!params{$key}.push(  $value  );              }              }              else  {              %!params{$key}  =  $value;              }   }  
  • 66. method  add_param  (  Str  $key,  $value  )  {              if  %.params{$key}  :exists  {              #  RAKUDO:  ~~  Scalar              if  %.params{$key}  ~~  Str  |  Int  {                          my  $old_param  =  %.params{$key};                          %!params{$key}  =                                    [  $old_param,  $value  ];              }              elsif  %.params{$key}  ~~  Array  {                          %!params{$key}.push(  $value  );              }              }              else  {              %!params{$key}  =  $value;              }   }  
  • 67. if  %*ENV<MODPERL6>  {            my  $r  =  Apache::RequestRec.new();            my  $len  =  $r.read($input,                                  %*ENV<CONTENT_LENGTH>);   }   else  {              #  Maybe  check  content_length  here                #  and  only  take  that  many  bytes?              $input  =  $*IN.slurp;   }   !
  • 68. (I never managed to install mod_parrot)
  • 69. Grammar for URL parsing
  • 70. grammar  November::URI::Grammar  {          token  TOP                {  ^  [<scheme>  ':']?                  [  '//'  <authority>]?                  <path>  ['?'  <query>]?  ['#'  <fragment>]?  $  };          token  scheme          {  <-­‐[:/&?#]>+  };          token  authority    {  <host>  [':'  <port>]?  };          token  host              {  <-­‐[/&?#:]>*  };          token  port              {  (d**1..5)                                                    <?{  $0  <  2  **  16  }>                                                <!before  d>  };          token  path              {  <slash>?  [  <chunk>  '/'?]*  };          token  slash            {  '/'  };          token  chunk            {  <-­‐[/?#]>+  };          token  query            {  <-­‐[#]>*  };          token  fragment      {  .*  };   }
  • 71. #  Official  regexp  (p5):   #  my($scheme,  $authority,  $path,  $query,  $fragment)  =   #  $uri  =~  m/   #                      (?:([^:/?#]+):)?   #                      (?://([^/?#]*))?   #                      ([^?#]*)   #                      (?:?([^#]*))?   #                      (?:#(.*))?   #                  /x;
  • 72. Not like Perl 5 any more :-)
  • 75. my  $app  =  sub  (%env)  {          return  (                  200,                  [                            Content-­‐Type  =>  'text/plain',                            Content-­‐Length  =>  %env.perl.bytes,                  ],                  [  %env.perl  ]          );   }; HTTP status code
  • 76. my  $app  =  sub  (%env)  {          return  (                  200,                  [                            Content-­‐Type  =>  'text/plain',                            Content-­‐Length  =>  %env.perl.bytes,                  ],                  [  %env.perl  ]          );   }; HTTP headers
  • 77. my  $app  =  sub  (%env)  {          return  (                  200,                  [                            Content-­‐Type  =>  'text/plain',                            Content-­‐Length  =>  %env.perl.bytes,                  ],                  [  %env.perl  ]          );   }; Response body
  • 78. my  $builder  =  Plackdo::Builder.new;   $builder.add_middleware(          Plackdo::Middleware::XFramework.new(                framework  =>  'foobar')   );   $builder.to_app($app);
  • 82. +
  • 85. perl  Configure.pl              -­‐-­‐backend=moar            -­‐-­‐gen-­‐moar     ! make   ! make  install
  • 89.
  • 93. Distribution modules live in install/share/perl6/lib
  • 94. Panda puts modules to install/share/perl6/site
  • 96. OK, Perl. Let’s build a web server
  • 97.
  • 101. my  $http  =  HTTP::Easy::PSGI.new(                                :port(8080)                        );  
  • 102. my  $app  =  sub  (%env)  {            .  .  .     }  
  • 103. my  $app  =  sub  (%env)  {            .  .  .     }   ! $http.handle($app);
  • 104. my  $app  =  sub  (%env)  {                return  [                  200,                  [                      'Content-­‐Type'  =>                      'text/plain'                  ],                  [                      'Hello,  World!’                  ]          ];   }
  • 105. use  HTTP::Easy::PSGI;   my  $http  =   HTTP::Easy::PSGI.new(:port(8080));   ! my  $app  =  sub  (%env)  {          my  $name  =  %env<QUERY_STRING>   ||  "World";          return  [  200,  [  'Content-­‐Type'   =>  'text/plain'  ],  [  "Hello   $name"  ]  ];   }   !
  • 109. Available in the Rakudo* distribution
  • 110. (Does not instantly work in the 2015.09 distribution)
  • 112. use  Bailador;   ! get  '/'  =>  sub  {   ! }  
  • 113. use  Bailador;   ! get  '/'  =>  sub  {          return  "Hin";   }   !
  • 114. use  Bailador;   ! get  '/'  =>  sub  {          return  "Hin";   }   ! baile;
  • 115. use  Bailador;   ! get  '/'  =>  sub  {          "Hin"   }   ! baile;
  • 116. $  perl6  test.pl   ! Entering  the  development  dance   floor:  http://0.0.0.0:3000   [2015-­‐11-­‐17T13:41:08Z]  Started  HTTP server.  
  • 117. Started… ! Then open it in a browser
  • 118. Method  'send'  not  found  for   invocant  of  class   'IO::Socket::INET'      in  method  run  at  /home/ash/p/ rakudo-­‐star-­‐2015.09/install/share/ perl6/lib/HTTP/Easy.pm6:193      in  sub  baile  at  /home/ash/p/ rakudo-­‐star-­‐2015.09/install/share/ perl6/lib/Bailador.pm:153      in  block  <unit>  at  test.pl:8
  • 120. git  clone  ...   panda  install  ./Bailador
  • 121. ! -­‐  connection.send($res.Str);   ! +  connection.print($res.Str);  
  • 122. use  Bailador;   ! get  '/'  =>  sub  {          return  "Hin";   }   ! get  '/hello/:name'  =>  sub  ($name)  {        return  "Hi,  $namen";   }   ! baile;
  • 123. use  Bailador;   ! get  '/'  =>  sub  {          return  "Hin";   }   ! get  '/hello/:name'  =>  sub  ($name)  {        return  "Hi,  $namen";   }   ! baile;
  • 124. NB!
  • 125. ! get  '/hello/:name'  =>  sub  ($name)  { ! vs. ! get  '/hello/:name'  =>  sub($name)  {
  • 126. ===SORRY!===     Error  while  compiling  test1.pl   Variable  '$name'  is  not  declared   at  test1.pl:7   ! -­‐-­‐-­‐-­‐-­‐-­‐>     get  '/hello/:name'  =>  sub(⏏$name)    
  • 128. get  '/'  =>  sub  {          return  request.perl;   }
  • 129. Bailador::Request.new(env  =>   {:HTTP_ACCEPT("*/ *"),  :HTTP_HOST("0.0.0.0:3000"),  :HTTP _USER_AGENT("curl/ 7.35.0"),  :PATH_INFO("/"),  :QUERY_STRI NG(""),  :REQUEST_METHOD("GET"),  :REQUE ST_URI("/"),  :SERVER_NAME("0.0.0.0"),   :SERVER_PORT(3000),  :SERVER_PROTOCOL(" HTTP/1.1"),  "p6sgi.encoding"  =>   "UTF-­‐8",  "p6sgi.errors"  =>   IO::Handle.new(path  =>   IO::Special.new(what  =>  "<STDERR>"),   ins  =>  0,  chomp  =>  Bool::True),  
  • 130. What is a ‘request’?
  • 131. class  Bailador::App  {          .  .  .          method  request  {                  $.context.request          }          method  response  {                  $.context.response          }          .  .  .   }
  • 132. get  /.*/  =>  sub  {          return                  request.env<REQUEST_URI>                  ~                  "n";   }  
  • 133. get  /.*/  =>  sub  {          return                  request.env<REQUEST_URI>                  ~                  "n";   }  
  • 135. get  '/'  =>  sub  {          template                    't.tt',                  {  name  =>  'Name'  }   }
  • 136. get  '/'  =>  sub  {          template                    't.tt',                  {  name  =>  'Name'  }   }
  • 137. %  my  ($h)  =  @_;   <html>   <head>          <title>              Hi,  <%=  $h<name>  %>          </title>   </head>   <body>          <h1>Hello  <%=  $h<name>  %></h1>   </body>   </html>
  • 138. %  my  ($h)  =  @_;   <html>   <head>          <title>              Hi,  <%=  $h<name>  %>          </title>   </head>   <body>          <h1>Hello  <%=  $h<name>  %></h1>   </body>   </html>
  • 139. Use  of  uninitialized  value   $_location  of  type  Any  in  string   context   Any  of  .^name,  .perl,  .gist,   or  .say  can  stringify  undefined   things,  if  needed.    in  method   template  at  /home/ash/p/rakudo-­‐ star-­‐2015.09/install/share/perl6/ site/lib/Bailador/App.pm:14   Failed  to  open  file  /views/t.tt:  no such  file  or  directory      in  method  template  at  
  • 140. my  $_location;   ! .  .  .   ! $!renderer.render(          slurp(                  "$_location/views/$tmpl"          ),          @params   ); lib/Bailador/App.pm
  • 141. my  $_location;   ! .  .  .   ! $!renderer.render(          slurp(                  "$_location/views/$tmpl"          ),          @params   ); lib/Bailador/App.pm
  • 142. my  $_location  =  '.';   ! .  .  .   ! $!renderer.render(          slurp(                  "$_location/views/$tmpl"          ),          @params   ); lib/Bailador/App.pm
  • 144. DBIish
  • 147. use  DBIish;   my  $dbh  =  DBIish.connect(      'mysql',      :host<example.com>,      :port(3306),      :database<$dbname>,      :user<$dbuser>,      :password<$dbpassword>);
  • 148. my  $sth  =  $dbh.prepare(            "select  now()"   );   ! $sth.execute();
  • 149. my  $arr  =            $sth.fetchall_arrayref();
  • 150. my  $arr  =            $sth.fetchall_arrayref();   ! for  $arr  -­‐>  $x  {          say  $x;   }