protected function createLogoutResponse($testrun, $logoutRequest, $logoutRelayState) { $this->log($testrun, 'Creating response with relaystate [' . $logoutRelayState . ']'); $idpMetadata = SimpleSAML_Configuration::loadFromArray($this->idpmetadata); $spMetadata = SimpleSAML_Configuration::loadFromArray($this->metadata); // Get SingleLogoutService URL $consumerURLf = $spMetadata->getDefaultEndpoint('SingleLogoutService', array('urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect')); $consumerURL = $consumerURLf['Location']; /* Create an send response. */ $response = sspmod_saml2_Message::buildLogoutResponse($idpMetadata, $spMetadata); $response->setRelayState($logoutRequest->getRelayState()); $response->setInResponseTo($logoutRequest->getId()); $keyArray = SimpleSAML_Utilities::loadPrivateKey($idpMetadata, TRUE); $certArray = SimpleSAML_Utilities::loadPublicKey($idpMetadata, FALSE); $privateKey = new XMLSecurityKey(XMLSecurityKey::RSA_SHA1, array('type' => 'private')); $privateKey->loadKey($keyArray['PEM'], FALSE); $response->setSignatureKey($privateKey); if ($certArray === NULL) { throw new Exception('No certificates found. [1]'); } if (!array_key_exists('PEM', $certArray)) { throw new Exception('No certificates found. [2]'); } $response->setCertificates(array($certArray['PEM'])); #$this->tweakResponse($testrun, $response); $msgStr = $response->toUnsignedXML(); #$this->tweakResponseDOM($testrun, $msgStr); $msgStr = $msgStr->ownerDocument->saveXML($msgStr); # echo '<pre>'; echo(htmlspecialchars($msgStr)); exit; # $msgStr = base64_encode($msgStr); # $msgStr = htmlspecialchars($msgStr); return array('url' => $consumerURL, 'Response' => $msgStr, 'ResponseObj' => $response, 'RelayState' => $logoutRelayState); }
$spEntityId = $source->getEntityId(); $metadata = SimpleSAML_Metadata_MetaDataStorageHandler::getMetadataHandler(); $idpMetadata = $metadata->getMetaDataConfig($idpEntityId, 'saml20-idp-remote'); $spMetadata = $source->getMetadata(); sspmod_saml2_Message::validateMessage($idpMetadata, $spMetadata, $message); if ($message instanceof SAML2_LogoutResponse) { $relayState = $message->getRelayState(); if ($relayState === NULL) { /* Somehow, our RelayState has been lost. */ throw new SimpleSAML_Error_BadRequest('Missing RelayState in logout response.'); } if (!$message->isSuccess()) { SimpleSAML_Logger::warning('Unsuccessful logout. Status was: ' . sspmod_saml2_Message::getResponseError($message)); } $state = SimpleSAML_Auth_State::loadState($relayState, sspmod_saml2_Auth_Source_SP::STAGE_LOGOUTSENT); SimpleSAML_Auth_Source::completeLogout($state); } elseif ($message instanceof SAML2_LogoutRequest) { SimpleSAML_Logger::debug('module/saml2/sp/logout: Request from ' . $idpEntityId); SimpleSAML_Logger::stats('saml20-idp-SLO idpinit ' . $spEntityId . ' ' . $idpEntityId); /* Notify source of logout, so that it may call logout callbacks. */ $source->onLogout($idpEntityId); /* Create an send response. */ $lr = sspmod_saml2_Message::buildLogoutResponse($spMetadata, $idpMetadata); $lr->setRelayState($message->getRelayState()); $lr->setInResponseTo($message->getId()); $binding = new SAML2_HTTPRedirect(); $binding->setDestination(sspmod_SAML2_Message::getDebugDestination()); $binding->send($lr); } else { throw new SimpleSAML_Error_BadRequest('Unknown message received on logout endpoint: ' . get_class($message)); }