diff options
Diffstat (limited to 'src/DotNetOpenId/Yadis/XrdsDocument.cs')
-rw-r--r-- | src/DotNetOpenId/Yadis/XrdsDocument.cs | 107 |
1 files changed, 67 insertions, 40 deletions
diff --git a/src/DotNetOpenId/Yadis/XrdsDocument.cs b/src/DotNetOpenId/Yadis/XrdsDocument.cs index 67bec24..d3510e5 100644 --- a/src/DotNetOpenId/Yadis/XrdsDocument.cs +++ b/src/DotNetOpenId/Yadis/XrdsDocument.cs @@ -1,11 +1,10 @@ -using System;
+using System.Collections.Generic;
+using System.Diagnostics;
using System.IO;
using System.Xml;
using System.Xml.XPath;
-using System.Collections.Generic;
-using DotNetOpenId.RelyingParty;
using DotNetOpenId.Provider;
-using System.Diagnostics;
+using DotNetOpenId.RelyingParty;
namespace DotNetOpenId.Yadis {
class XrdsDocument : XrdsNode {
@@ -31,63 +30,91 @@ namespace DotNetOpenId.Yadis { }
} else {
XPathNavigator node = Node.SelectSingleNode("/xrd:XRD", XmlNamespaceResolver);
- yield return new XrdElement(node, this);
+ if (node != null) {
+ yield return new XrdElement(node, this);
+ }
}
}
}
- internal ServiceEndpoint CreateServiceEndpoint(UriIdentifier claimedIdentifier) {
- return createServiceEndpoint(claimedIdentifier);
+ internal IEnumerable<ServiceEndpoint> CreateServiceEndpoints(UriIdentifier claimedIdentifier) {
+ List<ServiceEndpoint> endpoints = new List<ServiceEndpoint>();
+ endpoints.AddRange(generateOPIdentifierServiceEndpoints(claimedIdentifier));
+ // If any OP Identifier service elements were found, we must not proceed
+ // to return any Claimed Identifier services.
+ if (endpoints.Count == 0) {
+ endpoints.AddRange(generateClaimedIdentifierServiceEndpoints(claimedIdentifier));
+ }
+ return endpoints;
}
- internal ServiceEndpoint CreateServiceEndpoint(XriIdentifier userSuppliedIdentifier) {
- return createServiceEndpoint(userSuppliedIdentifier);
+ internal IEnumerable<ServiceEndpoint> CreateServiceEndpoints(XriIdentifier discoveredIdentifier, XriIdentifier userSuppliedIdentifier) {
+ List<ServiceEndpoint> endpoints = new List<ServiceEndpoint>();
+ endpoints.AddRange(generateOPIdentifierServiceEndpoints(userSuppliedIdentifier));
+ // If any OP Identifier service elements were found, we must not proceed
+ // to return any Claimed Identifier services.
+ if (endpoints.Count == 0) {
+ endpoints.AddRange(generateClaimedIdentifierServiceEndpoints(discoveredIdentifier, userSuppliedIdentifier));
+ }
+ return endpoints;
}
- const bool performCIDVerification = true;
-
- ServiceEndpoint createServiceEndpoint(Identifier userSuppliedOrClaimedIdentifier) {
- // First search for OP Identifier service elements
+ IEnumerable<ServiceEndpoint> generateOPIdentifierServiceEndpoints(Identifier opIdentifier) {
foreach (var service in findOPIdentifierServices()) {
foreach (var uri in service.UriElements) {
var protocol = Util.FindBestVersion(p => p.OPIdentifierServiceTypeURI, service.TypeElementUris);
- return new ServiceEndpoint(protocol.ClaimedIdentifierForOPIdentifier, uri.Uri,
- protocol.ClaimedIdentifierForOPIdentifier, service.TypeElementUris);
+ yield return ServiceEndpoint.CreateForProviderIdentifier(
+ opIdentifier, uri.Uri, service.TypeElementUris,
+ service.Priority, uri.Priority);
+ }
+ }
+ }
+
+ IEnumerable<ServiceEndpoint> generateClaimedIdentifierServiceEndpoints(UriIdentifier claimedIdentifier) {
+ foreach (var service in findClaimedIdentifierServices()) {
+ foreach (var uri in service.UriElements) {
+ yield return ServiceEndpoint.CreateForClaimedIdentifier(
+ claimedIdentifier, service.ProviderLocalIdentifier,
+ uri.Uri, service.TypeElementUris, service.Priority, uri.Priority);
}
}
- // Since we could not find an OP Identifier service element,
- // search for a Claimed Identifier element.
+ }
+
+ IEnumerable<ServiceEndpoint> generateClaimedIdentifierServiceEndpoints(XriIdentifier claimedIdentifier, XriIdentifier userSuppliedIdentifier) {
foreach (var service in findClaimedIdentifierServices()) {
foreach (var uri in service.UriElements) {
// spec section 7.3.2.3 on Claimed Id -> CanonicalID substitution
- if (userSuppliedOrClaimedIdentifier is XriIdentifier) {
- if (service.Xrd.CanonicalID == null) {
- Logger.WarnFormat(Strings.MissingCanonicalIDElement, userSuppliedOrClaimedIdentifier);
- return null;
- }
- // In the case of XRI names, the ClaimedId is actually the CanonicalID.
- // Per http://dev.inames.net/wiki/XRI_CanonicalID_Verification as of 6/20/08,
- // we need to perform CanonicalId verification when using xri.net as our proxy resolver
- // to protect ourselves against a security vulnerability.
- // We do this by asking the proxy to resolve again, based on the CanonicalId that we
- // just got from the XRI i-name. We SHOULD get the same document back, but in case
- // of the attack it would be a different document, and the second document would be
- // the reliable one.
- if (performCIDVerification && userSuppliedOrClaimedIdentifier != service.Xrd.CanonicalID) {
- Logger.InfoFormat("Performing XRI CanonicalID verification on user supplied identifier {0}, canonical id {1}.", userSuppliedOrClaimedIdentifier, service.Xrd.CanonicalID);
- Identifier canonicalId = service.Xrd.CanonicalID;
- return canonicalId.Discover();
- } else {
- userSuppliedOrClaimedIdentifier = service.Xrd.CanonicalID;
+ if (service.Xrd.CanonicalID == null) {
+ Logger.WarnFormat(Strings.MissingCanonicalIDElement, userSuppliedIdentifier);
+ break; // skip on to next service
+ }
+ // In the case of XRI names, the ClaimedId is actually the CanonicalID.
+ // Per http://dev.inames.net/wiki/XRI_CanonicalID_Verification as of 6/20/08,
+ // we need to perform CanonicalId verification when using xri.net as our proxy resolver
+ // to protect ourselves against a security vulnerability.
+ // We do this by asking the proxy to resolve again, based on the CanonicalId that we
+ // just got from the XRI i-name. We SHOULD get the same document back, but in case
+ // of the attack it would be a different document, and the second document would be
+ // the reliable one.
+ if (performCIDVerification && claimedIdentifier != service.Xrd.CanonicalID) {
+ Logger.InfoFormat("Performing XRI CanonicalID verification on user supplied identifier {0}, canonical id {1}.", userSuppliedIdentifier, service.Xrd.CanonicalID);
+ XriIdentifier canonicalId = new XriIdentifier(service.Xrd.CanonicalID);
+ foreach (var endpoint in canonicalId.Discover(userSuppliedIdentifier)) {
+ yield return endpoint;
}
+ yield break;
+ } else {
+ claimedIdentifier = new XriIdentifier(service.Xrd.CanonicalID);
}
- return new ServiceEndpoint(userSuppliedOrClaimedIdentifier, uri.Uri,
- service.ProviderLocalIdentifier, service.TypeElementUris);
+ yield return ServiceEndpoint.CreateForClaimedIdentifier(
+ claimedIdentifier, userSuppliedIdentifier, service.ProviderLocalIdentifier,
+ uri.Uri, service.TypeElementUris, service.Priority, uri.Priority);
}
}
- return null;
}
+ const bool performCIDVerification = true;
+
internal IEnumerable<RelyingPartyReceivingEndpoint> FindRelyingPartyReceivingEndpoints() {
foreach (var service in findReturnToServices()) {
foreach (var uri in service.UriElements) {
@@ -118,7 +145,7 @@ namespace DotNetOpenId.Yadis { IEnumerable<ServiceElement> findReturnToServices() {
foreach (var xrd in XrdElements) {
- foreach( var service in xrd.OpenIdRelyingPartyReturnToServices) {
+ foreach (var service in xrd.OpenIdRelyingPartyReturnToServices) {
yield return service;
}
}
|