[dancer-users] Question about the Dancer2 tutorial under Windows/Apache as an app...
Prairie Nyx
prairienyx at gmail.com
Sun May 31 06:34:55 BST 2015
Well... looks like I'm going to answer my own question after thinking about
how as a CGI app, the vars are completely fresh with each call... so I'll
play with setting a "session variable" and then not look back at this
example... :-)
Thank you anyway!
Prairie Nyx
On Sat, May 30, 2015 at 11:10 PM, Prairie Nyx <prairienyx at gmail.com> wrote:
> Here is the entire source for the "almost working" dancr.pl tutorial
> demo, implemented as an application under Windows/Apache:
>
> [*.../htdocs/dancr/lib/dancr.pm <http://dancr.pm>*] Note - Changes from
> "dancer.pl" in yellow...
>
>
> -----------------------------------------------------------------------------
>
> package dancr;
>
> use strict;
> use warnings;
>
> use Dancer2;
> use DBI;
> use File::Spec;
> use File::Slurp;
> use Template;
>
> our $VERSION = '0.1';
>
> # set 'database' => File::Spec->catfile(File::Spec->tmpdir(),
> 'dancr.db');
> # Set the database to live under the application directory...
> set 'database' => 'C:\Apache24\htdocs\dancr\dancr.db';
> #set 'session' => 'Simple';
> set 'session' => 'YAML';
> set 'template' => 'template_toolkit';
> set 'logger' => 'console';
> set 'log' => 'debug';
> set 'show_errors' => 1;
> set 'startup_info' => 1;
> set 'warnings' => 1;
> set 'username' => 'admin';
> set 'password' => 'password';
> set 'layout' => 'main';
>
> my $flash;
>
> sub set_flash {
> my $message = shift;
>
> $flash = $message;
> }
>
> sub get_flash {
> my $message = $flash;
> $flash = '';
>
> return $message;
> }
>
> sub connect_db {
> my $dbh = DBI->connect("dbi:SQLite:dbname=".setting('database')) or
> die $DBI::errstr;
>
> return $dbh;
> }
>
> sub init_db {
> my $db = connect_db();
> my $schema = read_file('./schema.sql');
> $db->do($schema) or die $db->errstr;
> }
>
> hook before_template => sub {
> my $tokens = shift;
>
> # $tokens->{'css_url'} = request->base . 'css/dancr.css';
> $tokens->{'css_url'} = request->base . '/css/dancr.css';
> $tokens->{'login_url'} = uri_for('/login');
> $tokens->{'logout_url'} = uri_for('/logout');
> $flash='';
> };
>
> get '/' => sub {
> my $db = connect_db();
> my $sql = 'select id, title, text from entries order by id desc';
> my $sth = $db->prepare($sql) or die $db->errstr;
> $sth->execute or die $sth->errstr;
>
> template 'show_entries.tt', {
> 'msg' => get_flash,
> 'add_entry_url' => uri_for('/add'),
> 'entries' => $sth->fetchall_hashref('id'),
> };
>
> };
>
> post '/add' => sub {
> if ( not session('logged_in') ) {
> send_error("Not logged in", 401);
> }
>
> my $db = connect_db();
> my $sql = 'insert into entries (title, text) values (?, ?)';
> my $sth = $db->prepare($sql) or die $db->errstr;
> $sth->execute(params->{'title'}, params->{'text'}) or die $sth->errstr;
>
> set_flash('New entry posted!');
> redirect '/';
> };
>
> any ['get', 'post'] => '/login' => sub {
> my $err;
> my $session = session;
>
> if ( request->method() eq "POST" ) {
> # process form input
> if ( params->{'username'} ne setting('username') ) {
> $err = "Invalid username";
> }
> elsif ( params->{'password'} ne setting('password') ) {
> $err = "Invalid password";
> }
> else {
> session 'logged_in' => true;
> set_flash('You are logged in.');
> return redirect '/';
> }
> }
>
> # display login form
> template 'login.tt', {
> 'err' => $err,
> };
>
> };
>
> get '/logout' => sub {
> app->destroy_session;
> set_flash('You are logged out.');
> redirect '/';
> };
>
> init_db();
> start;
>
> true;
>
>
> -----------------------------------------------------------------------------
>
> [*http.conf*]
>
> <Directory "C:/Apache24/htdocs/dancr">
> AllowOverride None
> Options +ExecCGI -MultiViews +SymLinksIfOwnerMatch
> Order allow,deny
> Allow from all
> AddHandler cgi-script .cgi
> </Directory>
>
> ScriptAlias /dancr "C:/Apache24/htdocs/dancr/public/dispatch.cgi"
>
>
> It all seems to boil down to the "*my $flash;*" global variable that
> never gets set correctly in "sub set_flash" (or read in get_flash)... I
> think it must be something about variable scope since the global and the
> subs are not part of a route in the context of the app...
>
> ---------------------------------
> my $flash;
>
> sub set_flash {
> my $message = shift;
>
> $flash = $message;
> }
> ---------------------------------
>
> Thank you for any input about this... I'm sure it's something obvious that
> I'm missing... but I'm hoping I can be enlightened...
>
> Prairie Nyx
>
>
> On Sat, May 30, 2015 at 10:47 PM, Prairie Nyx <prairienyx at gmail.com>
> wrote:
>
>> Perl Dancer Community:
>>
>> I am converting from Dancer to Dancer2 (better late than never) and also
>> developing some preliminary curriculum materials for CoderDojo using Perl
>> Dancer2 as a framework for web development.
>>
>> I started with SawyerX's tutorial page:
>>
>> http://search.cpan.org/~xsawyerx/Dancer2/lib/Dancer2/Tutorial.pod
>>
>> The "dancr.pl" tutorial program ran just fine under the port 3000 server
>> and the tutorial was useful and instructive:
>>
>> C:\Users\CoderDojo\Perl\Dancer\dancr>perl dancr.pl
>> >> Dancer2 v0.160001 server 2496 listening on http://0.0.0.0:3000
>>
>> I ran into an issue when I tried to convert this demo into an app that
>> would run under Apache in a Windows environment, however.
>>
>> The *crux* of the issue is that the "$flash message" does not work in the
>> app (I suspect because the global variable $flash and the two subroutines
>> are not part of a route, but I could *really* use an explanation, if this
>> issue is obvious to someone:
>>
>> I created the app as normal:
>>
>> C:\Apache24\htdocs>*dancer2 -a dancr*
>> + dancr
>> + dancr\config.yml
>> + dancr\cpanfile
>> + dancr\Makefile.PL
>> + dancr\MANIFEST.SKIP
>> + dancr\bin
>> + dancr\bin\app.psgi
>> + dancr\environments
>> + dancr\environments\development.yml
>> + dancr\environments\production.yml
>> + dancr\lib
>> + dancr\lib\dancr.pm
>> + dancr\public
>> + dancr\public\dispatch.cgi
>> + dancr\public\dispatch.fcgi
>> + dancr\public\404.html
>> + dancr\public\500.html
>> + dancr\public\favicon.ico
>> + dancr\public\css
>> + dancr\public\css\error.css
>> + dancr\public\css\style.css
>> + dancr\public\images
>> + dancr\public\images\perldancer-bg.jpg
>> + dancr\public\images\perldancer.jpg
>> + dancr\public\javascripts
>> + dancr\public\javascripts\jquery.js
>> + dancr\t
>> + dancr\t\001_base.t
>> + dancr\t\002_index_route.t
>> + dancr\views
>> + dancr\views\index.tt
>> + dancr\views\layouts
>> + dancr\views\layouts\main.tt
>>
>> With the resulting app files, I added the code from the original "
>> dancr.pl" demo to the applications "dancr.pm" module:
>>
>> package dancr;
>> use Dancer2;
>>
>> our $VERSION = '0.1';
>>
>> get '/' => sub {
>> template 'index';
>> };
>>
>> true;
>>
>> I had to make the following adjustments to the code for Windows/Apache:
>>
>> (1) Change the session to YAML
>>
>> #set 'session' => 'Simple';
>> set 'session' => 'YAML';
>>
>> (2) Adjust the path for request->base:
>>
>> # $tokens->{'css_url'} = request->base . 'css/dancr.css';
>> $tokens->{'css_url'} = request->base . '/css/dancr.css';
>>
>> Everything with the app works as expected *except* for the "$flash
>> message" code:
>>
>> my $flash;
>>
>> sub set_flash($message) {
>> my $message = shift;
>>
>> $flash = $message;
>> }
>>
>> sub get_flash {
>> my $message = $flash;
>> $flash = '';
>>
>> return $message;
>> }
>>
>> I suspect that since these subs are outside a route, perhaps I'm getting
>> an effect about the scope of the variables... but calls to these
>> subroutines do *not* set $flash or $message as expected:
>>
>> template 'show_entries.tt', {
>> 'msg' => get_flash,
>>
>> set_flash('New entry posted!');
>>
>> set_flash('You are logged in.');
>>
>> set_flash('You are logged out.');
>>
>> For each of these, the $flash variable (which is a free-standing global
>> in the module) is never set... and so the get_flash sub never returns a
>> value.
>>
>> --
>> Prairie Nyx
>> prairienyx at gmail.com
>>
>
>
>
> --
> Prairie Nyx
> prairienyx at gmail.com
>
--
Prairie Nyx
prairienyx at gmail.com
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.preshweb.co.uk/pipermail/dancer-users/attachments/20150531/ded95a26/attachment.html>
More information about the dancer-users
mailing list