Dear Monks,

I really like the idea of CGI::Application, but a problem I encountered several times was about a good aproach on how to provide a userbased access to certain funtions.

As simple example take a guestbook class. One might have the run modes for viewing and posting, but what about the admin part, like viewing the posters IP's and deleting bad entries?

My thoughts:

1. The module should be reusable as a subclass in larger projects.

2. I don't want to include any kind of authentication, as I feel this would cause problems with point 1. Also I think the underlying webserver and OS can do a better job on that anyways.

3. Subclassing the admin part seems not to be the best solution to me, as a Super-class should not know anything on it's childs. And how could I then do things like extending the view part for showing the IP's as well only when in "admin-mode"?


What I've come up with so far:
In the guestbook class...
package Guestbook; use base 'CGI::Application'; use strict; # define all run modes here to allow different sets, # the actual access control should then be enforced using # multiple instance scripts, which in turn are placed in a # secure area and only enable the desired set(s) sub _RUN_MODES { DEFAULT => { view => 'view_entries', sign => 'sign_guestbook' }, RESTRICTED => { delete => 'delete_entry' } } sub enable_rm_set { my $self = shift; my %run_modes = _RUN_MODES; foreach (@_) { $self->run_modes( %{$run_modes{$_}} ); #ensure that info on loaded sets is avaible $self->param($_ => '1'); } } sub setup { my $self = shift; $self->enable_rm_set('DEFAULT'); $self->start_mode('view'); } sub view_entries { my $self = shift; my ($ip, $del_link); # are we in "admin mode"? if ($self->param('RESTRICTED')) { $ip = "with IP's"; $del_link = '<a href="?rm=delete">+ del option</a>'; } return "showing guesbook entries $ip"; } sub sign_guestbook { my $self = shift; return "sign guestbook"; } # restricted sub delete_entry { my $self = shift; # bail out if authentification did not happen # (of course this check should be during setup ;) return _no_auth() unless defined($ENV{UserName}); return "delete entry"; } sub _no_auth { return "oops, authentification did not happen"; } 1;

In the admin instance-script...

which will be placed into a separated and secured area (e.g. /admin/guestbook.pl)
use Guestbook; my $gb = Guestbook->new(); # enable admin mode $gb->enable_rm_set('RESTRICTED'); $gb->run();

In the normal instance-script...

which will be placed into the public area (e.g. /guestbook.pl)
use Guestbook; my $gb = Guestbook->new(); $gb->run();

What do you think, is this a good way to go?

Thanks a lot in advance!
Golo

Updates:

  • added some more code to make my intention more clear
  • please see Re: Re: CGI::Application with access control on certain functions/run modes for a more comprehensive explanation why splitting into multiple classes might not be desirable in this case
  • added a more complex scenario in Re: Re: CGI::Application with access control on certain functions/run modes

  • In reply to CGI::Application with access control on certain functions/run modes by Golo

    Title:
    Use:  <p> text here (a paragraph) </p>
    and:  <code> code here </code>
    to format your post, it's "PerlMonks-approved HTML":



  • Posts are HTML formatted. Put <p> </p> tags around your paragraphs. Put <code> </code> tags around your code and data!
  • Titles consisting of a single word are discouraged, and in most cases are disallowed outright.
  • Read Where should I post X? if you're not absolutely sure you're posting in the right place.
  • Please read these before you post! —
  • Posts may use any of the Perl Monks Approved HTML tags:
    a, abbr, b, big, blockquote, br, caption, center, col, colgroup, dd, del, details, div, dl, dt, em, font, h1, h2, h3, h4, h5, h6, hr, i, ins, li, ol, p, pre, readmore, small, span, spoiler, strike, strong, sub, summary, sup, table, tbody, td, tfoot, th, thead, tr, tt, u, ul, wbr
  • You may need to use entities for some characters, as follows. (Exception: Within code tags, you can put the characters literally.)
            For:     Use:
    & &amp;
    < &lt;
    > &gt;
    [ &#91;
    ] &#93;
  • Link using PerlMonks shortcuts! What shortcuts can I use for linking?
  • See Writeup Formatting Tips and other pages linked from there for more info.