41 assert(is_array(
$info));
47 if (!isset(
$config[
'entityID'])) {
56 'authsources[' . var_export($this->authId,
true) .
']');
57 $this->entityId = $this->metadata->getString(
'entityID');
58 $this->idp = $this->metadata->getString(
'idp',
null);
59 $this->discoURL = $this->metadata->getString(
'discoURL',
null);
61 if (empty($this->discoURL) &&
SimpleSAML\Module::isModuleEnabled(
'discojuice')) {
106 if ($this->idp !==
null && $this->idp !==
$entityId) {
109 ' because it isn\'t a valid IdP for this SP.');
116 return $metadataHandler->getMetaDataConfig(
$entityId,
'saml20-idp-remote');
117 }
catch (Exception $e) {
124 return $metadataHandler->getMetaDataConfig(
$entityId,
'shib13-idp-remote');
125 }
catch (Exception $e) {
147 $ar = new \SimpleSAML\XML\Shib13\AuthnRequest();
148 $ar->setIssuer($this->entityId);
151 $ar->setRelayState(
$id);
153 $useArtifact =
$idpMetadata->getBoolean(
'saml1.useartifact',
null);
154 if ($useArtifact ===
null) {
155 $useArtifact = $this->metadata->getBoolean(
'saml1.useartifact',
false);
167 ' from ' . var_export($this->entityId,
true) .
'.');
179 if (isset(
$state[
'saml:ProxyCount']) &&
$state[
'saml:ProxyCount'] < 0) {
182 new \
SimpleSAML\Module\saml\Error\ProxyCountExceeded(\
SAML2\Constants::STATUS_RESPONDER)
192 $ar->setAssertionConsumerServiceURL(ILIAS_HTTP_PATH .
'/Services/Saml/lib/saml2-acs.php/default-sp/' . CLIENT_ID);
195 if (isset(
$state[
'SimpleSAML_Auth_Source.ReturnURL'])) {
196 $ar->setRelayState(
$state[
'SimpleSAML_Auth_Source.ReturnURL']);
199 if (isset(
$state[
'saml:AuthnContextClassRef'])) {
202 if (isset(
$state[
'saml:AuthnContextComparison']) && in_array(
$state[
'AuthnContextComparison'], array(
203 SAML2\Constants::COMPARISON_EXACT,
204 SAML2\Constants::COMPARISON_MINIMUM,
205 SAML2\Constants::COMPARISON_MAXIMUM,
206 SAML2\Constants::COMPARISON_BETTER,
208 $comp =
$state[
'saml:AuthnContextComparison'];
210 $ar->setRequestedAuthnContext(array(
'AuthnContextClassRef' => $accr,
'Comparison' => $comp));
213 if (isset(
$state[
'ForceAuthn'])) {
214 $ar->setForceAuthn((
bool)
$state[
'ForceAuthn']);
217 if (isset(
$state[
'isPassive'])) {
218 $ar->setIsPassive((
bool)
$state[
'isPassive']);
221 if (isset(
$state[
'saml:NameID'])) {
222 if (!is_array(
$state[
'saml:NameID']) && !is_a(
$state[
'saml:NameID'],
'\SAML2\XML\saml\NameID')) {
225 $ar->setNameId(
$state[
'saml:NameID']);
228 if (isset(
$state[
'saml:NameIDPolicy'])) {
229 if (is_string(
$state[
'saml:NameIDPolicy'])) {
231 'Format' => (
string)
$state[
'saml:NameIDPolicy'],
232 'AllowCreate' =>
true,
234 } elseif (is_array(
$state[
'saml:NameIDPolicy'])) {
235 $policy =
$state[
'saml:NameIDPolicy'];
239 $ar->setNameIdPolicy($policy);
242 if (isset(
$state[
'saml:IDPList'])) {
243 $IDPList =
$state[
'saml:IDPList'];
248 $ar->setIDPList(array_unique(array_merge($this->metadata->getArray(
'IDPList', array()),
252 if (isset(
$state[
'saml:ProxyCount']) &&
$state[
'saml:ProxyCount'] !==
null) {
253 $ar->setProxyCount(
$state[
'saml:ProxyCount']);
254 } elseif (
$idpMetadata->getInteger(
'ProxyCount',
null) !==
null) {
255 $ar->setProxyCount(
$idpMetadata->getInteger(
'ProxyCount',
null));
256 } elseif ($this->metadata->getInteger(
'ProxyCount',
null) !==
null) {
257 $ar->setProxyCount($this->metadata->getInteger(
'ProxyCount',
null));
260 $requesterID = array();
261 if (isset(
$state[
'saml:RequesterID'])) {
262 $requesterID =
$state[
'saml:RequesterID'];
265 if (isset(
$state[
'core:SP'])) {
266 $requesterID[] =
$state[
'core:SP'];
269 $ar->setRequesterID($requesterID);
271 if (isset(
$state[
'saml:Extensions'])) {
272 $ar->setExtensions(
$state[
'saml:Extensions']);
285 if ($ar->getProtocolBinding() === \
SAML2\Constants::BINDING_HOK_SSO) {
287 \
SAML2\Constants::BINDING_HOK_SSO)
290 $dst =
$idpMetadata->getEndpointPrioritizedByBinding(
'SingleSignOnService', [
291 \
SAML2\Constants::BINDING_HTTP_REDIRECT,
292 \
SAML2\Constants::BINDING_HTTP_POST,
295 $ar->setDestination(
$dst[
'Location']);
327 assert(is_string(
$idp));
333 case 'shib13-idp-remote':
336 case 'saml20-idp-remote':
363 'entityID' => $this->entityId,
365 'returnIDParam' =>
'idpentityid'
368 if(isset(
$state[
'saml:IDPList'])) {
372 if (isset(
$state[
'isPassive']) &&
$state[
'isPassive']) {
395 if (isset(
$state[
'saml:idp'])) {
399 if (isset(
$state[
'saml:IDPList']) &&
sizeof(
$state[
'saml:IDPList']) > 0) {
402 $known_idps =
$mdh->getList();
403 $intersection = array_intersect(
$state[
'saml:IDPList'], array_keys($known_idps));
405 if (empty($intersection)) {
408 \
SAML2\Constants::STATUS_REQUESTER,
409 'None of the IdPs requested are supported by this proxy.'
413 if (!is_null(
$idp) && !in_array(
$idp, $intersection,
true)) {
416 \
SAML2\Constants::STATUS_REQUESTER,
417 'None of the IdPs requested are available to this proxy.'
421 if (is_null(
$idp) &&
sizeof($intersection) === 1) {
450 foreach (
$data as $k => $v) {
455 if (isset(
$state[
'saml:IDPList']) &&
sizeof(
$state[
'saml:IDPList']) > 0 &&
456 !in_array(
$state[
'saml:sp:IdP'],
$state[
'saml:IDPList'],
true))
467 $known_idps =
$mdh->getList();
468 $intersection = array_intersect(
$state[
'saml:IDPList'], array_keys($known_idps));
470 if (empty($intersection)) {
473 \
SAML2\Constants::STATUS_REQUESTER,
474 'None of the IdPs requested are supported by this proxy.'
483 if (!is_null($this->idp) && !in_array($this->idp, $intersection,
true)) {
486 \
SAML2\Constants::STATUS_REQUESTER,
487 'None of the IdPs requested are available to this proxy.'
497 "Reauthentication after logout is needed. The IdP '${state['saml:sp:IdP']}' is not in the IDPList ".
498 "provided by the Service Provider '${state['core:SP']}'."
529 assert(array_key_exists(
'saml:sp:IdPMetadata',
$state));
530 assert(array_key_exists(
'saml:sp:AuthId',
$state));
531 assert(array_key_exists(
'core:IdP',
$state));
532 assert(array_key_exists(
'SPMetadata',
$state));
534 if (isset(
$state[
'isPassive']) && (
bool)
$state[
'isPassive']) {
537 \
SAML2\Constants::STATUS_REQUESTER,
538 'Reauthentication required'
560 if (isset(
$state[
'Responder'])) {
561 $state[
'saml:proxy:reauthLogout:PrevResponder'] =
$state[
'Responder'];
563 $state[
'Responder'] = array(
'sspmod_saml_Auth_Source_SP',
'reauthPostLogout');
577 assert(isset(
$state[
'ReturnCallback']));
599 assert(isset(
$state[
'saml:sp:AuthId']));
603 if (isset(
$state[
'saml:proxy:reauthLogout:PrevResponder'])) {
604 $state[
'Responder'] =
$state[
'saml:proxy:reauthLogout:PrevResponder'];
610 $sp->authenticate(
$state);
622 assert(array_key_exists(
'saml:logout:IdP',
$state));
623 assert(array_key_exists(
'saml:logout:NameID',
$state));
624 assert(array_key_exists(
'saml:logout:SessionIndex',
$state));
635 \
SAML2\Constants::BINDING_HTTP_REDIRECT,
636 \
SAML2\Constants::BINDING_HTTP_POST),
false);
650 $encryptNameId = $this->metadata->getBoolean(
'nameid.encryption',
false);
670 assert(array_key_exists(
'saml:logout:Type',
$state));
672 $logoutType =
$state[
'saml:logout:Type'];
673 switch ($logoutType) {
695 assert(is_string(
$idp));
696 assert(array_key_exists(
'LogoutState',
$state));
697 assert(array_key_exists(
'saml:logout:Type',
$state[
'LogoutState']));
701 $spMetadataArray = $this->metadata->toArray();
706 $state[
'PersistentAuthData'][] =
'saml:sp:IdP';
708 $authProcState = array(
709 'saml:sp:IdP' =>
$idp,
710 'saml:sp:State' =>
$state,
711 'ReturnCall' => array(
'sspmod_saml_Auth_Source_SP',
'onProcessingCompleted'),
714 'Destination' => $spMetadataArray,
715 'Source' => $idpMetadataArray,
718 if (isset(
$state[
'saml:sp:NameID'])) {
719 $authProcState[
'saml:sp:NameID'] =
$state[
'saml:sp:NameID'];
721 if (isset(
$state[
'saml:sp:SessionIndex'])) {
722 $authProcState[
'saml:sp:SessionIndex'] =
$state[
'saml:sp:SessionIndex'];
726 $pc->processState($authProcState);
761 assert(is_string($redirectTo));
776 assert(array_key_exists(
'saml:sp:IdP', $authProcState));
777 assert(array_key_exists(
'saml:sp:State', $authProcState));
778 assert(array_key_exists(
'Attributes', $authProcState));
780 $idp = $authProcState[
'saml:sp:IdP'];
781 $state = $authProcState[
'saml:sp:State'];
786 throw new Exception(
'Could not find authentication source with id ' .
$sourceId);
792 $state[
'Attributes'] = $authProcState[
'Attributes'];
794 if (isset(
$state[
'saml:sp:isUnsolicited']) && (
bool)
$state[
'saml:sp:isUnsolicited']) {
795 if (!empty(
$state[
'saml:sp:RelayState'])) {
796 $redirectTo =
$state[
'saml:sp:RelayState'];
798 $redirectTo =
$source->getMetadata()->getString(
'RelayState',
'/');
if(!array_key_exists(sspmod_authfacebook_Auth_Source_Facebook::AUTHID, $state)) $sourceId
if(!array_key_exists('stateid', $_REQUEST)) $state
Handle linkback() response from LinkedIn.
if(!isset($_REQUEST['ReturnTo'])) $returnTo
An exception for terminatinating execution or to throw for unit testing.
static getBinding($urn)
Retrieve a binding with the given URN.
const COMPARISON_EXACT
Request Authentication Context Comparison indicating that the resulting authentication context in the...
static getModuleURL($resource, array $parameters=array())
Get absolute URL to a specified module resource.
static arrayize($data, $index=0)
Put a non-array variable into an array.
static redirectUntrustedURL($url, $parameters=array())
This function redirects to the specified URL after performing the appropriate security checks on it.
static redirectTrustedURL($url, $parameters=array())
This function redirects to the specified URL without performing any security checks.
static getById($authId, $type=null)
Retrieve authentication source.
static completeAuth(&$state)
Complete authentication.
callLogoutCallback($assoc)
Call a logout callback based on association.
static getPersistentAuthData(array $state)
Get the persistent authentication state from the state array.
static throwException($state, SimpleSAML_Error_Exception $exception)
Throw exception to the state exception handler.
static saveState(&$state, $stage, $rawId=false)
Save the state.
static loadFromArray($config, $location='[ARRAY]', $instance=null)
Loads a configuration from the given array.
static getByState(array &$state)
Retrieve the IdP "owning" the state.
static getSessionFromRequest()
Retrieves the current session.
handleResponse(array $state, $idp, array $attributes)
Handle a response from a SSO operation.
static askForIdPChange(array &$state)
Ask the user to log out before being able to log in again with a different identity provider.
handleLogout($idpEntityId)
Handle a logout request from an IdP.
logout(&$state)
Start logout operation.
static handleUnsolicitedAuth($authId, array $state, $redirectTo)
Handle an unsolicited login operations.
authenticate(&$state)
Start login.
getIdPMetadata($entityId)
Retrieve the metadata of an IdP.
static reauthLogout(array $state)
Log the user out before logging in again.
startSLO2(&$state)
Start a SAML 2 logout operation.
startSSO2(SimpleSAML_Configuration $idpMetadata, array $state)
Send a SAML2 SSO request to an IdP.
__construct($info, $config)
Constructor for SAML SP authentication source.
getEntityId()
Retrieve the entity id of this SP.
reauthenticate(array &$state)
Re-authenticate an user.
startSSO($idp, array $state)
Send a SSO request to an IdP.
sendSAML2AuthnRequest(array &$state, \SAML2\Binding $binding, \SAML2\AuthnRequest $ar)
Function to actually send the authentication request.
static reauthPostLogin(array $state)
Complete login operation after re-authenticating the user on another IdP.
startDisco(array $state)
Start an IdP discovery service operation.
getMetadataURL()
Retrieve the URL to the metadata of this SP.
getMetadata()
Retrieve the metadata of this SP.
static onProcessingCompleted(array $authProcState)
Called when we have completed the procssing chain.
startSSO1(SimpleSAML_Configuration $idpMetadata, array $state)
Send a SAML1 SSO request to an IdP.
static buildLogoutRequest(SimpleSAML_Configuration $srcMetadata, SimpleSAML_Configuration $dstMetadata)
Build a logout request based on information in the metadata.
static buildAuthnRequest(SimpleSAML_Configuration $spMetadata, SimpleSAML_Configuration $idpMetadata)
Build an authentication request based on information in the metadata.
static getEncryptionKey(SimpleSAML_Configuration $metadata)
Retrieve the encryption key for the given entity.
if(!array_key_exists('StateId', $_REQUEST)) $id
if(array_key_exists('yes', $_REQUEST)) $attributes
Attribute-related utility methods.