Merge branch 'v2.0'

This commit is contained in:
Xavier Guimard 2019-05-17 10:26:19 +02:00
commit 5a1c090a18
27 changed files with 249 additions and 42 deletions

View File

@ -1,4 +1,4 @@
lemonldap-ng (2.0.4) bionic; urgency=medium
lemonldap-ng (2.0.4) stable; urgency=high
* Bugs:
* #1684: UI manager: boolean values do not appears in configuration forms with Yaml config format
@ -35,7 +35,7 @@ lemonldap-ng (2.0.4) bionic; urgency=medium
-- Clément <clem.oudot@gmail.com> Sun, 12 May 2019 16:17:01 +0200
lemonldap-ng (2.0.3) bionic; urgency=medium
lemonldap-ng (2.0.3) stable; urgency=medium
* Bugs:
* #1543: Redirection lost with CAS RP -> Choice -> SAML Discovery Protocol -> SAML IDP
@ -86,7 +86,7 @@ lemonldap-ng (2.0.3) bionic; urgency=medium
-- Clément <clem.oudot@gmail.com> Thu, 11 Apr 2019 10:09:35 +0200
lemonldap-ng (2.0.2) bionic; urgency=medium
lemonldap-ng (2.0.2) stable; urgency=medium
* Bugs:
* #1574: "Manager is unprotected" message when whatToTrace value is not the default
@ -130,7 +130,7 @@ lemonldap-ng (2.0.2) bionic; urgency=medium
-- Clément <clem.oudot@gmail.com> Tue, 12 Feb 2019 08:57:14 +0100
lemonldap-ng (2.0.1) artful; urgency=medium
lemonldap-ng (2.0.1) stable; urgency=medium
* Bugs:
* #1564: Function authLogout is missing in package "Lemonldap::NG::Portal::Auth::SSL"
@ -158,7 +158,7 @@ lemonldap-ng (2.0.1) artful; urgency=medium
-- Clément <clem.oudot@gmail.com> Fri, 21 Dec 2018 15:12:13 +0100
lemonldap-ng (2.0.0) artful; urgency=medium
lemonldap-ng (2.0.0) stable; urgency=medium
* Bugs:
* #757: "Attempt to free unreferenced scalar" in Lemonldap::NG::Common::Session

View File

@ -10,7 +10,8 @@ sub new {
my $show = 1;
foreach (qw(error warn notice info debug)) {
if ($show) {
eval qq'sub $_ {print STDERR "[$_] \$_[1]\n"}';
eval
qq'sub $_ {print STDERR "[".localtime."] [LLNG:\$\$] [$_] \$_[1]\n"}';
}
else {
eval qq'sub $_ {1}';

View File

@ -23,7 +23,8 @@ sub new {
my $name = $_;
$name = 'warning' if ( $_ eq 'warn' );
$name = 'err' if ( $_ eq 'error' );
eval qq'sub $_ {syslog("$name|".\$_[0]->{facility},\$_[1])}';
eval
qq'sub $_ {syslog("$name|".\$_[0]->{facility},"[$_] ". \$_[1])}';
die $@ if ($@);
}
else {

View File

@ -28,7 +28,7 @@ sub addRoutes {
my $hiddenKeys = '';
$hiddenKeys = $self->{viewerHiddenKeys};
my @enabledKeys = ();
my @keys = qw(virtualHosts samlIDPMetaDataNodes samlSPMetaDataNodes
my @keys = qw(virtualHosts samlIDPMetaDataNodes samlSPMetaDataNodes
applicationList oidcOPMetaDataNodes oidcRPMetaDataNodes
casSrvMetaDataNodes casAppMetaDataNodes
authChoiceModules grantSessionRules combModules

View File

@ -78,8 +78,14 @@ sub createToken {
# Create a new session
my $tsession =
$self->p->getApacheSession( undef, info => $infos, kind => 'TOKEN' );
$self->logger->debug("Token $tsession->{id} created");
return $tsession->id;
if ( $tsession->{id} ) {
$self->logger->debug("Token $tsession->{id} created");
return $tsession->id;
}
else {
$self->logger->error("NO token created");
return undef;
}
}
}

View File

@ -184,7 +184,7 @@ sub send_mail {
foreach ( keys %cid ) {
$message->attach(
Type => "image/" . ( $cid{$_} =~ m/\.(\w+)/ )[0],
Id => $_,
Id => $_,
Path => $self->conf->{templateDir} . "/"
. $self->conf->{portalSkin} . "/"
. $cid{$_},

View File

@ -873,6 +873,15 @@ sub lmError {
# Check URL
$self->controlUrl($req);
$req->pdata( {} );
if ( $req->wantJSON ) {
return $self->sendJSONresponse(
$req,
{ error => $httpError, result => 0 },
code => $httpError
);
}
my %templateParams = (
MAIN_LOGO => $self->conf->{portalMainLogo},
@ -880,7 +889,6 @@ sub lmError {
LOGOUT_URL => $self->conf->{portal} . "?logout=1",
URL => $req->{urldc},
);
$req->pdata( {} );
# Error code
$templateParams{"ERROR$_"} = ( $httpError == $_ ? 1 : 0 )

View File

@ -64,13 +64,16 @@ sub check {
my $token = $req->param('token');
unless ($token) {
$self->userLogger->warn('checkUser try without token');
$msg = PE_NOTOKEN;
$token = $self->ott->createToken( $req->userData );
$msg = PE_NOTOKEN;
$token = $self->ott->createToken( { _user => $req->{_user}, } );
}
unless ( $self->ott->getToken($token) ) {
$token = $self->ott->getToken($token);
#unless ( $token and $token->{_user} eq $req->{_user} ) {
unless ($token) {
$self->userLogger->warn('checkUser try with expired/bad token');
$msg = PE_TOKENEXPIRED;
$token = $self->ott->createToken( $req->userData );
$msg = PE_TOKENEXPIRED;
$token = $self->ott->createToken( { _user => $req->{_user}, } );
}
my $params = {
PORTAL => $self->conf->{portal},
@ -109,7 +112,7 @@ sub check {
LOGIN => '',
TOKEN => (
$self->ottRule->( $req, {} )
? $self->ott->createToken( $req->userData )
? $self->ott->createToken( { _user => $req->{_user}, } )
: ''
)
}
@ -136,7 +139,12 @@ sub check {
$attrs = {};
}
else {
$msg = 'checkUser';
#$msg = 'checkUser';
$msg =
$self->{conf}->{impersonationMergeSSOgroups}
? 'checkUserMerged'
: 'checkUser';
# Create an array of hashes for template loop
$self->logger->debug("Delete hidden or empty attributes");
@ -215,7 +223,7 @@ sub check {
GROUPS => $array_attrs->[0],
TOKEN => (
$self->ottRule->( $req, {} )
? $self->ott->createToken( $req->userData )
? $self->ott->createToken( { _user => $req->{_user}, } )
: ''
)
};
@ -258,18 +266,24 @@ sub display {
# Display form
my $params = {
PORTAL => $self->conf->{portal},
MAIN_LOGO => $self->conf->{portalMainLogo},
LANGS => $self->conf->{showLanguages},
MSG => 'checkUser',
ALERTE => 'alert-info',
PORTAL => $self->conf->{portal},
MAIN_LOGO => $self->conf->{portalMainLogo},
LANGS => $self->conf->{showLanguages},
MSG => (
$self->{conf}->{impersonationMergeSSOgroups} ? 'checkUserMerged'
: 'checkUser'
),
ALERTE => (
$self->{conf}->{impersonationMergeSSOgroups} ? 'alert-warning'
: 'alert-info'
),
LOGIN => $req->{userData}->{uid},
ATTRIBUTES => $array_attrs->[2],
MACROS => $array_attrs->[1],
GROUPS => $array_attrs->[0],
TOKEN => (
$self->ottRule->( $req, {} )
? $self->ott->createToken( $req->userData )
? $self->ott->createToken( { _user => $req->{_user}, } )
: ''
)
};

View File

@ -26,9 +26,9 @@ translatePage = (lang) ->
txt = translate args.shift()
for v in args
txt = txt.replace /%[sd]/, v
$(this).text txt
$(this).html txt
$("[trmsg]").each ->
$(this).text translate "PE#{$(this).attr 'trmsg'}"
$(this).html translate "PE#{$(this).attr 'trmsg'}"
msg = translate "PE#{$(this).attr 'trmsg'}"
if msg.match /_hide_/
$(this).parent().hide()

View File

@ -1,4 +1,4 @@
// Generated by CoffeeScript 1.12.7
// Generated by CoffeeScript 1.12.8
/*
LemonLDAP::NG Portal jQuery scripts
@ -34,11 +34,11 @@ LemonLDAP::NG Portal jQuery scripts
v = args[i];
txt = txt.replace(/%[sd]/, v);
}
return $(this).text(txt);
return $(this).html(txt);
});
$("[trmsg]").each(function() {
var msg;
$(this).text(translate("PE" + ($(this).attr('trmsg'))));
$(this).html(translate("PE" + ($(this).attr('trmsg'))));
msg = translate("PE" + ($(this).attr('trmsg')));
if (msg.match(/_hide_/)) {
return $(this).parent().hide();

File diff suppressed because one or more lines are too long

View File

@ -108,6 +108,7 @@
"changePwd":"غير كلمة المرور الخاصة بك",
"checkLastLogins":"تحقق من آخر تسجيلات دخول الخاصة بي",
"checkUser":"Check user SSO profile",
"checkUserMerged":"Check user SSO profile. Real and Spoofed SSO groups are merged!!!",
"choose2f":"Choose your second factor",
"chooseApp":"اختر أحد التطبيقات المسموح لك بالدخول إليها",
"clickHere":"الرجاء الضغط هنا",

View File

@ -108,6 +108,7 @@
"changePwd":"Ändere dein Passwort",
"checkLastLogins":"Überprüfe meine letzten Logins",
"checkUser":"Check user SSO profile",
"checkUserMerged":"Check user SSO profile. Real and Spoofed SSO groups are merged!!!",
"choose2f":"Wählen deinen Ihren zweiten Faktor",
"chooseApp":"Wählen Sie eine Anwendung aus, auf die du zugreifen darfst",
"clickHere":"Bitte hier klicken",

View File

@ -108,6 +108,7 @@
"changePwd":"Change your password",
"checkLastLogins":"Check my last logins",
"checkUser":"Check user SSO profile",
"checkUserMerged":"Check user SSO profile. Real and Spoofed SSO groups are merged!!!",
"choose2f":"Choose your second factor",
"chooseApp":"Choose an application your are allowed to access to",
"clickHere":"Please click here",

View File

@ -108,6 +108,7 @@
"changePwd":"Change your password",
"checkLastLogins":"Check my last logins",
"checkUser":"Check user SSO profile",
"checkUserMerged":"Check user SSO profile. Real and Spoofed SSO groups are merged!!!",
"choose2f":"Choose your second factor",
"chooseApp":"Choose an application your are allowed to access to",
"clickHere":"Please click here",

View File

@ -108,6 +108,7 @@
"changePwd":"Vaihda salasanasi",
"checkLastLogins":"Tarkista viimeiset kirjautumiseni",
"checkUser":"Check user SSO profile",
"checkUserMerged":"Check user SSO profile. Real and Spoofed SSO groups are merged!!!",
"choose2f":"Choose your second factor",
"chooseApp":"Choose an application your are allowed to access to",
"clickHere":"Please click here",

View File

@ -108,6 +108,7 @@
"changePwd":"Changez votre mot de passe",
"checkLastLogins":"Voir mes dernières connexions",
"checkUser":"Vérifier le profil SSO d'un utilisateur",
"checkUserMerged":"Vérifier le profil SSO d'un utilisateur. Les groupes SSO réels et usurpés sont fusionnés !!!",
"choose2f":"Choisissez votre second facteur",
"chooseApp":"Choisissez une application à laquelle vous êtes autorisé à accéder",
"clickHere":"Cliquez ici",

View File

@ -108,6 +108,7 @@
"changePwd":"Cambia la tua password",
"checkLastLogins":"Controllare i miei ultimi accessi",
"checkUser":"Controlla il profilo SSO dell'utente",
"checkUserMerged":"Check user SSO profile. Real and Spoofed SSO groups are merged!!!",
"choose2f":"Scegli il tuo secondo fattore",
"chooseApp":"Scegli un'applicazione alla quale ti è consentito l'accesso",
"clickHere":"Per favore clicka qui",

View File

@ -108,6 +108,7 @@
"changePwd":"Change your password",
"checkLastLogins":"Check my last logins",
"checkUser":"Check user SSO profile",
"checkUserMerged":"Check user SSO profile. Real and Spoofed SSO groups are merged!!!",
"choose2f":"Choose your second factor",
"chooseApp":"Choose an application your are allowed to access to",
"clickHere":"Please click here",

View File

@ -108,6 +108,7 @@
"changePwd":"Change your password",
"checkLastLogins":"Check my last logins",
"checkUser":"Check user SSO profile",
"checkUserMerged":"Check user SSO profile. Real and Spoofed SSO groups are merged!!!",
"choose2f":"Choose your second factor",
"chooseApp":"Choose an application your are allowed to access to",
"clickHere":"Please click here",

View File

@ -108,6 +108,7 @@
"changePwd":"Change your password",
"checkLastLogins":"Check my last logins",
"checkUser":"Check user SSO profile",
"checkUserMerged":"Check user SSO profile. Real and Spoofed SSO groups are merged!!!",
"choose2f":"Choose your second factor",
"chooseApp":"Choose an application your are allowed to access to",
"clickHere":"Please click here",

View File

@ -108,6 +108,7 @@
"changePwd":"Thay đổi mật khẩu của bạn",
"checkLastLogins":"Kiểm tra lần đăng nhập cuối cùng của bạn",
"checkUser":"Check user SSO profile",
"checkUserMerged":"Check user SSO profile. Real and Spoofed SSO groups are merged!!!",
"choose2f":"Choose your second factor",
"chooseApp":"Chọn một ứng dụng bạn được phép truy cập vào",
"clickHere":"Vui lòng nhấp vào đây",

View File

@ -108,6 +108,7 @@
"changePwd":"修改您的密码",
"checkLastLogins":"Check my last logins",
"checkUser":"Check user SSO profile",
"checkUserMerged":"Check user SSO profile. Real and Spoofed SSO groups are merged!!!",
"choose2f":"Choose your second factor",
"chooseApp":"Choose an application your are allowed to access to",
"clickHere":"请点击这里",

View File

@ -0,0 +1,162 @@
use Test::More;
use strict;
use IO::String;
BEGIN {
require 't/test-lib.pm';
}
my $res;
my $client = LLNG::Manager::Test->new( {
ini => {
logLevel => 'error',
authentication => 'Demo',
userDB => 'Same',
loginHistoryEnabled => 0,
brutForceProtection => 0,
portalMainLogo => 'common/logos/logo_llng_old.png',
checkUser => 1,
requireToken => 1,
tokenUseGlobalStorage => 1,
formTimeout => 2,
checkUserDisplayPersistentInfo => 1,
checkUserDisplayEmptyValues => 1,
}
}
);
## Try to authenticate
ok( $res = $client->_get( '/', accept => 'text/html' ), 'Get Menu', );
count(1);
my ( $host, $url, $query ) =
expectForm( $res, '#', undef, 'user', 'password', 'token' );
$query =~ s/user=/user=dwho/;
$query =~ s/password=/password=dwho/;
ok(
$res = $client->_post(
'/',
IO::String->new($query),
length => length($query),
accept => 'text/html',
),
'Auth query'
);
count(1);
my $id = expectCookie($res);
expectRedirection( $res, 'http://auth.example.com/' );
# CheckUser form
# ------------------------
ok(
$res = $client->_get(
'/checkuser',
cookie => "lemonldap=$id",
accept => 'text/html'
),
'CheckUser form',
);
count(1);
( $host, $url, $query ) =
expectForm( $res, undef, '/checkuser', 'user', 'url', 'token' );
ok( $res->[2]->[0] =~ m%<span trspan="checkUser">%, 'Found trspan="checkUser"' )
or explain( $res->[2]->[0], 'trspan="checkUser"' );
count(1);
# Expired token
sleep 3;
$query =~ s/user=/user=rtyler/;
$query =~ s/url=/url=http%3A%2F%2Ftest1.example.com/;
ok(
$res = $client->_post(
'/checkuser',
IO::String->new($query),
cookie => "lemonldap=$id",
length => length($query),
accept => 'text/html',
),
'POST checkuser'
);
ok( $res->[2]->[0] =~ m%<span trspan="PE82"></span>%, 'Found PE_TOKENEXPIRED' )
or explain( $res->[2]->[0], 'trspan="PE82"' );
count(2);
( $host, $url, $query ) =
expectForm( $res, undef, '/checkuser', 'user', 'url', 'token' );
# Valid token
$query =~ s/user=/user=rtyler/;
$query =~ s/url=/url=http%3A%2F%2Ftest1.example.com/;
ok(
$res = $client->_post(
'/checkuser',
IO::String->new($query),
cookie => "lemonldap=$id",
length => length($query),
accept => 'text/html',
),
'POST checkuser'
);
count(1);
( $host, $url, $query ) =
expectForm( $res, undef, '/checkuser', 'user', 'url', 'token' );
ok( $res->[2]->[0] =~ m%<span trspan="checkUser">%, 'Found trspan="checkUser"' )
or explain( $res->[2]->[0], 'trspan="checkUser"' );
ok(
$res->[2]->[0] =~
m%<div class="alert alert-success"><b><span trspan="allowed"></span></b></div>%,
'Found trspan="allowed"'
) or explain( $res->[2]->[0], 'trspan="allowed"' );
ok( $res->[2]->[0] =~ m%<span trspan="headers">%, 'Found trspan="headers"' )
or explain( $res->[2]->[0], 'trspan="headers"' );
ok( $res->[2]->[0] =~ m%<span trspan="groups_sso">%,
'Found trspan="groups_sso"' )
or explain( $res->[2]->[0], 'trspan="groups_sso"' );
ok( $res->[2]->[0] =~ m%<span trspan="macros">%, 'Found trspan="macros"' )
or explain( $res->[2]->[0], 'trspan="macros"' );
ok( $res->[2]->[0] =~ m%<span trspan="attributes">%,
'Found trspan="attributes"' )
or explain( $res->[2]->[0], 'trspan="attributes"' );
ok( $res->[2]->[0] =~ m%<td class="align-middle">Auth-User</td>%,
'Found Auth-User' )
or explain( $res->[2]->[0], 'Header Key: Auth-User' );
ok( $res->[2]->[0] =~ m%<td class="align-middle">rtyler</td>%, 'Found rtyler' )
or explain( $res->[2]->[0], 'Header Value: rtyler' );
ok( $res->[2]->[0] =~ m%<td class="align-middle">su</td>%, 'Found su' )
or explain( $res->[2]->[0], 'SSO Groups: su' );
ok( $res->[2]->[0] =~ m%<td class="align-middle">_whatToTrace</td>%,
'Found _whatToTrace' )
or explain( $res->[2]->[0], 'Macro Key _whatToTrace' );
ok( $res->[2]->[0] =~ m%<td class="text-left">uid</td>%, 'Found uid' )
or explain( $res->[2]->[0], 'Attribute Value uid' );
count(11);
$query =~ s/user=dwho/user=msmith/;
$query =~
s/url=http%3A%2F%2Ftest1.example.com/url=http%3A%2F%2Fmanager.example.com%2Fmanager.html/;
ok(
$res = $client->_post(
'/checkuser',
IO::String->new($query),
cookie => "lemonldap=$id",
length => length($query),
accept => 'text/html',
),
'POST checkuser'
);
ok(
$res->[2]->[0] =~
m%<div class="alert alert-danger"><b><span trspan="forbidden"></span></b></div>%,
'Found trspan="forbidden"'
) or explain( $res->[2]->[0], 'trspan="forbidden"' );
count(2);
$client->logout($id);
clean_sessions();
done_testing( count() );

View File

@ -18,6 +18,7 @@ my $client = LLNG::Manager::Test->new( {
portalMainLogo => 'common/logos/logo_llng_old.png',
checkUser => 1,
requireToken => 1,
tokenUseGlobalStorage => 0,
formTimeout => 2,
checkUserDisplayPersistentInfo => 1,
checkUserDisplayEmptyValues => 1,

View File

@ -62,8 +62,9 @@ ok(
count(1);
( $host, $url, $query ) =
expectForm( $res, undef, '/checkuser', 'user', 'url' );
ok( $res->[2]->[0] =~ m%<span trspan="checkUser">%, 'Found trspan="checkUser"' )
or explain( $res->[2]->[0], 'trspan="checkUser"' );
ok( $res->[2]->[0] =~ m%<span trspan="checkUserMerged">%,
'Found trspan="checkUserMerged"' )
or explain( $res->[2]->[0], 'trspan="checkUserMerged"' );
count(1);
$query =~ s/url=/url=test1.example.com/;
@ -82,8 +83,9 @@ count(1);
( $host, $url, $query ) =
expectForm( $res, undef, '/checkuser', 'user', 'url' );
ok( $res->[2]->[0] =~ m%<span trspan="checkUser">%, 'Found trspan="checkUser"' )
or explain( $res->[2]->[0], 'trspan="checkUser"' );
ok( $res->[2]->[0] =~ m%<span trspan="checkUserMerged">%,
'Found trspan="checkUserMerged"' )
or explain( $res->[2]->[0], 'trspan="checkUserMerged"' );
ok(
$res->[2]->[0] =~
m%<div class="alert alert-success"><b><span trspan="allowed"></span></b></div>%,

View File

@ -11,12 +11,12 @@ count(1);
my $client = LLNG::Manager::Test->new( {
ini => {
logLevel => 'error',
mail2fActivation => 1,
mail2fCodeRegex => '\d{4}',
authentication => 'Demo',
userDB => 'Same',
tokenUseGlobalStorage => 1,
logLevel => 'error',
mail2fActivation => 1,
mail2fCodeRegex => '\d{4}',
authentication => 'Demo',
userDB => 'Same',
tokenUseGlobalStorage => 1,
}
}
);