View Javadoc

1   /*
2    * Copyright 2007 University Corporation for Advanced Internet Development, Inc.
3    *
4    * Licensed under the Apache License, Version 2.0 (the "License");
5    * you may not use this file except in compliance with the License.
6    * You may obtain a copy of the License at
7    *
8    * http://www.apache.org/licenses/LICENSE-2.0
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS,
12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   * See the License for the specific language governing permissions and
14   * limitations under the License.
15   */
16  
17  package edu.internet2.middleware.shibboleth.common.attribute.resolver.provider.principalConnector;
18  
19  import org.opensaml.common.SAMLObject;
20  import org.opensaml.saml1.core.NameIdentifier;
21  import org.opensaml.saml2.core.NameID;
22  import org.opensaml.util.storage.StorageService;
23  
24  import edu.internet2.middleware.shibboleth.common.attribute.resolver.AttributeResolutionException;
25  import edu.internet2.middleware.shibboleth.common.attribute.resolver.provider.ShibbolethResolutionContext;
26  import edu.internet2.middleware.shibboleth.common.attribute.resolver.provider.attributeDefinition.TransientIdEntry;
27  import edu.internet2.middleware.shibboleth.common.profile.provider.SAMLProfileRequestContext;
28  
29  /**
30   * A principal connector that attempts to look up a name identifier within a store.
31   */
32  public class TransientPrincipalConnector extends BasePrincipalConnector {
33  
34      /** Store used to map transient identifier tokens to principal names. */
35      private StorageService<String, TransientIdEntry> identifierStore;
36  
37      /** Storage partition in which IDs are stored. */
38      private String partition;
39  
40      /**
41       * Constructor.
42       * 
43       * @param store the backing store used to map transient identifier tokens to principal names
44       */
45      public TransientPrincipalConnector(StorageService<String, TransientIdEntry> store) {
46          if (store == null) {
47              throw new IllegalArgumentException("Identifier store may not be null");
48          }
49          identifierStore = store;
50          partition = "transientId";
51      }
52  
53      /** {@inheritDoc} */
54      public String resolve(ShibbolethResolutionContext resolutionContext) throws AttributeResolutionException {
55          SAMLProfileRequestContext requestContext = resolutionContext.getAttributeRequestContext();
56  
57          String transientId = null;
58          SAMLObject subjectId = requestContext.getSubjectNameIdentifier();
59          if (subjectId instanceof NameIdentifier) {
60              NameIdentifier nameId = (NameIdentifier) requestContext.getSubjectNameIdentifier();
61              if (nameId != null) {
62                  transientId = nameId.getNameIdentifier();
63              }
64          } else if (requestContext.getSubjectNameIdentifier() instanceof NameID) {
65              NameID nameId = (NameID) requestContext.getSubjectNameIdentifier();
66              if (nameId != null) {
67                  transientId = nameId.getValue();
68              }
69          } else {
70              throw new AttributeResolutionException("Subject name identifier is not of a supported type");
71          }
72  
73          if (transientId == null) {
74              throw new AttributeResolutionException("Invalid subject name identifier");
75          }
76  
77          TransientIdEntry idToken = identifierStore.get(partition, transientId);
78          if (idToken == null || idToken.isExpired()) {
79              throw new AttributeResolutionException("No information associated with transient identifier: "
80                      + transientId);
81          }
82  
83          if (!idToken.getRelyingPartyId().equals(requestContext.getInboundMessageIssuer())) {
84              throw new AttributeResolutionException("Transient identifier was issued to " + idToken.getRelyingPartyId()
85                      + " but is being used by " + requestContext.getInboundMessageIssuer());
86          }
87  
88          return idToken.getPrincipalName();
89      }
90  
91      /** {@inheritDoc} */
92      public void validate() throws AttributeResolutionException {
93  
94      }
95  }