From 327a71e894bc7a903f367cdc014b60b6eb629854 Mon Sep 17 00:00:00 2001
From: Olav Morken <olav.morken@uninett.no>
Date: Tue, 4 Mar 2008 13:18:00 +0000
Subject: [PATCH] Added XML metadata source.

git-svn-id: https://simplesamlphp.googlecode.com/svn/trunk@348 44740490-163a-0410-bde0-09ae8108e29a
---
 config/config-template.php                    |  15 +++
 .../Metadata/MetaDataStorageHandlerXML.php    | 103 ++++++++++++++++++
 .../Metadata/MetaDataStorageSource.php        |   3 +
 3 files changed, 121 insertions(+)
 create mode 100644 lib/SimpleSAML/Metadata/MetaDataStorageHandlerXML.php

diff --git a/config/config-template.php b/config/config-template.php
index 3da780acd..cbbf74c1b 100644
--- a/config/config-template.php
+++ b/config/config-template.php
@@ -154,6 +154,15 @@ $config = array (
 	 *                this option is the value of the 'metadatadir' configuration option, or
 	 *                'metadata/' if that option is unset.
 	 *
+	 * XML metadata handler:
+	 * This metadata handler parses an XML file with either an EntityDescriptor element or an
+	 * EntitiesDescriptor element. The XML file may be stored locally, or (for debugging) on a remote
+	 * web server.
+	 * The XML hetadata handler defines the following options:
+	 * - 'type': This is always 'xml'.
+	 * - 'file': Path to an XML file with either
+	 * - 'url': The url to fetch metadata from. THIS IS ONLY FOR DEBUGGING - THERE IS NO CACHING OF THE RESPONSE.
+	 *
 	 *
 	 * Examples:
 	 *
@@ -165,6 +174,12 @@ $config = array (
 	 *     array('type' => 'flatfile', 'directory' => 'metadata-generated'),
 	 *     ),
 	 *
+	 * This example defines a flatfile source and an XML source.
+	 * 'metadata.sources' => array(
+	 *     array('type' => 'flatfile'),
+	 *     array('type' => 'xml', 'file' => 'idp.example.org-idpMeta.xml'),
+	 *     ),
+	 *
 	 *
 	 * Default:
 	 * 'metadata.sources' => array(
diff --git a/lib/SimpleSAML/Metadata/MetaDataStorageHandlerXML.php b/lib/SimpleSAML/Metadata/MetaDataStorageHandlerXML.php
new file mode 100644
index 000000000..131eaa7e8
--- /dev/null
+++ b/lib/SimpleSAML/Metadata/MetaDataStorageHandlerXML.php
@@ -0,0 +1,103 @@
+<?php
+
+require_once('SimpleSAML/Configuration.php');
+require_once('SimpleSAML/Metadata/MetaDataStorageSource.php');
+require_once('SimpleSAML/Metadata/SAMLParser.php');
+
+/**
+ * This class implements a metadata source which loads metadata from XML files.
+ * The XML files should be in the SAML 2.0 metadata format.
+ *
+ * @author Olav Morken, UNINETT AS.
+ * @package simpleSAMLphp
+ * @version $Id$
+ */
+class SimpleSAML_Metadata_MetaDataStorageHandlerXML extends SimpleSAML_Metadata_MetaDataStorageSource {
+
+	/**
+	 * This variable contains an associative array with the parsed metadata.
+	 */
+	private $metadata;
+
+
+	/**
+	 * This function initializes the XML metadata source. The configuration must contain one of
+	 * the following options:
+	 * - 'file': Path to a file with the metadata. This path is relative to the simpleSAMLphp
+	 *           base directory.
+	 * - 'url': URL we should download the metadata from. This is only meant for testing.
+	 *
+	 * @param $config  The configuration for this instance of the XML metadata source.
+	 */
+	protected function __construct($config) {
+
+		/* Get the configuration. */
+		$globalConfig = SimpleSAML_Configuration::getInstance();
+
+		if(array_key_exists('file', $config)) {
+			$src = $globalConfig->resolvePath($config['file']);
+		} elseif(array_key_exists('url', $config)) {
+			$src = $config['url'];
+		} else {
+			throw new Exception('Missing either \'file\' or \'url\' in XML metadata source configuration.');
+		}
+
+
+		$SP1x = array();
+		$IdP1x = array();
+		$SP20 = array();
+		$IdP20 = array();
+
+		$entities = SimpleSAML_Metadata_SAMLParser::parseDescriptorsFile($src);
+		foreach($entities as $entityId => $entity) {
+
+			$md = $entity->getMetadata1xSP();
+			if($md !== NULL) {
+				$SP1x[$entityId] = $md;
+			}
+
+			$md = $entity->getMetadata1xIdP();
+			if($md !== NULL) {
+				$IdP1x[$entityId] = $md;
+			}
+
+			$md = $entity->getMetadata20SP();
+			if($md !== NULL) {
+				$SP20[$entityId] = $md;
+			}
+
+			$md = $entity->getMetadata20IdP();
+			if($md !== NULL) {
+				$IdP20[$entityId] = $md;
+			}
+
+		}
+
+		$this->metadata = array(
+			'shib13-sp-remote' => $SP1x,
+			'shib13-idp-remote' => $IdP1x,
+			'saml20-sp-remote' => $SP20,
+			'saml20-idp-remote' => $IdP20,
+			);
+
+	}
+
+
+	/**
+	 * This function returns an associative array with metadata for all entities in the given set. The
+	 * key of the array is the entity id.
+	 *
+	 * @param $set  The set we want to list metadata for.
+	 * @return An associative array with all entities in the given set.
+	 */
+	public function getMetadataSet($set) {
+		if(array_key_exists($set, $this->metadata)) {
+			return $this->metadata[$set];
+		}
+
+		/* We don't have this metadata set. */
+		return array();
+	}
+}
+
+?>
\ No newline at end of file
diff --git a/lib/SimpleSAML/Metadata/MetaDataStorageSource.php b/lib/SimpleSAML/Metadata/MetaDataStorageSource.php
index 3eaa5c587..c80e66072 100644
--- a/lib/SimpleSAML/Metadata/MetaDataStorageSource.php
+++ b/lib/SimpleSAML/Metadata/MetaDataStorageSource.php
@@ -1,6 +1,7 @@
 <?php
 
 require_once('SimpleSAML/Metadata/MetaDataStorageHandlerFlatfile.php');
+require_once('SimpleSAML/Metadata/MetaDataStorageHandlerXML.php');
 
 /**
  * This abstract class defines an interface for metadata storage sources.
@@ -37,6 +38,8 @@ abstract class SimpleSAML_Metadata_MetaDataStorageSource {
 		switch($type) {
 		case 'flatfile':
 			return new SimpleSAML_Metadata_MetaDataStorageHandlerFlatFile($sourceConfig);
+		case 'xml':
+			return new SimpleSAML_Metadata_MetaDataStorageHandlerXML($sourceConfig);
 		default:
 			throw new Exception('Invalid metadata source type: "' . $type . '".');
 		}
-- 
GitLab