merged from Benjamin's branch
This commit is contained in:
commit
976ccd50a4
|
@ -1,49 +1,34 @@
|
|||
<?php
|
||||
require_once('lassospkit_helper.inc.php');
|
||||
require_once('lassospkit_debug.inc.php');
|
||||
require_once('lassospkit_utils.inc.php');
|
||||
require_once('lassospkit_metadata.inc.php');
|
||||
|
||||
class LassoSPKitEndpoint {
|
||||
var $dispatch_table = array();
|
||||
var $protocol = null;
|
||||
require_once('lassospkit_url_dispatch.inc.php');
|
||||
|
||||
class LassoSPKitEndpoint extends LassoSPKitUrlDispatch {
|
||||
function LassoSPKitEndpoint($protocol) {
|
||||
$this->__construct($protocol);
|
||||
}
|
||||
function __construct($protocol) {
|
||||
$this->protocol = $protocol;
|
||||
$this->addDispatch('/metadata', 'metadata');
|
||||
}
|
||||
function addDispatch($point, $method) {
|
||||
$dispatch_table[$point] = $method;
|
||||
}
|
||||
function dispatchAndExit() {
|
||||
if (! isset($_SERVER['PATH_INFO'])) {
|
||||
throw new Exception('No PATH INFO');
|
||||
}
|
||||
$path_info = $_SERVER['PATH_INFO'];
|
||||
$fname = $this->dispatch_table[$path_info];
|
||||
if ($fname) {
|
||||
$fname();
|
||||
exit(0);
|
||||
} else {
|
||||
header("HTTP/1.0 404 Not Found");
|
||||
exit(0);
|
||||
}
|
||||
$this->addDispatch('/assertionConsumer', 'assertionConsumer');
|
||||
$this->addDispatch('/sloBrws','sloBrws');
|
||||
$this->addDispatch('/sloSoap','sloSoap');
|
||||
$this->addDispatch('/sloReturn','sloReturn');
|
||||
}
|
||||
|
||||
// Urls
|
||||
function metadata() {
|
||||
$datadir = LassoSPKitHelper::getMetadataDir($this->protocol);
|
||||
$pkey = $datadir . "/" . PRIVATE_KEY;
|
||||
LassoSPKitUtils::extractPublicKey($pkey, $publickey, $error);
|
||||
$content = LassoSPKitMetadataSAML2::generateMetadata(dirname(LassoSPKitUtils::mydir()), LassoSPKitConfig::get('organization'), $publickey);
|
||||
if ($content) {
|
||||
header('Content-type: text/xml');
|
||||
echo $content;
|
||||
/** Return the session object. */
|
||||
function getSession() {
|
||||
static $session;
|
||||
if ($session == null) {
|
||||
$session_class = "LassoSPKit" . LassoSPKitConfig::get('session');
|
||||
$session = new $session_class();
|
||||
}
|
||||
return $session;
|
||||
}
|
||||
// Verify that the host is the same has HTTP_HOST
|
||||
function distpatchAndExit() {
|
||||
if (isset($_SERVER['HTTP_REFERER'])) {
|
||||
$host = $_SERVER['HTTP_REFERER'];
|
||||
$this->verifyUrl($host);
|
||||
}
|
||||
parent::dispatchAndExit();
|
||||
}
|
||||
/** Verify that the host is the same has HTTP_HOST */
|
||||
function verifyUrl($host) {
|
||||
$host = strstr('//', $host);
|
||||
$pos = strpos($host, '/');
|
||||
|
@ -56,5 +41,72 @@ class LassoSPKitEndpoint {
|
|||
exit(1);
|
||||
}
|
||||
}
|
||||
function getProfileObject() {
|
||||
throw new Exception('Not implemented');
|
||||
}
|
||||
function assertionConsumer() {
|
||||
$profile = $this->getProfileObject();
|
||||
$http_method = $this->limitMethodBrws($this->identifyHttpMethod());
|
||||
$query_string = $this->getQueryString($http_method);
|
||||
$ok = $profile->ssoConsumer($http_method, $query_string);
|
||||
$return_url = LassoSPKitUtilsSession::getRelayState('sso');
|
||||
finish($return_url);
|
||||
}
|
||||
/** Profiles initiés par l'IdP */
|
||||
function sloBrws() {
|
||||
$profile = $this->getProfileObject();
|
||||
$http_method = $this->limitMethodBrws($this->identifyHttpMethod());
|
||||
$query_string = $this->getQueryString($http_method);
|
||||
return $profile->processRequestSLO($http_method, $query_string);
|
||||
}
|
||||
function sloSoap() {
|
||||
$profile = $this->getProfileObject();
|
||||
return $profile->processSOAPRequestSLO();
|
||||
}
|
||||
/** Profiles initiés par le SP */
|
||||
function sloReturn() {
|
||||
$profile = $this->getProfileObject();
|
||||
$http_method = $this->limitMethodBrws($this->identifyHttpMethod());
|
||||
$query_string = $this->getQueryString($http_method);
|
||||
return $profile->processResponseSLO($http_method, $query_string);
|
||||
}
|
||||
function identifyHttpMethod() {
|
||||
if (isset($_POST) && ( isset($_POST['SAMLResponse']) || isset($_POST['SAMLRequest']))) {
|
||||
return LASSO_HTTP_METHOD_POST;
|
||||
}
|
||||
if (isset($_GET) && ( isset($_GET['SAMLResponse']) || isset($_GET['SAMLRequest']) ) {
|
||||
return LASSO_HTTP_METHOD_REDIRECT;
|
||||
}
|
||||
if (isset($_GET) && ( isset($_GET['SAMLart']))) {
|
||||
return LASSO_HTTP_METHOD_ARTIFACT_GET;
|
||||
}
|
||||
if (isset($_POST) && ( isset($_POST['SAMLart']))) {
|
||||
return LASSO_HTTP_METHOD_ARTIFACT_POST;
|
||||
}
|
||||
return LASSO_HTTP_METHOD_NONE;
|
||||
}
|
||||
function getQueryString($http_method) {
|
||||
switch ($http_method) {
|
||||
case LASSO_HTTP_METHOD_POST:
|
||||
case LASSO_HTTP_METHOD_ARTIFACT_POST:
|
||||
return @file_get_contents('php://input');
|
||||
case LASSO_HTTP_METHOD_REDIRECT:
|
||||
case LASSO_HTTP_METHOD_ARTIFACT_GET:
|
||||
return $_SERVER['QUERY_STRING'];
|
||||
}
|
||||
return null;
|
||||
}
|
||||
/** Restrict possible method for HTTP endpoints,
|
||||
so forbid using SOAP on HTTP endpoints. */
|
||||
function limitMethodBrws($http_method) {
|
||||
switch ($http_method) {
|
||||
case LASSO_HTTP_METHOD_POST:
|
||||
case LASSO_HTTP_METHOD_ARTIFACT_POST:
|
||||
case LASSO_HTTP_METHOD_REDIRECT:
|
||||
case LASSO_HTTP_METHOD_ARTIFACT_GET:
|
||||
return $http_method;
|
||||
}
|
||||
return LASSO_HTTP_METHOD_NONE;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -2,6 +2,15 @@
|
|||
require_once('lassospkit_utils_session.inc.php');
|
||||
require_once('lassospkit_utils.inc.php');
|
||||
require_once('lassospkit_config.inc.php');
|
||||
require_once("lassospkit_helper.inc.php");
|
||||
require_once("lassospkit_dispatcher.inc.php");
|
||||
require_once("lassospkit_saml2.inc.php");
|
||||
require_once("lassospkit_metadata.inc.php");
|
||||
require_once("lassospkit_utils.inc.php");
|
||||
require_once("lassospkit_utils_session.inc.php");
|
||||
require_once("lassospkit_dummysession.inc.php");
|
||||
require_once("lassospkit_autopersistentsession.inc.php");
|
||||
|
||||
|
||||
/** This file contains the public front-end API
|
||||
to the LassoSPKit for PHP.
|
||||
|
@ -136,3 +145,11 @@ function lassospkit_get_assertion_attributes() {
|
|||
return $attributes;
|
||||
}
|
||||
|
||||
function lassospkit_soap_logout() {
|
||||
$session_class = "LassoSPKit" . LassoSPKitConfig::get('session');
|
||||
$session = new $session_class();
|
||||
$saml2 = new LassoSPKitSAML2($session);
|
||||
$method = LASSO_HTTP_METHOD_SOAP;
|
||||
$ret = $saml2->initiateSLO($method);
|
||||
}
|
||||
|
||||
|
|
|
@ -27,13 +27,13 @@ class LassoSPKitSaml2 extends LassoSPKitSAMLCommon {
|
|||
to create a new federation if a persistent
|
||||
one is asked for federate = TRUE.
|
||||
*/
|
||||
function sso($create = TRUE, $federate = TRUE, $passive = FALSE) {
|
||||
function sso($create = TRUE, $federate = TRUE, $passive = FALSE, $relayState = null) {
|
||||
if ($federate) {
|
||||
$format = LASSO_SAML2_NAME_IDENTIFIER_FORMAT_PERSISTENT;
|
||||
} else {
|
||||
$format = LASSO_SAML2_NAME_IDENTIFIER_FORMAT_TRANSIENT;
|
||||
}
|
||||
return $this->ssoInit(array('allowCreate' => $create, 'nameIDFormat' => $format, 'isPassive' => $passive));
|
||||
return $this->ssoInit(array('allowCreate' => $create, 'nameIDFormat' => $format, 'isPassive' => $passive, 'relayState' => $relayState));
|
||||
}
|
||||
function ssoInit($params = array())
|
||||
{
|
||||
|
@ -44,12 +44,13 @@ class LassoSPKitSaml2 extends LassoSPKitSAMLCommon {
|
|||
'method' => LASSO_HTTP_METHOD_REDIRECT,
|
||||
'isConsentObtained' => FALSE,
|
||||
'forceAuthn' => FALSE,
|
||||
'relayState' => null,
|
||||
'isPassive' => FALSE);
|
||||
$params = array_merge($default_params, $params);
|
||||
extract($params);
|
||||
#lassospkit_debuglog("Params isPassive: $isPassive allowCreate: $allowCreate format: $nameIDFormat");
|
||||
$login = null;
|
||||
return parent::ssoCommon($login, $remoteID, $method, $isConsentObtained, $forceAuthn, $isPassive, array('nameIDFormat'=>$nameIDFormat, 'allowCreate' => $allowCreate));
|
||||
return parent::ssoCommon($login, $remoteID, $method, $isConsentObtained, $forceAuthn, $isPassive, $relayState, array('nameIDFormat'=>$nameIDFormat, 'allowCreate' => $allowCreate));
|
||||
}
|
||||
/** Defederation, convert to NameIdManagement protocol **/
|
||||
public function initiateFTNotification($method = LASSO_HTTP_METHOD_SOAP,$remoteID = null)
|
||||
|
|
|
@ -0,0 +1,39 @@
|
|||
<?php
|
||||
require_once('lassospkit_debug.inc.php');
|
||||
require_once('lassospkit_endpoints.inc.php');
|
||||
require_once('lassospkit_metadata.inc.php');
|
||||
|
||||
class LassoSPKitSaml2Endpoint extends LassoSPKitEndpoint {
|
||||
function LassoSPKitSaml2Endpoint() {
|
||||
parent::LassoSPKitEndpoint();
|
||||
$this->addDispatch('/nameIdManagementBrws','nameIdManagementBrws');
|
||||
$this->addDispatch('/nameIdManagementSoap','nameIdManagementSoap');
|
||||
$this->addDispatch('/nameIdManagementReturn','nameIdManagementReturn');
|
||||
$this->addDispatch('/metadata','metadata');
|
||||
}
|
||||
function getProfileObject() {
|
||||
return new LassoSPKitSAML2($this->getSession());
|
||||
}
|
||||
/** Generate metadatas for the SAML2 endpoint */
|
||||
function metadata() {
|
||||
$datadir = LassoSPKitHelper::getMetadataDir(LASSO_PROTOCOL_SAML_2_0);
|
||||
$pkey = $datadir . "/" . PRIVATE_KEY;
|
||||
LassoSPKitUtils::extractPublicKey($pkey, $publickey, $error);
|
||||
try {
|
||||
$content = LassoSPKitMetadataSAML2::generateMetadata(LassoSPKitConfig::get('baseUrl'), LassoSPKitConfig::get('organization'), $publickey);
|
||||
if ($content) {
|
||||
header('Content-type: text/xml');
|
||||
echo $content;
|
||||
}
|
||||
} catch (Exception $e) {
|
||||
echo 'An exception occured';
|
||||
lassospkit_errlog($e);
|
||||
}
|
||||
}
|
||||
function nameIdManagementBrws() {
|
||||
}
|
||||
function nameIdManagementSoap() {
|
||||
}
|
||||
function nameIdManagementReturn() {
|
||||
}
|
||||
}
|
|
@ -4,19 +4,21 @@ require_once('lassospkit_debug.inc.php');
|
|||
require_once('lassospkit_lib.inc.php');
|
||||
require_once('lassospkit_generic_session.inc.php');
|
||||
require_once('lassospkit_utils_session.inc.php');
|
||||
|
||||
/**
|
||||
* TODO: initServer();
|
||||
*/
|
||||
class LassoSPKitSAMLCommon {
|
||||
public $session;
|
||||
public $server;
|
||||
var $session;
|
||||
var $server;
|
||||
|
||||
/** Error handling */
|
||||
public $reset_status = 0;
|
||||
public $human_status = "";
|
||||
public $ret = 0;
|
||||
public $ret_str = "";
|
||||
public $exception = null;
|
||||
var $reset_status = 0;
|
||||
var $human_status = "";
|
||||
var $ret = 0;
|
||||
var $ret_str = "";
|
||||
var $exception = null;
|
||||
var $relay_state = null;
|
||||
|
||||
public function __construct(LassoSPKitGenericSession $session) {
|
||||
$this->session = $session;
|
||||
|
@ -108,7 +110,13 @@ class LassoSPKitSAMLCommon {
|
|||
lassospkit_errlog("artifactResolve: soapCall result empty");
|
||||
$content = "";
|
||||
}
|
||||
$retPRM = $profile->processResponseMsg($content);
|
||||
try {
|
||||
$retPRM = $profile->processResponseMsg($content);
|
||||
} catch (Exception $e) {
|
||||
lassospkit_showCode($content);
|
||||
var_dump($e);
|
||||
throw $e;
|
||||
}
|
||||
if ($retIR || $retBRM || $retPRM) {
|
||||
lassospkit_errlog("artifactResolve: retIR: $retIR retBRM: $retBRM retPRM: $retPRM");
|
||||
if ($retIR) {
|
||||
|
@ -159,7 +167,9 @@ class LassoSPKitSAMLCommon {
|
|||
$isConsentObtained,
|
||||
$forceAuthn,
|
||||
$isPassive,
|
||||
$relayState,
|
||||
$blob) {
|
||||
lassospkit_debuglog("isPassive: $isPassive");
|
||||
$login = new LassoLogin($this->server);
|
||||
$retFF = $this->findFederation($login);
|
||||
$retIAR = $login->initAuthnRequest($remoteID,$method);
|
||||
|
@ -173,6 +183,9 @@ class LassoSPKitSAMLCommon {
|
|||
} else {
|
||||
throw new Exception("SSO: Pas d'object NameIDPolicy");
|
||||
}
|
||||
if ($relayState && is_string($relayState)) {
|
||||
$request->msgRelayState = $relayState;
|
||||
}
|
||||
$retBAR = $login->buildAuthnRequestMsg();
|
||||
switch($method) {
|
||||
case LASSO_HTTP_METHOD_REDIRECT:
|
||||
|
@ -187,6 +200,7 @@ class LassoSPKitSAMLCommon {
|
|||
$login = new LassoLogin($this->server);
|
||||
$retPRM = 0;
|
||||
$retAR = 0;
|
||||
$retFF = 0;
|
||||
switch ($method) {
|
||||
case LASSO_HTTP_METHOD_ARTIFACT_GET:
|
||||
case LASSO_HTTP_METHOD_ARTIFACT_POST:
|
||||
|
@ -195,6 +209,7 @@ class LassoSPKitSAMLCommon {
|
|||
$method);
|
||||
break;
|
||||
case LASSO_HTTP_METHOD_POST:
|
||||
case LASSO_HTTP_METHOD_REDIRECT:
|
||||
$retPRM = $this->processResponseMsg($message);
|
||||
break;
|
||||
}
|
||||
|
@ -206,6 +221,9 @@ class LassoSPKitSAMLCommon {
|
|||
$retPRM == LASSO_LOGIN_ERROR_STATUS_NOT_SUCCESS) {
|
||||
$this->setMessage("Request denied");
|
||||
}
|
||||
if ($login->msgRelayState) {
|
||||
$this->relay_state = $login->msgRelayState;
|
||||
}
|
||||
if ($retAR || $retPRM) {
|
||||
lassospkit_errlog("ssoConsumer, retAR: $retAR retPRM: $retPRM");
|
||||
} else {
|
||||
|
@ -221,12 +239,25 @@ class LassoSPKitSAMLCommon {
|
|||
$utils_session->setAssertionAttributes($attributes);
|
||||
}
|
||||
$this->saveFederation($login);
|
||||
|
||||
if ($retAR) {
|
||||
return $retAR;
|
||||
}
|
||||
if ($retPRM) {
|
||||
return $retPRM;
|
||||
}
|
||||
if ($retFF) {
|
||||
return $retFF;
|
||||
}
|
||||
}
|
||||
|
||||
/** Web SLO methods */
|
||||
/* SP initiated */
|
||||
public function initiateSLO($method = LASSO_HTTP_METHOD_SOAP, $remoteID = null)
|
||||
public function initiateSLO($method = LASSO_HTTP_METHOD_SOAP, $remoteID = null, $relayState = null)
|
||||
{
|
||||
if ($method == null) {
|
||||
$method = LASSO_HTTP_METHOD_SOAP;
|
||||
}
|
||||
$logout = new LassoLogout($this->server);
|
||||
$this->findFederation($logout);
|
||||
$retIR = $logout->initRequest($remoteID, $method);
|
||||
|
@ -237,7 +268,7 @@ class LassoSPKitSAMLCommon {
|
|||
break;
|
||||
case LASSO_HTTP_METHOD_SOAP:
|
||||
$this->finishSOAPRequest($logout, $response);
|
||||
$this->processResponseSLO($logout, $response);
|
||||
$this->processResponseSLO($method, $response, $logout);
|
||||
break;
|
||||
case LASSO_HTTP_METHOD_ARTIFACT_GET:
|
||||
case LASSO_HTTP_METHOD_ARTIFACT_POST:
|
||||
|
@ -247,11 +278,10 @@ class LassoSPKitSAMLCommon {
|
|||
}
|
||||
}
|
||||
public function processRedirectResponseSLO() {
|
||||
$logout = null;
|
||||
$this->processResponseSLO($logout, $_SERVER['QUERY_STRING']);
|
||||
$this->processResponseSLO(LASSO_HTTP_METHOD_REDIRECT, $_SERVER['QUERY_STRING']);
|
||||
}
|
||||
public function processResponseSLO(&$logout, $message) {
|
||||
if (! $logout) {
|
||||
public function processResponseSLO($http_method, $message, &$logout = null) {
|
||||
if ($logout == null) {
|
||||
$logout = new LassoLogout($this->server);
|
||||
$this->findFederation($logout);
|
||||
}
|
||||
|
@ -279,11 +309,15 @@ class LassoSPKitSAMLCommon {
|
|||
return $this->processRequestSLO(LASSO_HTTP_METHOD_REDIRECT,
|
||||
$_SERVER['QUERY_STRING']);
|
||||
}
|
||||
/** Read the SOAP request in the POSTed HTTP message,
|
||||
and process it as a SLO request. */
|
||||
public function processSOAPRequestSLO() {
|
||||
$contents = $this->receiveSoapMessage();
|
||||
return $this->processRequestSLO(LASSO_HTTP_METHOD_SOAP,
|
||||
$contents);
|
||||
}
|
||||
/** Use $message as a query for the given http_method,
|
||||
and treat it as a SLO request. */
|
||||
public function processRequestSLO($method, $message) {
|
||||
$logout = new LassoLogout($this->server);
|
||||
$retPRM = $logout->processRequestMsg($message);
|
||||
|
@ -291,16 +325,34 @@ class LassoSPKitSAMLCommon {
|
|||
$retVR = $logout->validateRequest();
|
||||
$retBR = $this->finishResponse($logout, $logout->http_request_method);
|
||||
$this->session->logout();
|
||||
lassospkit_infolog("Logout request handled for nameId: " . $logout->nameID . " retPRM: $retPRM retVR: $retVR retBR: $retBR");
|
||||
return $ok;
|
||||
if ($retPRM || $retVR || $retBR) {
|
||||
lassospkit_infolog("Error during SLO request handling for nameId: " . $logout->nameID . " retPRM: $retPRM retVR: $retVR retBR: $retBR");
|
||||
}
|
||||
if ($retPRM) {
|
||||
return $retPRM;
|
||||
}
|
||||
if ($retVR) {
|
||||
return $retVR;
|
||||
}
|
||||
if ($retBR) {
|
||||
return $retBR;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
/** If result of profile is a modification of identity or session objects,
|
||||
save them in the federations database. */
|
||||
public function saveFederation(LassoProfile $profile) {
|
||||
LassoSPKitHelper::saveFederation($profile, $this->session);
|
||||
}
|
||||
/** Find a federation using as many hints as possible (maybe the nameid given in the request,
|
||||
or the nameid present in the current session) */
|
||||
public function findFederation(LassoProfile $profile) {
|
||||
return LassoSPKitHelper::findFederation($profile, $this->session);
|
||||
}
|
||||
/** Federation termination **/
|
||||
/** Federation termination.
|
||||
Supress the current federation. That is the records associated
|
||||
to the nameid and userid in the current session.
|
||||
**/
|
||||
public function initiateFTNotification($method = LASSO_HTTP_METHOD_SOAP, $remoteID = null) {
|
||||
$this->session->changeFederation(null, null);
|
||||
}
|
||||
|
@ -334,4 +386,7 @@ class LassoSPKitSAMLCommon {
|
|||
function setMessage($message) {
|
||||
LassoSPKitUtilsSession::setLastError($message);
|
||||
}
|
||||
function getRelayState() {
|
||||
return $this->relay_state;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,26 @@
|
|||
<?php
|
||||
require_once('lassospkit_helper.inc.php');
|
||||
require_once('lassospkit_utils.inc.php');
|
||||
require_once('lassospkit_metadata.inc.php');
|
||||
|
||||
class LassoSPKitUrlDispatch {
|
||||
var $dispatch_table = array();
|
||||
|
||||
function addDispatch($point, $method) {
|
||||
$this->dispatch_table[$point] = $method;
|
||||
}
|
||||
function dispatchAndExit() {
|
||||
if (! isset($_SERVER['PATH_INFO'])) {
|
||||
throw new Exception('No PATH INFO');
|
||||
}
|
||||
$path_info = $_SERVER['PATH_INFO'];
|
||||
$fname = $this->dispatch_table[$path_info];
|
||||
if ($fname) {
|
||||
$fname();
|
||||
exit(0);
|
||||
} else {
|
||||
header("HTTP/1.0 404 Not Found");
|
||||
exit(0);
|
||||
}
|
||||
}
|
||||
}
|
Reference in New Issue