Merge branch 'v2.0'
This commit is contained in:
commit
499b16bd07
|
@ -24,7 +24,7 @@ use constant MANAGERSECTION => "manager";
|
|||
use constant SESSIONSEXPLORERSECTION => "sessionsExplorer";
|
||||
use constant APPLYSECTION => "apply";
|
||||
our $hashParameters = qr/^(?:(?:l(?:o(?:ca(?:lSessionStorageOption|tionRule)|goutService)|dapExportedVar|wp(?:Ssl)?Opt)|(?:(?:d(?:emo|bi)|facebook|webID)ExportedVa|exported(?:Heade|Va)|issuerDBGetParamete)r|re(?:moteGlobalStorageOption|st2f(?:Verify|Init)Arg|loadUrl)|g(?:r(?:antSessionRule|oup)|lobalStorageOption)|n(?:otificationStorageOption|ginxCustomHandler)|macro)s|o(?:idc(?:RPMetaData(?:(?:Option(?:sExtraClaim)?|ExportedVar)s|Node)|OPMetaData(?:(?:ExportedVar|Option)s|J(?:SON|WKS)|Node)|S(?:erviceMetaDataAuthnContext|torageOptions))|penIdExportedVars)|s(?:aml(?:S(?:PMetaData(?:(?:ExportedAttribute|Option)s|Node|XML)|torageOptions)|IDPMetaData(?:(?:ExportedAttribute|Option)s|Node|XML))|essionDataToRemember|laveExportedVars|fExtra)|c(?:as(?:S(?:rvMetaData(?:(?:ExportedVar|Option)s|Node)|torageOptions)|A(?:ppMetaData(?:(?:ExportedVar|Option)s|Node)|ttributes))|(?:ustomAddParam|ombModule)s)|p(?:ersistentStorageOptions|o(?:rtalSkinRules|st))|a(?:ut(?:hChoiceMod|oSigninR)ules|pplicationList)|v(?:hostOptions|irtualHost)|S(?:MTPTLSOpts|SLVarIf))$/;
|
||||
our $boolKeys = qr/^(?:s(?:aml(?:IDP(?:MetaDataOptions(?:(?:Check(?:S[LS]OMessageSignatur|Audienc|Tim)|IsPassiv)e|A(?:llow(?:LoginFromIDP|ProxiedAuthn)|daptSessionUtime)|Force(?:Authn|UTF8)|StoreSAMLToken|RelayStateURL)|SSODescriptorWantAuthnRequestsSigned)|S(?:P(?:MetaDataOptions(?:(?:CheckS[LS]OMessageSignatur|OneTimeUs)e|EnableIDPInitiatedURL|ForceUTF8)|SSODescriptor(?:WantAssertion|AuthnRequest)sSigned)|erviceUseCertificateInResponse)|DiscoveryProtocol(?:Activation|IsPassive)|CommonDomainCookieActivation|UseQueryStringSpecific|MetadataForceUTF8)|ingle(?:Session(?:UserByIP)?|(?:UserBy)?IP)|oap(?:Session|Config)Server|t(?:ayConnecte|orePasswor)d|kipRenewConfirmation|fRemovedUseNotif|howLanguages|slByAjax)|o(?:idc(?:ServiceAllow(?:(?:AuthorizationCode|Implicit|Hybrid)Flow|DynamicRegistration)|RPMetaDataOptions(?:LogoutSessionRequired|BypassConsent|RequirePKCE|Public)|OPMetaDataOptions(?:(?:CheckJWTSignatur|UseNonc)e|StoreIDToken))|ldNotifFormat)|c(?:a(?:ptcha_(?:register|login|mail)_enabled|sSrvMetaDataOptions(?:Gateway|Renew))|heck(?:User(?:Display(?:PersistentInfo|EmptyValues))?|State|XSS)|o(?:ntextSwitchingStopWithLogout|rsEnabled)|da)|p(?:ortal(?:ErrorOn(?:ExpiredSession|MailNotFound)|DisplayRe(?:setPassword|gister)|(?:CheckLogin|Statu)s|OpenLinkInNewWindow|RequireOldPassword|ForceAuthn|AntiFrame)|roxyUseSoap)|l(?:dap(?:(?:Group(?:DecodeSearchedValu|Recursiv)|UsePasswordResetAttribut)e|(?:AllowResetExpired|Set)Password|ChangePasswordAsUser|PpolicyControl)|oginHistoryEnabled)|i(?:ssuerDB(?:OpenID(?:Connect)?|SAML|CAS|Get)Activation|mpersonationSkipEmptyValues)|to(?:tp2f(?:UserCan(?:Chang|Remov)eKey|DisplayExistingSecret)|kenUseGlobalStorage)|u(?:se(?:RedirectOn(?:Forbidden|Error)|SafeJail)|2fUserCanRemoveKey|pgradeSession)|no(?:tif(?:ication(?:Server)?|y(?:Deleted|Other))|AjaxHook)|(?:mai(?:lOnPasswordChang|ntenanc)|vhostMaintenanc)e|d(?:isablePersistentStorage|biDynamicHashEnabled)|rest(?:(?:Session|Config)Server|ExportSecretKeys)|h(?:ideOldPassword|ttpOnly)|yubikey2fUserCanRemoveKey|(?:activeTim|wsdlServ)er|krb(?:RemoveDomain|ByJs)|bruteForceProtection)$/;
|
||||
our $boolKeys = qr/^(?:s(?:aml(?:IDP(?:MetaDataOptions(?:(?:Check(?:S[LS]OMessageSignatur|Audienc|Tim)|IsPassiv)e|A(?:llow(?:LoginFromIDP|ProxiedAuthn)|daptSessionUtime)|Force(?:Authn|UTF8)|StoreSAMLToken|RelayStateURL)|SSODescriptorWantAuthnRequestsSigned)|S(?:P(?:MetaDataOptions(?:(?:CheckS[LS]OMessageSignatur|OneTimeUs)e|EnableIDPInitiatedURL|ForceUTF8)|SSODescriptor(?:WantAssertion|AuthnRequest)sSigned)|erviceUseCertificateInResponse)|DiscoveryProtocol(?:Activation|IsPassive)|CommonDomainCookieActivation|UseQueryStringSpecific|MetadataForceUTF8)|ingle(?:Session(?:UserByIP)?|(?:UserBy)?IP)|oap(?:Session|Config)Server|t(?:ayConnecte|orePasswor)d|kipRenewConfirmation|fRemovedUseNotif|howLanguages|slByAjax)|o(?:idc(?:ServiceAllow(?:(?:AuthorizationCode|Implicit|Hybrid)Flow|DynamicRegistration)|RPMetaDataOptions(?:LogoutSessionRequired|BypassConsent|RequirePKCE|Public)|OPMetaDataOptions(?:(?:CheckJWTSignatur|UseNonc)e|StoreIDToken))|ldNotifFormat)|c(?:a(?:ptcha_(?:register|login|mail)_enabled|sSrvMetaDataOptions(?:Gateway|Renew))|heck(?:User(?:Display(?:PersistentInfo|EmptyValues))?|State|XSS)|o(?:ntextSwitchingStopWithLogout|rsEnabled)|da)|p(?:ortal(?:ErrorOn(?:ExpiredSession|MailNotFound)|DisplayRe(?:setPassword|gister)|(?:CheckLogin|Statu)s|OpenLinkInNewWindow|RequireOldPassword|ForceAuthn|AntiFrame)|roxyUseSoap)|l(?:dap(?:(?:Group(?:DecodeSearchedValu|Recursiv)|UsePasswordResetAttribut)e|(?:AllowResetExpired|Set)Password|ChangePasswordAsUser|PpolicyControl)|oginHistoryEnabled)|i(?:ssuerDB(?:OpenID(?:Connect)?|SAML|CAS|Get)Activation|mpersonationSkipEmptyValues)|no(?:tif(?:ication(?:Server(?:(?:POS|GE)T|DELETE)?)?|y(?:Deleted|Other))|AjaxHook)|to(?:tp2f(?:UserCan(?:Chang|Remov)eKey|DisplayExistingSecret)|kenUseGlobalStorage)|u(?:se(?:RedirectOn(?:Forbidden|Error)|SafeJail)|2fUserCanRemoveKey|pgradeSession)|(?:mai(?:lOnPasswordChang|ntenanc)|vhostMaintenanc)e|d(?:isablePersistentStorage|biDynamicHashEnabled)|rest(?:(?:Session|Config)Server|ExportSecretKeys)|h(?:ideOldPassword|ttpOnly)|yubikey2fUserCanRemoveKey|(?:activeTim|wsdlServ)er|krb(?:RemoveDomain|ByJs)|bruteForceProtection)$/;
|
||||
|
||||
our @sessionTypes = ( 'remoteGlobal', 'global', 'localSession', 'persistent', 'saml', 'oidc', 'cas' );
|
||||
|
||||
|
|
|
@ -158,6 +158,9 @@ sub defaultValues {
|
|||
'multiValuesSeparator' => '; ',
|
||||
'mySessionAuthorizedRWKeys' =>
|
||||
[ '_appsListOrder', '_oidcConnectedRP', '_oidcConsents' ],
|
||||
'notificationServerPOST' => 1,
|
||||
'notificationServerSentAttributes' =>
|
||||
'uid reference date title subtitle text check',
|
||||
'notificationStorage' => 'File',
|
||||
'notificationStorageOptions' => {
|
||||
'dirName' => '/var/lib/lemonldap-ng/notifications'
|
||||
|
|
|
@ -218,7 +218,8 @@ m[^(?:(?:\-+\s*BEGIN\s+(?:PUBLIC\s+KEY|CERTIFICATE)\s*\-+\r?\n)?[a-zA-Z0-9/\+\r\
|
|||
},
|
||||
'select' => {
|
||||
'test' => sub {
|
||||
my $test = grep( { $_ eq $_[0]; }
|
||||
my $test =
|
||||
grep( { $_ eq $_[0]; }
|
||||
map( { $_->{'k'}; } @{ $_[2]{'select'}; } ) );
|
||||
return $test
|
||||
? 1
|
||||
|
@ -1756,6 +1757,22 @@ qr/^(?:\*\.)?(?:(?:(?:(?:[a-zA-Z0-9][-a-zA-Z0-9]*)?[a-zA-Z0-9])[.])*(?:[a-zA-Z][
|
|||
'default' => 0,
|
||||
'type' => 'bool'
|
||||
},
|
||||
'notificationServerDELETE' => {
|
||||
'default' => 0,
|
||||
'type' => 'bool'
|
||||
},
|
||||
'notificationServerGET' => {
|
||||
'default' => 0,
|
||||
'type' => 'bool'
|
||||
},
|
||||
'notificationServerPOST' => {
|
||||
'default' => 1,
|
||||
'type' => 'bool'
|
||||
},
|
||||
'notificationServerSentAttributes' => {
|
||||
'default' => 'uid reference date title subtitle text check',
|
||||
'type' => 'text'
|
||||
},
|
||||
'notificationStorage' => {
|
||||
'default' => 'File',
|
||||
'type' => 'PerlModule'
|
||||
|
|
|
@ -1051,6 +1051,28 @@ sub attributes {
|
|||
type => 'bool',
|
||||
documentation => 'Notification server activation',
|
||||
},
|
||||
notificationServerGET => {
|
||||
default => 0,
|
||||
type => 'bool',
|
||||
documentation => 'Notification server activation',
|
||||
},
|
||||
notificationServerPOST => {
|
||||
default => 1,
|
||||
type => 'bool',
|
||||
documentation => 'Notification server activation',
|
||||
},
|
||||
notificationServerDELETE => {
|
||||
default => 0,
|
||||
type => 'bool',
|
||||
documentation => 'Notification server activation',
|
||||
},
|
||||
notificationServerSentAttributes => {
|
||||
type => 'text',
|
||||
default => 'uid reference date title subtitle text check',
|
||||
documentation =>
|
||||
'Prameters to send with notification server GET method',
|
||||
flags => 'p',
|
||||
},
|
||||
notificationStorage => {
|
||||
type => 'PerlModule',
|
||||
default => 'File',
|
||||
|
|
|
@ -599,12 +599,29 @@ sub tree {
|
|||
help => 'notifications.html',
|
||||
nodes => [
|
||||
'notification',
|
||||
'notificationServer',
|
||||
'oldNotifFormat',
|
||||
'notificationStorage',
|
||||
'notificationStorageOptions',
|
||||
'notificationWildcard',
|
||||
'notificationXSLTfile'
|
||||
'notificationXSLTfile',
|
||||
{
|
||||
title => 'serverNotification',
|
||||
help => 'notifications.html#server',
|
||||
nodes => [
|
||||
'notificationServer',
|
||||
'notificationServerSentAttributes',
|
||||
{
|
||||
title =>
|
||||
'notificationServerMethods',
|
||||
form => 'simpleInputContainer',
|
||||
nodes => [
|
||||
'notificationServerPOST',
|
||||
'notificationServerGET',
|
||||
'notificationServerDELETE',
|
||||
]
|
||||
},
|
||||
]
|
||||
},
|
||||
]
|
||||
},
|
||||
{
|
||||
|
@ -684,8 +701,6 @@ sub tree {
|
|||
'contextSwitchingRule',
|
||||
'contextSwitchingIdRule',
|
||||
'contextSwitchingStopWithLogout',
|
||||
|
||||
#'contextSwitchingHiddenAttributes',
|
||||
]
|
||||
},
|
||||
]
|
||||
|
@ -776,6 +791,7 @@ sub tree {
|
|||
'yubikey2fTTL',
|
||||
],
|
||||
},
|
||||
'sfExtra',
|
||||
{
|
||||
title => 'sfRemovedNotification',
|
||||
help => 'secondfactor.html',
|
||||
|
@ -787,7 +803,6 @@ sub tree {
|
|||
],
|
||||
},
|
||||
'sfRequired',
|
||||
'sfExtra',
|
||||
]
|
||||
},
|
||||
{
|
||||
|
@ -959,8 +974,7 @@ sub tree {
|
|||
help => 'samlservice.html#organization',
|
||||
form => 'simpleInputContainer',
|
||||
nodes => [
|
||||
'samlOrganizationDisplayName',
|
||||
'samlOrganizationName',
|
||||
'samlOrganizationDisplayName', 'samlOrganizationName',
|
||||
'samlOrganizationURL'
|
||||
]
|
||||
},
|
||||
|
|
|
@ -482,6 +482,12 @@
|
|||
"notification":"تفعيل",
|
||||
"notifications":"إشعار",
|
||||
"notificationServer":"إشعارالخادم",
|
||||
"notificationServerDELETE":"DELETE method",
|
||||
"notificationServerGET":"GET method",
|
||||
"notificationServerMethods":"HTTP methods",
|
||||
"notificationServerPOST":"POST method",
|
||||
"notificationServerSentAttributes":"Notification parameters to send",
|
||||
"serverNotification":"Server",
|
||||
"notificationCreated":"تم إنشاء إشعار",
|
||||
"notificationDeleted":"تم حذف الإشعار",
|
||||
"notificationDone":"انتهى الإشعار",
|
||||
|
|
|
@ -481,6 +481,12 @@
|
|||
"notification":"Activation",
|
||||
"notifications":"Notifications",
|
||||
"notificationServer":"Notification server",
|
||||
"notificationServerDELETE":"DELETE method",
|
||||
"notificationServerGET":"GET method",
|
||||
"notificationServerMethods":"HTTP methods",
|
||||
"notificationServerPOST":"POST method",
|
||||
"notificationServerSentAttributes":"Notification parameters to send",
|
||||
"serverNotification":"Server",
|
||||
"notificationCreated":"Notification has been created",
|
||||
"notificationDeleted":"Notification deleted",
|
||||
"notificationDone":"notification done",
|
||||
|
|
|
@ -481,6 +481,12 @@
|
|||
"notification":"Activation",
|
||||
"notifications":"Notifications",
|
||||
"notificationServer":"Notification server",
|
||||
"notificationServerDELETE":"DELETE method",
|
||||
"notificationServerGET":"GET method",
|
||||
"notificationServerMethods":"HTTP methods",
|
||||
"notificationServerPOST":"POST method",
|
||||
"notificationServerSentAttributes":"Notification parameters to send",
|
||||
"serverNotification":"Server",
|
||||
"notificationCreated":"Notification has been created",
|
||||
"notificationDeleted":"Notification deleted",
|
||||
"notificationDone":"notification done",
|
||||
|
|
|
@ -481,6 +481,12 @@
|
|||
"notification":"Activation",
|
||||
"notifications":"Notifications",
|
||||
"notificationServer":"Serveur de notifications",
|
||||
"notificationServerDELETE":"Méthode DELETE",
|
||||
"notificationServerGET":"Méthode GET",
|
||||
"notificationServerMethods":"Méthodes HTTP",
|
||||
"notificationServerPOST":"Méthode POST",
|
||||
"notificationServerSentAttributes":"Paramètres de notification à transmettre",
|
||||
"serverNotification":"Serveur",
|
||||
"notificationCreated":"La notification a été créée",
|
||||
"notificationDeleted":"La notification a été marquée comme lue",
|
||||
"notificationDone":"notification validée",
|
||||
|
|
|
@ -481,6 +481,12 @@
|
|||
"notification":"Attivazione",
|
||||
"notifications":"Notifiche",
|
||||
"notificationServer":"Server di notifica",
|
||||
"notificationServerDELETE":"DELETE method",
|
||||
"notificationServerGET":"GET method",
|
||||
"notificationServerMethods":"HTTP methods",
|
||||
"notificationServerPOST":"POST method",
|
||||
"notificationServerSentAttributes":"Notification parameters to send",
|
||||
"serverNotification":"Server",
|
||||
"notificationCreated":"La notifica è stata creata",
|
||||
"notificationDeleted":"La notifica è stata cancellata",
|
||||
"notificationDone":"La notifica è stata effettuata",
|
||||
|
|
|
@ -481,6 +481,12 @@
|
|||
"notification":"Kích hoạt",
|
||||
"notifications":"Thông báo",
|
||||
"notificationServer":"Máy chủ Thông báo",
|
||||
"notificationServerDELETE":"DELETE method",
|
||||
"notificationServerGET":"GET method",
|
||||
"notificationServerMethods":"HTTP methods",
|
||||
"notificationServerPOST":"POST method",
|
||||
"notificationServerSentAttributes":"Notification parameters to send",
|
||||
"serverNotification":"Server",
|
||||
"notificationCreated":"Thông báo đã được tạo ra",
|
||||
"notificationDeleted":"Thông báo đã xoá",
|
||||
"notificationDone":"thông báo được thực hiện",
|
||||
|
|
|
@ -481,6 +481,12 @@
|
|||
"notification":"激活",
|
||||
"notifications":"Notifications",
|
||||
"notificationServer":"Notification server",
|
||||
"notificationServerDELETE":"DELETE method",
|
||||
"notificationServerGET":"GET method",
|
||||
"notificationServerMethods":"HTTP methods",
|
||||
"notificationServerPOST":"POST method",
|
||||
"notificationServerSentAttributes":"Notification parameters to send",
|
||||
"serverNotification":"Server",
|
||||
"notificationCreated":"Notification has been created",
|
||||
"notificationDeleted":"Notification deleted",
|
||||
"notificationDone":"notification done",
|
||||
|
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
@ -1493,14 +1493,21 @@ sub metadata {
|
|||
|
||||
# List response types depending on allowed flows
|
||||
my $response_types = [];
|
||||
push( @$response_types, "code" )
|
||||
if $self->conf->{oidcServiceAllowAuthorizationCodeFlow};
|
||||
push( @$response_types, "id_token", "id_token token" )
|
||||
if $self->conf->{oidcServiceAllowImplicitFlow};
|
||||
my $grant_types = [];
|
||||
if ( $self->conf->{oidcServiceAllowAuthorizationCodeFlow} ) {
|
||||
push( @$response_types, "code" );
|
||||
push( @$grant_types, "authorization_code" );
|
||||
}
|
||||
if ( $self->conf->{oidcServiceAllowImplicitFlow} ) {
|
||||
push( @$response_types, "id_token", "id_token token" );
|
||||
push( @$grant_types, "implicit" );
|
||||
}
|
||||
if ( $self->conf->{oidcServiceAllowHybridFlow} ) {
|
||||
push( @$response_types,
|
||||
"code id_token",
|
||||
"code token", "code id_token token" )
|
||||
if $self->conf->{oidcServiceAllowHybridFlow};
|
||||
"code token", "code id_token token" );
|
||||
push( @$grant_types, "hybrid" );
|
||||
}
|
||||
|
||||
# Create OpenID configuration hash;
|
||||
return $self->p->sendJSONresponse(
|
||||
|
@ -1530,7 +1537,7 @@ sub metadata {
|
|||
# Scopes
|
||||
scopes_supported => [qw/openid profile email address phone/],
|
||||
response_types_supported => $response_types,
|
||||
grant_types_supported => [qw/authorization_code implicit hybrid/],
|
||||
grant_types_supported => $grant_types,
|
||||
acr_values_supported => \@acr,
|
||||
subject_types_supported => ["public"],
|
||||
token_endpoint_auth_methods_supported =>
|
||||
|
|
|
@ -64,6 +64,9 @@ sub checkForNotifications {
|
|||
next unless $j;
|
||||
$i++;
|
||||
}
|
||||
@res =
|
||||
sort { $a->{date} cmp $b->{date} or $a->{reference} cmp $b->{reference} }
|
||||
@res;
|
||||
$form .= $self->toForm( $req, @res );
|
||||
|
||||
# Stop here if nothing to display
|
||||
|
@ -248,27 +251,22 @@ sub notificationServer {
|
|||
eval { $self->notifObject->getNotifications($uid) };
|
||||
return $self->p->sendError( $req, $@, 500 ) if ($@);
|
||||
$res = [];
|
||||
foreach ( keys %$notifs ) {
|
||||
$self->p->logger->debug("Found notification $_");
|
||||
foreach my $notif ( keys %$notifs ) {
|
||||
$self->p->logger->debug("Found notification $notif");
|
||||
my $json;
|
||||
eval { $json = from_json( $notifs->{$_}, { allow_nonref => 1 } ) };
|
||||
eval {
|
||||
$json = from_json( $notifs->{$notif}, { allow_nonref => 1 } );
|
||||
};
|
||||
return $self->p->sendError( $req, "Unable to decode JSON file: $@",
|
||||
400 )
|
||||
if ($@);
|
||||
$self->p->logger->debug(
|
||||
"Notification $_: " . Dumper($json) );
|
||||
$self->p->logger->debug( "Notification $notif: " . Dumper($json) );
|
||||
if ($ref) {
|
||||
push(
|
||||
@$res,
|
||||
{
|
||||
"uid" => $json->{uid},
|
||||
"reference" => $json->{reference},
|
||||
"date" => $json->{date},
|
||||
"title" => $json->{title},
|
||||
"text" => $json->{text}
|
||||
|
||||
}
|
||||
) if ( $json->{reference} =~ /^$ref$/ );
|
||||
push( @$res,
|
||||
map { "$_" => $json->{$_} },
|
||||
split /\s+/,
|
||||
$self->conf->{notificationServerSentAttributes} )
|
||||
if ( $json->{reference} =~ /^$ref$/ );
|
||||
}
|
||||
else {
|
||||
push @$res,
|
||||
|
|
|
@ -7,6 +7,7 @@ use Lemonldap::NG::Common::Session;
|
|||
use Lemonldap::NG::Common::UserAgent;
|
||||
use Lemonldap::NG::Common::FormEncode;
|
||||
use XML::Simple;
|
||||
use HTML::Entities qw(decode_entities);
|
||||
use MIME::Base64;
|
||||
use HTTP::Request; # SOAP call
|
||||
use POSIX qw(strftime); # Convert SAML2 date into timestamp
|
||||
|
@ -264,6 +265,10 @@ sub loadIDPs {
|
|||
# Store IDP entityID and Organization Name
|
||||
my ( $tmp, $entityID ) =
|
||||
( $idp_metadata =~ /entityID=(['"])(.+?)\1/si );
|
||||
|
||||
# Decode HTML entities from entityID
|
||||
decode_entities($entityID);
|
||||
|
||||
my $name = $self->getOrganizationName( $self->lassoServer, $entityID )
|
||||
|| ucfirst($_);
|
||||
$self->idpList->{$entityID}->{confKey} = $_;
|
||||
|
@ -360,6 +365,10 @@ sub loadSPs {
|
|||
|
||||
# Store SP entityID and Organization Name
|
||||
my ( $tmp, $entityID ) = ( $sp_metadata =~ /entityID=(['"])(.+?)\1/si );
|
||||
|
||||
# Decode HTML entities from entityID
|
||||
decode_entities($entityID);
|
||||
|
||||
my $name = $self->getOrganizationName( $self->lassoServer, $entityID )
|
||||
|| ucfirst($_);
|
||||
$self->spList->{$entityID}->{confKey} = $_;
|
||||
|
|
|
@ -50,16 +50,16 @@ sub init {
|
|||
$self->addUnauthRoute(
|
||||
notifications => 'notificationServer',
|
||||
['POST']
|
||||
);
|
||||
) if ( $self->conf->{notificationServerPOST} // 1 );
|
||||
$self->addUnauthRoute(
|
||||
notifications => { '*' => 'notificationServer' },
|
||||
['GET']
|
||||
);
|
||||
) if ( $self->conf->{notificationServerGET} );
|
||||
$self->addUnauthRoute(
|
||||
notifications =>
|
||||
{ ':uid' => { ':reference' => 'notificationServer' } },
|
||||
['DELETE']
|
||||
);
|
||||
) if ( $self->conf->{notificationServerDELETE} );
|
||||
}
|
||||
|
||||
# Search for configuration options
|
||||
|
@ -80,7 +80,6 @@ sub init {
|
|||
$type->import( $self->conf->{oldNotifFormat} ? 'XML' : 'JSON' );
|
||||
|
||||
# TODO: use conf database?
|
||||
|
||||
my $prms = {
|
||||
%{ $self->conf->{notificationStorageOptions} },
|
||||
p => $self->p,
|
||||
|
|
|
@ -1,11 +1,10 @@
|
|||
# Launch SSL request
|
||||
|
||||
tryssl = () ->
|
||||
host = window.datas.sslHost
|
||||
path = window.location.pathname
|
||||
url = "#{host}#{path}"
|
||||
console.log 'Call URL -> ', url
|
||||
$.ajax url,
|
||||
console.log 'path -> ', path
|
||||
console.log 'Call URL -> ', window.datas.sslHost
|
||||
$.ajax window.datas.sslHost,
|
||||
dataType: 'jsonp'
|
||||
# PE_BADCREDENTIALS
|
||||
statusCode:
|
||||
|
@ -15,14 +14,24 @@ tryssl = () ->
|
|||
# If request succeed, cookie is set, posting form to get redirection
|
||||
# or menu
|
||||
success: (data) ->
|
||||
$('#lform').submit()
|
||||
sendUrl path
|
||||
console.log 'Success -> ', data
|
||||
# Case else, will display PE_BADCREDENTIALS or fallback to next auth
|
||||
# backend
|
||||
error: () ->
|
||||
$('#lform').submit()
|
||||
sendUrl path
|
||||
console.log 'Error'
|
||||
false
|
||||
|
||||
sendUrl = (path) ->
|
||||
form_url = $('#lform').attr('action')
|
||||
if form_url.match /^#$/
|
||||
form_url = path
|
||||
else
|
||||
form_url = form_url + path
|
||||
console.log 'form action URL -> ', form_url
|
||||
$('#lform').attr('action', form_url)
|
||||
$('#lform').submit()
|
||||
|
||||
$(document).ready ->
|
||||
$('.sslclick').on 'click', tryssl
|
|
@ -1,11 +1,10 @@
|
|||
# Launch SSL request
|
||||
|
||||
tryssl = () ->
|
||||
host = window.datas.sslHost
|
||||
path = window.location.pathname
|
||||
url = "#{host}#{path}"
|
||||
console.log 'Call URL -> ', url
|
||||
$.ajax url,
|
||||
console.log 'path -> ', path
|
||||
console.log 'Call URL -> ', window.datas.sslHost
|
||||
$.ajax window.datas.sslHost,
|
||||
dataType: 'jsonp'
|
||||
# PE_BADCREDENTIALS
|
||||
statusCode:
|
||||
|
@ -15,14 +14,24 @@ tryssl = () ->
|
|||
# If request succeed, cookie is set, posting form to get redirection
|
||||
# or menu
|
||||
success: (data) ->
|
||||
$('#lformSSL').submit()
|
||||
sendUrl path
|
||||
console.log 'Success -> ', data
|
||||
# Case else, will display PE_BADCREDENTIALS or fallback to next auth
|
||||
# backend
|
||||
error: () ->
|
||||
$('#lformSSL').submit()
|
||||
sendUrl path
|
||||
console.log 'Error'
|
||||
false
|
||||
|
||||
sendUrl = (path) ->
|
||||
form_url = $('#lformSSL').attr('action')
|
||||
if form_url.match /^#$/
|
||||
form_url = path
|
||||
else
|
||||
form_url = form_url + path
|
||||
console.log 'form action URL -> ', form_url
|
||||
$('#lformSSL').attr('action', form_url)
|
||||
$('#lformSSL').submit()
|
||||
|
||||
$(document).ready ->
|
||||
$('.sslclick').on 'click', tryssl
|
|
@ -1,14 +1,13 @@
|
|||
// Generated by CoffeeScript 1.12.7
|
||||
(function() {
|
||||
var tryssl;
|
||||
var sendUrl, tryssl;
|
||||
|
||||
tryssl = function() {
|
||||
var host, path, url;
|
||||
host = window.datas.sslHost;
|
||||
var path;
|
||||
path = window.location.pathname;
|
||||
url = "" + host + path;
|
||||
console.log('Call URL -> ', url);
|
||||
$.ajax(url, {
|
||||
console.log('path -> ', path);
|
||||
console.log('Call URL -> ', window.datas.sslHost);
|
||||
$.ajax(window.datas.sslHost, {
|
||||
dataType: 'jsonp',
|
||||
statusCode: {
|
||||
401: function() {
|
||||
|
@ -17,17 +16,30 @@
|
|||
}
|
||||
},
|
||||
success: function(data) {
|
||||
$('#lform').submit();
|
||||
sendUrl(path);
|
||||
return console.log('Success -> ', data);
|
||||
},
|
||||
error: function() {
|
||||
$('#lform').submit();
|
||||
sendUrl(path);
|
||||
return console.log('Error');
|
||||
}
|
||||
});
|
||||
return false;
|
||||
};
|
||||
|
||||
sendUrl = function(path) {
|
||||
var form_url;
|
||||
form_url = $('#lform').attr('action');
|
||||
if (form_url.match(/^#$/)) {
|
||||
form_url = path;
|
||||
} else {
|
||||
form_url = form_url + path;
|
||||
}
|
||||
console.log('form action URL -> ', form_url);
|
||||
$('#lform').attr('action', form_url);
|
||||
return $('#lform').submit();
|
||||
};
|
||||
|
||||
$(document).ready(function() {
|
||||
return $('.sslclick').on('click', tryssl);
|
||||
});
|
||||
|
|
|
@ -1 +1 @@
|
|||
(function(){var tryssl;tryssl=function(){var host,path,url;host=window.datas.sslHost;path=window.location.pathname;url=""+host+path;console.log("Call URL -> ",url);$.ajax(url,{dataType:"jsonp",statusCode:{401:function(){$("#lform").submit();return console.log("Error code 401")}},success:function(data){$("#lform").submit();return console.log("Success -> ",data)},error:function(){$("#lform").submit();return console.log("Error")}});return false};$(document).ready(function(){return $(".sslclick").on("click",tryssl)})}).call(this);
|
||||
(function(){var sendUrl,tryssl;tryssl=function(){var path;path=window.location.pathname;console.log("path -> ",path);console.log("Call URL -> ",window.datas.sslHost);$.ajax(window.datas.sslHost,{dataType:"jsonp",statusCode:{401:function(){$("#lform").submit();return console.log("Error code 401")}},success:function(data){sendUrl(path);return console.log("Success -> ",data)},error:function(){sendUrl(path);return console.log("Error")}});return false};sendUrl=function(path){var form_url;form_url=$("#lform").attr("action");if(form_url.match(/^#$/)){form_url=path}else{form_url=form_url+path}console.log("form action URL -> ",form_url);$("#lform").attr("action",form_url);return $("#lform").submit()};$(document).ready(function(){return $(".sslclick").on("click",tryssl)})}).call(this);
|
||||
|
|
|
@ -1,14 +1,13 @@
|
|||
// Generated by CoffeeScript 1.12.8
|
||||
// Generated by CoffeeScript 1.12.7
|
||||
(function() {
|
||||
var tryssl;
|
||||
var sendUrl, tryssl;
|
||||
|
||||
tryssl = function() {
|
||||
var host, path, url;
|
||||
host = window.datas.sslHost;
|
||||
var path;
|
||||
path = window.location.pathname;
|
||||
url = "" + host + path;
|
||||
console.log('Call URL -> ', url);
|
||||
$.ajax(url, {
|
||||
console.log('path -> ', path);
|
||||
console.log('Call URL -> ', window.datas.sslHost);
|
||||
$.ajax(window.datas.sslHost, {
|
||||
dataType: 'jsonp',
|
||||
statusCode: {
|
||||
401: function() {
|
||||
|
@ -17,17 +16,30 @@
|
|||
}
|
||||
},
|
||||
success: function(data) {
|
||||
$('#lformSSL').submit();
|
||||
sendUrl(path);
|
||||
return console.log('Success -> ', data);
|
||||
},
|
||||
error: function() {
|
||||
$('#lformSSL').submit();
|
||||
sendUrl(path);
|
||||
return console.log('Error');
|
||||
}
|
||||
});
|
||||
return false;
|
||||
};
|
||||
|
||||
sendUrl = function(path) {
|
||||
var form_url;
|
||||
form_url = $('#lformSSL').attr('action');
|
||||
if (form_url.match(/^#$/)) {
|
||||
form_url = path;
|
||||
} else {
|
||||
form_url = form_url + path;
|
||||
}
|
||||
console.log('form action URL -> ', form_url);
|
||||
$('#lformSSL').attr('action', form_url);
|
||||
return $('#lformSSL').submit();
|
||||
};
|
||||
|
||||
$(document).ready(function() {
|
||||
return $('.sslclick').on('click', tryssl);
|
||||
});
|
||||
|
|
|
@ -1 +1 @@
|
|||
(function(){var tryssl;tryssl=function(){var host,path,url;host=window.datas.sslHost;path=window.location.pathname;url=""+host+path;console.log("Call URL -> ",url);$.ajax(url,{dataType:"jsonp",statusCode:{401:function(){$("#lformSSL").submit();return console.log("Error code 401")}},success:function(data){$("#lformSSL").submit();return console.log("Success -> ",data)},error:function(){$("#lformSSL").submit();return console.log("Error")}});return false};$(document).ready(function(){return $(".sslclick").on("click",tryssl)})}).call(this);
|
||||
(function(){var sendUrl,tryssl;tryssl=function(){var path;path=window.location.pathname;console.log("path -> ",path);console.log("Call URL -> ",window.datas.sslHost);$.ajax(window.datas.sslHost,{dataType:"jsonp",statusCode:{401:function(){$("#lformSSL").submit();return console.log("Error code 401")}},success:function(data){sendUrl(path);return console.log("Success -> ",data)},error:function(){sendUrl(path);return console.log("Error")}});return false};sendUrl=function(path){var form_url;form_url=$("#lformSSL").attr("action");if(form_url.match(/^#$/)){form_url=path}else{form_url=form_url+path}console.log("form action URL -> ",form_url);$("#lformSSL").attr("action",form_url);return $("#lformSSL").submit()};$(document).ready(function(){return $(".sslclick").on("click",tryssl)})}).call(this);
|
||||
|
|
|
@ -6,6 +6,7 @@
|
|||
<form action="/2fchoice" method="POST">
|
||||
<input type="hidden" id="token" name="token" value="<TMPL_VAR NAME="TOKEN">" />
|
||||
<input type="hidden" id="checkLogins" name="checkLogins" value="<TMPL_VAR NAME="CHECKLOGINS">">
|
||||
<input type="hidden" name="skin" value="<TMPL_VAR NAME="SKIN">" />
|
||||
<TMPL_LOOP NAME="MODULES">
|
||||
<button type="submit" name="sf" value="<TMPL_VAR NAME="CODE">" class="mx-3">
|
||||
<img src="<TMPL_VAR NAME="STATIC_PREFIX"><TMPL_VAR NAME="SKIN">/<TMPL_VAR NAME="LOGO">" alt="<TMPL_VAR NAME="CODE">2F" title="<TMPL_VAR NAME="CODE">2F" />
|
||||
|
|
|
@ -3,7 +3,9 @@ use strict;
|
|||
use IO::String;
|
||||
|
||||
my $res;
|
||||
my $maintests = 6;
|
||||
my $file = 't/notifications.db';
|
||||
my $maintests = 8;
|
||||
eval { unlink $file };
|
||||
require 't/test-lib.pm';
|
||||
my $file = tempdb();
|
||||
|
||||
|
@ -38,7 +40,7 @@ q{INSERT INTO notifications VALUES ('dwho','testref2','2016-05-30 00:00:00',?,nu
|
|||
'[
|
||||
{
|
||||
"uid": "dwho",
|
||||
"date": "2016-05-30",
|
||||
"date": "2016-05-29",
|
||||
"reference": "testref2",
|
||||
"title": "Test2 title",
|
||||
"subtitle": "Test2 subtitle",
|
||||
|
@ -77,7 +79,14 @@ q{INSERT INTO notifications VALUES ('dwho','testref2','2016-05-30 00:00:00',?,nu
|
|||
);
|
||||
expectOK($res);
|
||||
my $id = expectCookie($res);
|
||||
ok( $res->[2]->[0] =~ /1x1x1/, ' Found ref' );
|
||||
my @refs = ( $res->[2]->[0] =~
|
||||
/<input type="hidden" name="reference[\dx]+" value="(\w+?)">/gs );
|
||||
ok( @refs == 2, 'Two notification references found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( @refs[0] eq 'testref2', '1st reference found is "testref2"' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( @refs[1] eq 'testref', '2nd reference found is "testref"' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
expectForm( $res, undef, '/notifback', 'reference1x1', 'url' );
|
||||
|
||||
# Verify that cookie is ciphered (session unvalid)
|
||||
|
|
|
@ -22,13 +22,15 @@ my $jsonbis = '{
|
|||
"text": "This is a second test text"
|
||||
}';
|
||||
|
||||
my $json2 = '{
|
||||
my $json2 = q%{
|
||||
"date": "2016-05-30",
|
||||
"reference": "testref2",
|
||||
"uid": "dwho",
|
||||
"title": "Test2 title",
|
||||
"text": "This is a second test text"
|
||||
}';
|
||||
"text": "This is a second test text",
|
||||
"subtitle": "Application 2",
|
||||
"check": ["I agree","Yes, I'm sure"]
|
||||
}%;
|
||||
|
||||
my $jsonall = '{
|
||||
"date": "2016-05-30",
|
||||
|
@ -45,7 +47,10 @@ my $client = LLNG::Manager::Test->new( {
|
|||
logLevel => 'error',
|
||||
useSafeJail => 1,
|
||||
notification => 1,
|
||||
notificationServer => 1,
|
||||
notificationServer => 1, # POST method enabled if undefined
|
||||
notificationServerGET => 1,
|
||||
notificationServerDELETE => 1,
|
||||
notificationServerSentAttributes => 'uid reference date title text subtitle check',
|
||||
notificationWildcard => 'everyone',
|
||||
notificationStorage => 'File',
|
||||
notificationStorageOptions => {
|
||||
|
@ -70,6 +75,20 @@ foreach ( $json, $json2, $jsonall ) {
|
|||
count(2);
|
||||
}
|
||||
|
||||
ok(
|
||||
$res = $client->_get(
|
||||
'/notifications', type => 'application/json',
|
||||
),
|
||||
'List notifications for "allusers"'
|
||||
);
|
||||
ok( $res->[2]->[0] =~ /"result"\s*:\s*/, 'Result found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( $res->[2]->[0] =~ /"reference":"testrefall"/, 'Notification for all users found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( $res->[2]->[0] =~ /"uid":"everyone"/, 'Wildcard found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
count(4);
|
||||
|
||||
ok(
|
||||
$res = $client->_get(
|
||||
'/notifications/dwho', type => 'application/json',
|
||||
|
@ -82,8 +101,10 @@ ok( $res->[2]->[0] =~ /"reference":"testref"/, 'First notification found' )
|
|||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( $res->[2]->[0] =~ /"reference":"testref2"/, 'Second notification found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( $res->[2]->[0] =~ /"reference":"testrefall"/, 'Third notification found (all users)' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok(
|
||||
$res->[2]->[0] =~ /"reference":"testrefall"/,
|
||||
'Third notification found (all users)'
|
||||
) or print STDERR Dumper( $res->[2]->[0] );
|
||||
count(5);
|
||||
|
||||
ok(
|
||||
|
@ -108,6 +129,32 @@ ok( $res->[2]->[0] =~ /"uid"\s*:\s*"dwho"/, 'Notification uid found' )
|
|||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
count(7);
|
||||
|
||||
ok(
|
||||
$res = $client->_get(
|
||||
'/notifications/dwho/testref2', type => 'application/json',
|
||||
),
|
||||
'List notification with reference "testref2"'
|
||||
);
|
||||
ok( $res->[2]->[0] =~ /"result"\s*:\s*/, 'Result found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( $res->[2]->[0] =~ /"reference"\s*:\s*"testref2"/,
|
||||
'Notification reference found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( $res->[2]->[0] =~ /"title"\s*:\s*"Test2 title"/, 'Notification title found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( $res->[2]->[0] =~ /"text"\s*:\s*"This is a second test text"/,
|
||||
'Notification text found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( $res->[2]->[0] =~ /"date"\s*:\s*"2016-05-30"/, 'Notification date found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( $res->[2]->[0] =~ /"uid"\s*:\s*"dwho"/, 'Notification uid found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( $res->[2]->[0] =~ /"subtitle"\s*:\s*"Application 2"/, 'Notification subtitle found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
ok( $res->[2]->[0] =~ /"check":\["I agree","Yes, I\'m sure"\]/, 'Notification check boxes found' )
|
||||
or print STDERR Dumper( $res->[2]->[0] );
|
||||
count(9);
|
||||
|
||||
ok(
|
||||
$res = $client->_put(
|
||||
'/notifications', IO::String->new($content),
|
||||
|
|
|
@ -214,8 +214,10 @@ Requires: perl(Lemonldap::NG::Common) = %{version}-%{release}
|
|||
Requires: perl(mod_perl2)
|
||||
%if 0%{?rhel}%{?fedora}
|
||||
Requires(post): httpd
|
||||
Requires: mod_fcgid
|
||||
%else
|
||||
Requires(post): apache2
|
||||
Requires: apache2-mod_fcgid
|
||||
%endif
|
||||
|
||||
%description conf
|
||||
|
@ -323,6 +325,7 @@ Nginx support for LemonLDAP::NG.
|
|||
%package -n perl-Lemonldap-NG-Common
|
||||
Summary: LemonLDAP-NG Common Modules
|
||||
Requires: perl(JSON::XS)
|
||||
Requires: perl(String::Random)
|
||||
|
||||
%description -n perl-Lemonldap-NG-Common
|
||||
This package installs the configuration libraries used by other LemonLDAP::NG
|
||||
|
|
Loading…
Reference in New Issue
Block a user