Menu in progress (#595)

This commit is contained in:
Xavier Guimard 2016-04-13 21:06:04 +00:00
parent 8cc77fc304
commit 24d536b7d1
6 changed files with 82 additions and 40 deletions

View File

@ -242,10 +242,10 @@ sub checkMaintenanceMode {
# @param $cond optional Function granting access # @param $cond optional Function granting access
# @return True if the user is granted to access to the current URL # @return True if the user is granted to access to the current URL
sub grant { sub grant {
my ( $class, $uri, $cond ) = @_; my ( $class, $uri, $cond, $vhost ) = @_;
return &{$cond}() if ($cond); return &{$cond}() if ($cond);
my $vhost = $class->resolveAlias; $vhost ||= $class->resolveAlias;
for ( my $i = 0 ; $i < $class->tsv->{locationCount}->{$vhost} ; $i++ ) { for ( my $i = 0 ; $i < $class->tsv->{locationCount}->{$vhost} ; $i++ ) {
if ( $uri =~ $class->tsv->{locationRegexp}->{$vhost}->[$i] ) { if ( $uri =~ $class->tsv->{locationRegexp}->{$vhost}->[$i] ) {
$class->lmLog( $class->lmLog(

View File

@ -76,17 +76,18 @@ sub display {
else { else {
$skinfile = 'menu'; $skinfile = 'menu';
#utf8::decode($auth_user); #utf8::decode($auth_user);
%templateParams = ( %templateParams = (
AUTH_USER => $req->{sessionInfo}->{ $self->conf->{portalUserAttr} }, AUTH_USER =>
NEWWINDOW => $self->conf->{portalOpenLinkInNewWindow}, $req->{sessionInfo}->{ $self->conf->{portalUserAttr} },
LOGOUT_URL => $self->conf->{portal} . "?logout=1", NEWWINDOW => $self->conf->{portalOpenLinkInNewWindow},
APPSLIST_ORDER => $req->{sessionInfo}->{'appsListOrder'}, LOGOUT_URL => $self->conf->{portal} . "?logout=1",
PING => $self->conf->{portalPingInterval}, APPSLIST_ORDER => $req->{sessionInfo}->{'appsListOrder'},
PING => $self->conf->{portalPingInterval},
$self->menu->params($req), $self->menu->params($req),
); );
} }
} }
@ -310,7 +311,7 @@ sub display {
} }
$self->lmLog( "Skin returned: $skinfile", 'debug' ); $self->lmLog( "Skin returned: $skinfile", 'debug' );
return ( $skinfile, \%templateParams); return ( $skinfile, \%templateParams );
} }
@ -410,4 +411,40 @@ sub getCustomTemplateParameters {
return $customTplParams; return $customTplParams;
} }
# Build an HTML array to display sessions
# @param $sessions Array ref of hash ref containing sessions datas
# @param $title Title of the array
# @param $displayUser To display "User" column
# @param $displaError To display "Error" column
# @return HTML string
sub mkSessionArray {
my ( $self, $sessions, $title, $displayUser, $displayError ) = @_;
return "" unless ( ref $sessions eq "ARRAY" and @$sessions );
my $tmp = $title ? "<h3>$title</h3>" : "";
$tmp .=
'<table class="info"><tbody><tr>'
. ( $displayUser ? '<th trspan="user">User</th>' : '' )
. '<th trspan="date">Date</th><th trspan="ipAddr">IP address</th>';
$tmp .= "<th>" . $self->conf->{sessionDataToRemember}->{$_} . "</th>"
foreach ( keys %{ $self->conf->{sessionDataToRemember} } );
$tmp .= '<th trspan="errorMsg">Error message</th>' if ($displayError);
$tmp .= '</tr>';
foreach my $session (@$sessions) {
$tmp .= "<tr>";
$tmp .= "<td>$session->{user}</td>" if ($displayUser);
$tmp .=
"<td><script type=\"text/javascript\">var _date=new Date($session->{_utime}*1000);document.write(_date.toLocaleString());</script></td>";
$tmp .= "<td>$session->{ipAddr}</td>";
$tmp .= "<td>" . ( $session->{$_} || "" ) . "</td>"
foreach ( keys %{ $self->conf->{sessionDataToRemember} } );
$tmp .= "<td>$session->{error}</td>" if ($displayError);
$tmp .= "</tr>";
}
$tmp .= '</tbody></table>';
return $tmp;
}
1; 1;

View File

@ -19,6 +19,7 @@ use Regexp::Assemble;
# Configuration storage # Configuration storage
has localConfig => ( is => 'rw', default => sub { {} } ); has localConfig => ( is => 'rw', default => sub { {} } );
has conf => ( is => 'rw', default => sub { {} } ); has conf => ( is => 'rw', default => sub { {} } );
has menu => ( is => 'rw', default => sub { {} } );
# Sub modules # Sub modules
has _authentication => ( is => 'rw' ); has _authentication => ( is => 'rw' );
@ -74,7 +75,7 @@ sub init {
# "/" # "/"
->addUnauthRoute( '*', 'login', ['GET'] ) ->addUnauthRoute( '*', 'login', ['GET'] )
->addUnauthRoute( '*', 'postLogin', ['POST'] ) ->addUnauthRoute( '*', 'postLogin', ['POST'] )
->addAuthRoute( '*', 'authenticatedRequest', ['GET'] ) ->addAuthRoute( '*', 'authenticatedRequest', ['GET'] )
->addAuthRoute( '*', 'postAuthenticatedRequest', ['POST'] ) ->addAuthRoute( '*', 'postAuthenticatedRequest', ['POST'] )
# Core REST API # Core REST API
@ -226,7 +227,7 @@ sub reloadConf {
$self->loadPlugin($plugin) or return 0; $self->loadPlugin($plugin) or return 0;
} }
$self->menu = $self->loadModule('::Main::Menu'); $self->menu( $self->loadModule('::Main::Menu') );
1; 1;
} }

View File

@ -15,8 +15,11 @@ has menuModules => (
my %res; my %res;
foreach (qw(Appslist ChangePassword LoginHistory Logout)) { foreach (qw(Appslist ChangePassword LoginHistory Logout)) {
my $cond = $conf->{"portalDisplay$_"} // 1; my $cond = $conf->{"portalDisplay$_"} // 1;
$_[0]->p->lmLog( "Evaluate condition $cond for module $_", 'debug' ); $_[0]
$res{$_} = $_[0]->{p}->HANDLER->tsv->{jail}->jail_reval($cond); ->p->lmLog( "Evaluate condition $cond for module $_", 'debug' );
my $tmp =
$_[0]->{p}->HANDLER->tsv->{jail}->jail_reval("sub{return $cond}");
$res{$_} = $tmp if ($tmp);
} }
return \%res; return \%res;
} }
@ -42,9 +45,6 @@ sub params {
# Tab to display # Tab to display
# Get the tab URL parameter # Get the tab URL parameter
$res{DISPLAY_TAB} =
scalar( grep /^(password|logout|loginHistory)$/, $req->param("tab") )
|| "applist";
# Force password tab in case of password error # Force password tab in case of password error
if ( if (
@ -73,12 +73,15 @@ sub params {
# else calculate modules to display # else calculate modules to display
else { else {
$res{DISPLAY_MODULES} = $self->displayModules($req); $res{DISPLAY_TAB} =
scalar( grep /^(password|logout|loginHistory)$/, $req->param("tab") )
|| "applist";
} }
$res{DISPLAY_MODULES} = $self->displayModules($req);
$res{AUTH_ERROR_TYPE} = $res{AUTH_ERROR_TYPE} =
$req->error_type( $res{AUTH_ERROR} = $req->menuError ); $req->error_type( $res{AUTH_ERROR} = $req->menuError );
return \%res; return %res;
} }
## @method arrayref displayModules() ## @method arrayref displayModules()
@ -100,11 +103,11 @@ sub displayModules {
} }
elsif ( $module eq 'LoginHistory' ) { elsif ( $module eq 'LoginHistory' ) {
$moduleHash->{'SUCCESS_LOGIN'} = $moduleHash->{'SUCCESS_LOGIN'} =
$self->mkSessionArray( $self->p->mkSessionArray(
$req->{sessionInfo}->{loginHistory}->{successLogin}, $req->{sessionInfo}->{loginHistory}->{successLogin},
"", 0, 0 ); "", 0, 0 );
$moduleHash->{'FAILED_LOGIN'} = $moduleHash->{'FAILED_LOGIN'} =
$self->mkSessionArray( $self->p->mkSessionArray(
$req->{sessionInfo}->{loginHistory}->{failedLogin}, $req->{sessionInfo}->{loginHistory}->{failedLogin},
"", 0, 1 ); "", 0, 1 );
} }
@ -172,7 +175,7 @@ sub _buildCategoryHash {
next if $catkey =~ /(type|options|catname)/; next if $catkey =~ /(type|options|catname)/;
if ( $cathash->{$catkey}->{type} eq "category" ) { if ( $cathash->{$catkey}->{type} eq "category" ) {
push @$categories, push @$categories,
$self->_buildCategoryHash( $catkey, $cathash->{$catkey}, $self->_buildCategoryHash( $req, $catkey, $cathash->{$catkey},
$catlevel + 1 ); $catlevel + 1 );
} }
} }
@ -390,7 +393,7 @@ sub _filter {
} }
# Filter hash # Filter hash
$self->_filterHash($filteredHash); $self->_filterHash( $req, $filteredHash );
# Hide empty categories # Hide empty categories
$self->_isCategoryEmpty($filteredHash); $self->_isCategoryEmpty($filteredHash);
@ -403,36 +406,36 @@ sub _filter {
# @param $apphash Menu elements # @param $apphash Menu elements
# @return filtered hash # @return filtered hash
sub _filterHash { sub _filterHash {
my $self = shift; my ( $self, $req, $apphash ) = @_;
my ($apphash) = @_;
my $key;
my $appkey;
foreach $key ( keys %$apphash ) { foreach my $key ( keys %$apphash ) {
next if $key =~ /(type|options|catname)/; next if $key =~ /(type|options|catname)/;
if ( $apphash->{$key}->{type} if ( $apphash->{$key}->{type}
and $apphash->{$key}->{type} eq "category" ) and $apphash->{$key}->{type} eq "category" )
{ {
# Filter the category # Filter the category
$self->_filterHash( $apphash->{$key} ); $self->_filterHash( $req, $apphash->{$key} );
} }
if ( $apphash->{$key}->{type} if ( $apphash->{$key}->{type}
and $apphash->{$key}->{type} eq "application" ) and $apphash->{$key}->{type} eq "application" )
{ {
# Find sub applications and filter them # Find sub applications and filter them
foreach $appkey ( keys %{ $apphash->{$key} } ) { foreach my $appkey ( keys %{ $apphash->{$key} } ) {
next if $appkey =~ /(type|options|catname)/; next if $appkey =~ /(type|options|catname)/;
# We have sub elements, so we filter them # We have sub elements, so we filter them
$self->_filterHash( $apphash->{$key} ); $self->_filterHash( $req, $apphash->{$key} );
} }
# Check rights # Check rights
my $appdisplay = $apphash->{$key}->{options}->{display} my $appdisplay = $apphash->{$key}->{options}->{display}
|| "auto"; || "auto";
my $appuri = $apphash->{$key}->{options}->{uri}; my ( $vhost, $appuri ) =
$apphash->{$key}->{options}->{uri} =~ m#^https?://([^/]*)(.*)#;
$vhost =~ s/:\d+$//;
$appuri ||= '/';
# Remove if display is "no" or "off" # Remove if display is "no" or "off"
delete $apphash->{$key} and next if ( $appdisplay =~ /^(no|off)$/ ); delete $apphash->{$key} and next if ( $appdisplay =~ /^(no|off)$/ );
@ -441,7 +444,8 @@ sub _filterHash {
next if ( $appdisplay =~ /^(yes|on)$/ ); next if ( $appdisplay =~ /^(yes|on)$/ );
# Check grant function if display is "auto" (this is the default) # Check grant function if display is "auto" (this is the default)
delete $apphash->{$key} unless ( $self->_grant($appuri) ); delete $apphash->{$key}
unless ( $self->p->HANDLER->grant( $appuri, undef, $vhost ) );
next; next;
} }
} }

View File

@ -80,9 +80,6 @@ PE77:"You have to type the captcha",
PE78:"Please enter your information", PE78:"Please enter your information",
PE79:"An information is missing", PE79:"An information is missing",
PE80:"This address is already used", PE80:"This address is already used",
PM0:"User",
PM1:"Date",
PM2:"IP address",
PM3:"The following sessions have been closed", PM3:"The following sessions have been closed",
PM4:"Other active sessions", PM4:"Other active sessions",
PM5:"Remove other sessions", PM5:"Remove other sessions",
@ -101,7 +98,6 @@ PM17:"Update Common Domain Cookie",
PM18:"Parameter %s requested for federation isn't available", PM18:"Parameter %s requested for federation isn't available",
PM19:"Data usage policy is available at", PM19:"Data usage policy is available at",
PM20:"Do you agree to provide the following parameters?", PM20:"Do you agree to provide the following parameters?",
PM21:"Error Message",
PM22:"Your last logins", PM22:"Your last logins",
PM23:"Your last failed logins", PM23:"Your last failed logins",
PM24:"The application %s would like to know:", PM24:"The application %s would like to know:",
@ -138,9 +134,11 @@ connectedAs:"Connected as",
continue:"Continue", continue:"Continue",
createAccount:"Create an account", createAccount:"Create an account",
currentPwd:"Current password", currentPwd:"Current password",
date:"Date",
enterCred:"Please enter your credentials", enterCred:"Please enter your credentials",
enterOpenIDLogin:"Please enter your OpenID login", enterOpenIDLogin:"Please enter your OpenID login",
enterYubikey:"Please use your Yubikey", enterYubikey:"Please use your Yubikey",
errorMsg:"Error Message",
firstName:"First name", firstName:"First name",
forgotPwd:"Forgot your password?", forgotPwd:"Forgot your password?",
generatePwd:"Generate the password automatically", generatePwd:"Generate the password automatically",
@ -150,6 +148,7 @@ gplSoft:"free software covered by the GPL license",
hello:"Hello", hello:"Hello",
imSure:"I'm sure", imSure:"I'm sure",
info:"Information", info:"Information",
ipAddr:"IP address",
lastFailedLogins:"Last failed logins", lastFailedLogins:"Last failed logins",
lastLogins:"Last logins", lastLogins:"Last logins",
lastName:"Last name", lastName:"Last name",
@ -188,6 +187,7 @@ serverError:"Error occurs on the server",
serviceProvidedBy:"Service provided by", serviceProvidedBy:"Service provided by",
SSOSessionInactive:"SSO session inactive", SSOSessionInactive:"SSO session inactive",
submit:"Submit", submit:"Submit",
user:"User",
useYubikey:"use your Yubikey", useYubikey:"use your Yubikey",
wait:"Wait", wait:"Wait",
warning:"Warning", warning:"Warning",

View File

@ -80,9 +80,6 @@ PE77:"Vous devez saisir le captcha",
PE78:"Merci de saisir vos informations", PE78:"Merci de saisir vos informations",
PE79:"Une information est manquante", PE79:"Une information est manquante",
PE80:"Cette adresse est déjà utilisée", PE80:"Cette adresse est déjà utilisée",
PM0:"Utilisateur",
PM1:"Date",
PM2:"Adresse IP",
PM3:"Les sessions suivantes ont été fermées", PM3:"Les sessions suivantes ont été fermées",
PM4:"Autres sessions ouvertes", PM4:"Autres sessions ouvertes",
PM5:"Fermer les autres sessions", PM5:"Fermer les autres sessions",
@ -101,7 +98,6 @@ PM17:"Mise à jour du cookie de domaine commun",
PM18:"Le paramètre %s exigé pour la fédération n'est pas disponible", PM18:"Le paramètre %s exigé pour la fédération n'est pas disponible",
PM19:"La politique d'utilisation des données est disponible ici", PM19:"La politique d'utilisation des données est disponible ici",
PM20:"Consentez-vous à communiquer les paramètres suivants&nbsp;?", PM20:"Consentez-vous à communiquer les paramètres suivants&nbsp;?",
PM21:"Message d'erreur",
PM22:"Vos dernières connexions", PM22:"Vos dernières connexions",
PM23:"Vos dernières connexions refusées", PM23:"Vos dernières connexions refusées",
PM24:"L'application %s voudrait connaître :", PM24:"L'application %s voudrait connaître :",
@ -138,9 +134,11 @@ connect:"Se connecter",
continue:"Continuer", continue:"Continuer",
createAccount:"Créer un compte", createAccount:"Créer un compte",
currentPwd:"Mot de passe actuel", currentPwd:"Mot de passe actuel",
date:"Date",
enterCred:"Merci de vous authentifier", enterCred:"Merci de vous authentifier",
enterOpenIDLogin:"Entrez votre identifiant OpenID", enterOpenIDLogin:"Entrez votre identifiant OpenID",
enterYubikey:"Utilisez votre Yubikey", enterYubikey:"Utilisez votre Yubikey",
errorMsg:"Message d'erreur",
firstName:"Prénom", firstName:"Prénom",
forgotPwd:"Mot de passe oublié ?", forgotPwd:"Mot de passe oublié ?",
generatePwd:"Générer le mot de passe automatiquement", generatePwd:"Générer le mot de passe automatiquement",
@ -150,6 +148,7 @@ gplSoft:"logiciel libre protégé par la licence GPL",
hello:"Bonjour", hello:"Bonjour",
imSure:"Je suis sûr", imSure:"Je suis sûr",
info:"Information", info:"Information",
ipAddr:"Adresse IP",
lastFailedLogins:"Dernières connexions refusées", lastFailedLogins:"Dernières connexions refusées",
lastLogins:"Dernières connexions", lastLogins:"Dernières connexions",
lastName:"Nom", lastName:"Nom",
@ -188,6 +187,7 @@ serverError:"Une erreur est survenue sur le serveur",
serviceProvidedBy:"Ce service est fourni par", serviceProvidedBy:"Ce service est fourni par",
SSOSessionInactive:"Session SSO inactive", SSOSessionInactive:"Session SSO inactive",
submit:"Envoyer", submit:"Envoyer",
user:"Utilisateur",
useYubikey:"utilisez votre Yubikey", useYubikey:"utilisez votre Yubikey",
wait:"Attendre", wait:"Attendre",
warning:"Attention", warning:"Attention",