[java-identity-provider] 26/27: Redo AttributeMappingNodeProcessor using registry.
Scott Cantor
cantor.2 at osu.edu
Fri May 3 14:32:16 EDT 2019
This is an automated email from the git hooks/post-receive script.
scantor pushed a commit to branch feature/IDP-1434
in repository java-identity-provider.
View the commit online:
http://git.shibboleth.net/view/?p=java-identity-provider.git;a=commit;h=368541a29d00a20bf0933967809814ed975c9b92
commit 368541a29d00a20bf0933967809814ed975c9b92
Author: Scott Cantor <cantor.2 at osu.edu>
AuthorDate: Fri May 3 14:12:42 2019 -0400
Redo AttributeMappingNodeProcessor using registry.
---
.../impl/MappedAttributeInMetadataMatcher.java | 2 +-
.../impl/MappedAttributeInMetadataMatcherTest.java | 2 +-
idp-attribute-impl/pom.xml | 5 -
.../spring/AttributeMappingNodeProcessorTest.java | 17 +-
.../src/test/resources/logback-test.xml | 3 +
.../idp/attribute/resolver/filter/service.xml | 49 +++--
.../logic/impl/IsAttributeRequiredPredicate.java | 2 +-
.../NodeProcessingAttachingBeanPostProcessor.java | 14 +-
.../AbstractSAMLAttributeTranscoder.java | 6 +-
.../AttributesMapContainer.java | 16 +-
.../impl/AttributeMappingNodeProcessor.java | 232 +++++++++------------
...estedAttributesInAttributeConsumingService.java | 33 ++-
12 files changed, 176 insertions(+), 205 deletions(-)
diff --git a/idp-attribute-filter-impl/src/main/java/net/shibboleth/idp/attribute/filter/matcher/saml/impl/MappedAttributeInMetadataMatcher.java b/idp-attribute-filter-impl/src/main/java/net/shibboleth/idp/attribute/filter/matcher/saml/impl/MappedAttributeInMetadataMatcher.java
index 4109814..92b8626 100644
--- a/idp-attribute-filter-impl/src/main/java/net/shibboleth/idp/attribute/filter/matcher/saml/impl/MappedAttributeInMetadataMatcher.java
+++ b/idp-attribute-filter-impl/src/main/java/net/shibboleth/idp/attribute/filter/matcher/saml/impl/MappedAttributeInMetadataMatcher.java
@@ -32,7 +32,7 @@ import net.shibboleth.idp.attribute.IdPAttributeValue;
import net.shibboleth.idp.attribute.IdPRequestedAttribute;
import net.shibboleth.idp.attribute.filter.Matcher;
import net.shibboleth.idp.attribute.filter.context.AttributeFilterContext;
-import net.shibboleth.idp.saml.attribute.mapping.AttributesMapContainer;
+import net.shibboleth.idp.saml.attribute.transcoding.AttributesMapContainer;
import net.shibboleth.utilities.java.support.annotation.constraint.NonnullElements;
import net.shibboleth.utilities.java.support.component.AbstractIdentifiableInitializableComponent;
import net.shibboleth.utilities.java.support.component.ComponentSupport;
diff --git a/idp-attribute-filter-impl/src/test/java/net/shibboleth/idp/attribute/filter/matcher/saml/impl/MappedAttributeInMetadataMatcherTest.java b/idp-attribute-filter-impl/src/test/java/net/shibboleth/idp/attribute/filter/matcher/saml/impl/MappedAttributeInMetadataMatcherTest.java
index 9b875fa..0eb5877 100644
--- a/idp-attribute-filter-impl/src/test/java/net/shibboleth/idp/attribute/filter/matcher/saml/impl/MappedAttributeInMetadataMatcherTest.java
+++ b/idp-attribute-filter-impl/src/test/java/net/shibboleth/idp/attribute/filter/matcher/saml/impl/MappedAttributeInMetadataMatcherTest.java
@@ -44,7 +44,7 @@ import net.shibboleth.idp.attribute.IdPAttributeValue;
import net.shibboleth.idp.attribute.IdPRequestedAttribute;
import net.shibboleth.idp.attribute.filter.context.AttributeFilterContext;
import net.shibboleth.idp.attribute.filter.matcher.impl.DataSources;
-import net.shibboleth.idp.saml.attribute.mapping.AttributesMapContainer;
+import net.shibboleth.idp.saml.attribute.transcoding.AttributesMapContainer;
import net.shibboleth.utilities.java.support.component.ComponentInitializationException;
/**
diff --git a/idp-attribute-impl/pom.xml b/idp-attribute-impl/pom.xml
index 77f3e9f..1587f93 100644
--- a/idp-attribute-impl/pom.xml
+++ b/idp-attribute-impl/pom.xml
@@ -30,11 +30,6 @@
<version>${project.version}</version>
</dependency>
- <dependency>
- <groupId>net.shibboleth.ext</groupId>
- <artifactId>spring-extensions</artifactId>
- </dependency>
-
<!-- Provided Dependencies -->
<!-- Runtime Dependencies -->
diff --git a/idp-attribute-resolver-spring/src/test/java/net/shibboleth/idp/attribute/resolver/spring/AttributeMappingNodeProcessorTest.java b/idp-attribute-resolver-spring/src/test/java/net/shibboleth/idp/attribute/resolver/spring/AttributeMappingNodeProcessorTest.java
index 6fd00ff..70c654b 100644
--- a/idp-attribute-resolver-spring/src/test/java/net/shibboleth/idp/attribute/resolver/spring/AttributeMappingNodeProcessorTest.java
+++ b/idp-attribute-resolver-spring/src/test/java/net/shibboleth/idp/attribute/resolver/spring/AttributeMappingNodeProcessorTest.java
@@ -32,7 +32,7 @@ import org.opensaml.saml.saml2.metadata.AttributeConsumingService;
import org.opensaml.saml.saml2.metadata.EntityDescriptor;
import org.springframework.context.support.ConversionServiceFactoryBean;
import org.springframework.context.support.GenericApplicationContext;
-import org.testng.annotations.AfterMethod;
+import org.testng.annotations.AfterClass;
import org.testng.annotations.BeforeClass;
import org.testng.annotations.Test;
@@ -43,8 +43,8 @@ import net.shibboleth.ext.spring.util.SchemaTypeAwareXMLBeanDefinitionReader;
import net.shibboleth.idp.attribute.IdPAttribute;
import net.shibboleth.idp.attribute.IdPRequestedAttribute;
import net.shibboleth.idp.attribute.StringAttributeValue;
-import net.shibboleth.idp.attribute.resolver.AttributeResolver;
-import net.shibboleth.idp.saml.attribute.mapping.AttributesMapContainer;
+import net.shibboleth.idp.attribute.transcoding.AttributeTranscoderRegistry;
+import net.shibboleth.idp.saml.attribute.transcoding.AttributesMapContainer;
import net.shibboleth.idp.saml.metadata.impl.AttributeMappingNodeProcessor;
import net.shibboleth.utilities.java.support.service.ReloadableService;
@@ -55,13 +55,13 @@ public class AttributeMappingNodeProcessorTest extends XMLObjectBaseTestCase {
private EntityDescriptor entityDescriptor;
- private ReloadableService<AttributeResolver> service;
+ private ReloadableService<AttributeTranscoderRegistry> service;
private AttributeMappingNodeProcessor processor;
private GenericApplicationContext pendingTeardownContext = null;
- @AfterMethod public void tearDownTestContext() {
+ @AfterClass public void tearDownTestContext() {
if (null == pendingTeardownContext ) {
return;
}
@@ -82,7 +82,7 @@ public class AttributeMappingNodeProcessorTest extends XMLObjectBaseTestCase {
processor = new AttributeMappingNodeProcessor(service);
}
- private ReloadableService<AttributeResolver> getService() {
+ private ReloadableService<AttributeTranscoderRegistry> getService() {
GenericApplicationContext context = new GenericApplicationContext();
setTestContext(context);
context.setDisplayName("ApplicationContext: ");
@@ -100,8 +100,7 @@ public class AttributeMappingNodeProcessorTest extends XMLObjectBaseTestCase {
beanDefinitionReader.loadBeanDefinitions("/net/shibboleth/idp/attribute/resolver/filter/service.xml");
context.refresh();
- final ReloadableService<AttributeResolver> attributeResolverService = context.getBean(ReloadableService.class);
- return attributeResolverService;
+ return context.getBean(ReloadableService.class);
}
@Test public void entityAttributes() throws FilterException {
@@ -138,7 +137,7 @@ public class AttributeMappingNodeProcessorTest extends XMLObjectBaseTestCase {
final AttributesMapContainer container = acs.getObjectMetadata().get(AttributesMapContainer.class).get(0);
- final Multimap<String, IdPRequestedAttribute> map = container.get();
+ final Multimap<String,IdPRequestedAttribute> map = container.get();
assertEquals(map.size(), 3);
diff --git a/idp-attribute-resolver-spring/src/test/resources/logback-test.xml b/idp-attribute-resolver-spring/src/test/resources/logback-test.xml
index bc9eaee..5c5330f 100644
--- a/idp-attribute-resolver-spring/src/test/resources/logback-test.xml
+++ b/idp-attribute-resolver-spring/src/test/resources/logback-test.xml
@@ -2,8 +2,11 @@
<configuration>
<logger name="net.shibboleth.idp.attribute.resolver.spring" level="DEBUG"/>
+ <logger name="net.shibboleth.idp.attribute.transcoding.spring" level="DEBUG"/>
<logger name="net.shibboleth.idp.attribute.resolver" level="DEBUG"/>
+ <logger name="net.shibboleth.idp.attribute.transcoding" level="DEBUG"/>
<logger name="net.shibboleth.idp.saml.attribute.resolver" level="DEBUG"/>
+ <logger name="net.shibboleth.idp.saml.attribute.transcoding" level="DEBUG"/>
<logger name="net.shibboleth.ext.spring" level="DEBUG"/>
<logger name="net.shibboleth.ext.spring.util" level="DEBUG"/>
<logger name="org.springframework" level="WARN"/>
diff --git a/idp-attribute-resolver-spring/src/test/resources/net/shibboleth/idp/attribute/resolver/filter/service.xml b/idp-attribute-resolver-spring/src/test/resources/net/shibboleth/idp/attribute/resolver/filter/service.xml
index 0a82971..2dfc86e 100644
--- a/idp-attribute-resolver-spring/src/test/resources/net/shibboleth/idp/attribute/resolver/filter/service.xml
+++ b/idp-attribute-resolver-spring/src/test/resources/net/shibboleth/idp/attribute/resolver/filter/service.xml
@@ -5,30 +5,17 @@
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util.xsd"
default-init-method="initialize" default-destroy-method="destroy">
- <bean id="shibboleth.VelocityEngine"
- class="net.shibboleth.ext.spring.velocity.VelocityEngineFactoryBean">
- <property name="velocityProperties">
- <props>
- <prop key="resource.loader">classpath, string</prop>
- <prop key="classpath.resource.loader.class">
- org.apache.velocity.runtime.resource.loader.ClasspathResourceLoader
- </prop>
- <prop key="string.resource.loader.class">
- org.apache.velocity.runtime.resource.loader.StringResourceLoader
- </prop>
- </props>
- </property>
- </bean>
- <bean id="shibboleth.AttributeResolverService" class="net.shibboleth.ext.spring.service.ReloadableSpringService"
+
+ <bean id="shibboleth.AttributeRegistryService" class="net.shibboleth.ext.spring.service.ReloadableSpringService"
depends-on="shibboleth.VelocityEngine" p:failFast="true"
p:reloadCheckDelay="0">
<constructor-arg name="claz"
- value="net.shibboleth.idp.attribute.resolver.AttributeResolver" />
+ value="net.shibboleth.idp.attribute.transcoding.AttributeTranscoderRegistry" />
<constructor-arg name="strategy">
- <bean
- class="net.shibboleth.idp.attribute.resolver.spring.impl.AttributeResolverServiceStrategy"
- p:id="ShibbolethAttributeResolver" />
+ <bean class="net.shibboleth.idp.attribute.transcoding.spring.impl.AttributeRegistryServiceStrategy"
+ p:id="shibboleth.AttributeRegistryService"
+ p:namingRegistry="DefaultNamingRegistry" />
</constructor-arg>
<property name="serviceConfigurations">
<util:list>
@@ -38,4 +25,28 @@
</property>
</bean>
+ <util:map id="DefaultNamingRegistry">
+ <entry key="#{T(org.opensaml.saml.saml2.core.Attribute)}">
+ <bean class="net.shibboleth.idp.saml.attribute.transcoding.AbstractSAML2AttributeTranscoder.NamingFunction" />
+ </entry>
+ <entry key="#{T(org.opensaml.saml.saml1.core.AttributeDesignator)}">
+ <bean class="net.shibboleth.idp.saml.attribute.transcoding.AbstractSAML1AttributeTranscoder.NamingFunction" />
+ </entry>
+ </util:map>
+
+ <bean id="shibboleth.VelocityEngine"
+ class="net.shibboleth.ext.spring.velocity.VelocityEngineFactoryBean">
+ <property name="velocityProperties">
+ <props>
+ <prop key="resource.loader">classpath, string</prop>
+ <prop key="classpath.resource.loader.class">
+ org.apache.velocity.runtime.resource.loader.ClasspathResourceLoader
+ </prop>
+ <prop key="string.resource.loader.class">
+ org.apache.velocity.runtime.resource.loader.StringResourceLoader
+ </prop>
+ </props>
+ </property>
+ </bean>
+
</beans>
\ No newline at end of file
diff --git a/idp-consent-impl/src/main/java/net/shibboleth/idp/consent/logic/impl/IsAttributeRequiredPredicate.java b/idp-consent-impl/src/main/java/net/shibboleth/idp/consent/logic/impl/IsAttributeRequiredPredicate.java
index d64bf06..a23ae41 100644
--- a/idp-consent-impl/src/main/java/net/shibboleth/idp/consent/logic/impl/IsAttributeRequiredPredicate.java
+++ b/idp-consent-impl/src/main/java/net/shibboleth/idp/consent/logic/impl/IsAttributeRequiredPredicate.java
@@ -40,7 +40,7 @@ import com.google.common.collect.Multimap;
import net.shibboleth.idp.attribute.IdPAttribute;
import net.shibboleth.idp.attribute.IdPRequestedAttribute;
-import net.shibboleth.idp.saml.attribute.mapping.AttributesMapContainer;
+import net.shibboleth.idp.saml.attribute.transcoding.AttributesMapContainer;
import net.shibboleth.utilities.java.support.logic.Predicate;
/**
diff --git a/idp-profile-spring/src/main/java/net/shibboleth/idp/profile/spring/relyingparty/metadata/impl/NodeProcessingAttachingBeanPostProcessor.java b/idp-profile-spring/src/main/java/net/shibboleth/idp/profile/spring/relyingparty/metadata/impl/NodeProcessingAttachingBeanPostProcessor.java
index 4610805..79be3bb 100644
--- a/idp-profile-spring/src/main/java/net/shibboleth/idp/profile/spring/relyingparty/metadata/impl/NodeProcessingAttachingBeanPostProcessor.java
+++ b/idp-profile-spring/src/main/java/net/shibboleth/idp/profile/spring/relyingparty/metadata/impl/NodeProcessingAttachingBeanPostProcessor.java
@@ -33,7 +33,7 @@ import org.opensaml.saml.metadata.resolver.filter.impl.NodeProcessingMetadataFil
import org.springframework.beans.factory.BeanCreationException;
import org.springframework.beans.factory.config.BeanPostProcessor;
-import net.shibboleth.idp.attribute.resolver.AttributeResolver;
+import net.shibboleth.idp.attribute.transcoding.AttributeTranscoderRegistry;
import net.shibboleth.idp.saml.metadata.RelyingPartyMetadataProvider;
import net.shibboleth.idp.saml.metadata.impl.AttributeMappingNodeProcessor;
import net.shibboleth.idp.saml.security.impl.KeyAuthorityNodeProcessor;
@@ -52,8 +52,8 @@ import net.shibboleth.utilities.java.support.service.ReloadableService;
*/
public class NodeProcessingAttachingBeanPostProcessor implements BeanPostProcessor {
- /** The attribute resolver we use to map attributes. */
- @Nullable private final ReloadableService<AttributeResolver> atributeResolverService;
+ /** The registry of decoding rules. */
+ @Nullable private final ReloadableService<AttributeTranscoderRegistry> transcoderRegistry;
/**
* Constructor.
@@ -61,8 +61,8 @@ public class NodeProcessingAttachingBeanPostProcessor implements BeanPostProcess
* @param service the attribute resolver we use to map attributes
*/
public NodeProcessingAttachingBeanPostProcessor(
- @Nullable @ParameterName(name="service") final ReloadableService<AttributeResolver> service) {
- atributeResolverService = service;
+ @Nullable @ParameterName(name="service") final ReloadableService<AttributeTranscoderRegistry> service) {
+ transcoderRegistry = service;
}
// Checkstyle: CyclomaticComplexity OFF
@@ -96,8 +96,8 @@ public class NodeProcessingAttachingBeanPostProcessor implements BeanPostProcess
final NodeProcessingMetadataFilter filterToAttach = new NodeProcessingMetadataFilter();
final List<MetadataNodeProcessor> processors = new ArrayList<>(
Arrays.asList(new EntitiesDescriptorNameProcessor(), new KeyAuthorityNodeProcessor()));
- if (null != atributeResolverService) {
- processors.add(new AttributeMappingNodeProcessor(atributeResolverService));
+ if (null != transcoderRegistry) {
+ processors.add(new AttributeMappingNodeProcessor(transcoderRegistry));
}
filterToAttach.setNodeProcessors(processors);
try {
diff --git a/idp-saml-api/src/main/java/net/shibboleth/idp/saml/attribute/transcoding/AbstractSAMLAttributeTranscoder.java b/idp-saml-api/src/main/java/net/shibboleth/idp/saml/attribute/transcoding/AbstractSAMLAttributeTranscoder.java
index 137b119..33f15c6 100644
--- a/idp-saml-api/src/main/java/net/shibboleth/idp/saml/attribute/transcoding/AbstractSAMLAttributeTranscoder.java
+++ b/idp-saml-api/src/main/java/net/shibboleth/idp/saml/attribute/transcoding/AbstractSAMLAttributeTranscoder.java
@@ -132,8 +132,10 @@ public abstract class AbstractSAMLAttributeTranscoder<AttributeType extends SAML
idpAttributeValues.add(idpAttributeValue);
}
}
-
- log.debug("Decoded {} values for attribute {}", idpAttributeValues.size(), attributeName);
+
+ if (!idpAttributeValues.isEmpty()) {
+ log.debug("Decoded {} values for attribute {}", idpAttributeValues.size(), attributeName);
+ }
return buildIdPAttribute(profileRequestContext, input, properties, idpAttributeValues);
}
diff --git a/idp-saml-api/src/main/java/net/shibboleth/idp/saml/attribute/mapping/AttributesMapContainer.java b/idp-saml-api/src/main/java/net/shibboleth/idp/saml/attribute/transcoding/AttributesMapContainer.java
similarity index 74%
rename from idp-saml-api/src/main/java/net/shibboleth/idp/saml/attribute/mapping/AttributesMapContainer.java
rename to idp-saml-api/src/main/java/net/shibboleth/idp/saml/attribute/transcoding/AttributesMapContainer.java
index 3c7bb17..d27a1df 100644
--- a/idp-saml-api/src/main/java/net/shibboleth/idp/saml/attribute/mapping/AttributesMapContainer.java
+++ b/idp-saml-api/src/main/java/net/shibboleth/idp/saml/attribute/transcoding/AttributesMapContainer.java
@@ -15,7 +15,7 @@
* limitations under the License.
*/
-package net.shibboleth.idp.saml.attribute.mapping;
+package net.shibboleth.idp.saml.attribute.transcoding;
import net.shibboleth.idp.attribute.IdPAttribute;
@@ -23,28 +23,28 @@ import com.google.common.base.Supplier;
import com.google.common.collect.Multimap;
/**
- * Container for reverse mapped attributes. This gives us a distinguished class to look for in the
+ * Container for decoded attributes. This gives us a distinguished class to look for in the
* {@link org.opensaml.core.xml.XMLObject#getObjectMetadata()}.
*
- * @param <OutType> The type of attribute we are mapping to.
+ * @param <OutType> The type of object decoded
*/
-public class AttributesMapContainer<OutType extends IdPAttribute> implements Supplier<Multimap<String, OutType>> {
+public class AttributesMapContainer<OutType extends IdPAttribute> implements Supplier<Multimap<String,OutType>> {
/** The map we are encapsulating.*/
- private final Multimap<String, OutType> providedValue;
+ private final Multimap<String,OutType> providedValue;
/**
* Constructor.
*
* @param value the value to return.
*/
- public AttributesMapContainer(final Multimap<String, OutType> value) {
+ public AttributesMapContainer(final Multimap<String,OutType> value) {
providedValue = value;
}
/** {@inheritDoc} */
- @Override public Multimap<String, OutType> get() {
+ @Override public Multimap<String,OutType> get() {
return providedValue;
}
-}
+}
\ No newline at end of file
diff --git a/idp-saml-impl/src/main/java/net/shibboleth/idp/saml/metadata/impl/AttributeMappingNodeProcessor.java b/idp-saml-impl/src/main/java/net/shibboleth/idp/saml/metadata/impl/AttributeMappingNodeProcessor.java
index 1fe014d..919434f 100644
--- a/idp-saml-impl/src/main/java/net/shibboleth/idp/saml/metadata/impl/AttributeMappingNodeProcessor.java
+++ b/idp-saml-impl/src/main/java/net/shibboleth/idp/saml/metadata/impl/AttributeMappingNodeProcessor.java
@@ -17,21 +17,22 @@
package net.shibboleth.idp.saml.metadata.impl;
-import java.time.Instant;
-import java.util.ArrayList;
+import java.util.Collection;
import java.util.List;
+import java.util.Properties;
import javax.annotation.Nonnull;
-import javax.annotation.Nullable;
import javax.annotation.concurrent.NotThreadSafe;
+import net.shibboleth.idp.attribute.AttributeDecodingException;
import net.shibboleth.idp.attribute.IdPAttribute;
import net.shibboleth.idp.attribute.IdPRequestedAttribute;
-import net.shibboleth.idp.attribute.resolver.AttributeResolver;
-import net.shibboleth.idp.saml.attribute.mapping.AttributesMapContainer;
-import net.shibboleth.idp.saml.attribute.mapping.impl.RequestedAttributesMapper;
-import net.shibboleth.idp.saml.attribute.mapping.impl.SAML2AttributesMapper;
-import net.shibboleth.utilities.java.support.component.ComponentInitializationException;
+import net.shibboleth.idp.attribute.transcoding.AttributeTranscoder;
+import net.shibboleth.idp.attribute.transcoding.AttributeTranscoderRegistry;
+import net.shibboleth.idp.attribute.transcoding.TranscoderSupport;
+import net.shibboleth.idp.saml.attribute.transcoding.AttributesMapContainer;
+import net.shibboleth.utilities.java.support.annotation.constraint.Live;
+import net.shibboleth.utilities.java.support.annotation.constraint.NonnullElements;
import net.shibboleth.utilities.java.support.logic.Constraint;
import net.shibboleth.utilities.java.support.service.ReloadableService;
import net.shibboleth.utilities.java.support.service.ServiceableComponent;
@@ -48,6 +49,7 @@ import org.opensaml.saml.saml2.metadata.RequestedAttribute;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
+import com.google.common.collect.HashMultimap;
import com.google.common.collect.Multimap;
/**
@@ -60,178 +62,138 @@ public class AttributeMappingNodeProcessor implements MetadataNodeProcessor {
/** Class logger. */
@Nonnull private final Logger log = LoggerFactory.getLogger(AttributeMappingNodeProcessor.class);
- /** Service used to get the resolver used to fetch attributes. */
- @Nonnull private final ReloadableService<AttributeResolver> attributeResolverService;
-
- /** Whether the last invocation of {@link #refreshMappers()} failed. */
- @Nonnull private boolean refreshFailed;
-
- /** Cached RequestedAttributeMapper. */
- @Nullable private RequestedAttributesMapper requestedAttributesMapper;
-
- /** Cached AttributeMapper. */
- @Nullable private SAML2AttributesMapper attributesMapper;
-
- /** Date when the cache was last refreshed. */
- @Nullable private Instant lastReload;
+ /** Service used to get the registry of decoding rules. */
+ @Nonnull private final ReloadableService<AttributeTranscoderRegistry> transcoderRegistry;
/**
* Constructor.
*
- * @param resolverService the service for the attribute resolver we are to derive unmapping info from
- */
- public AttributeMappingNodeProcessor(@Nonnull final ReloadableService<AttributeResolver> resolverService) {
- attributeResolverService = Constraint.isNotNull(resolverService, "AttributeResolver cannot be null");
- }
-
- /**
- * Get the current RequestedAttributesMapper.
- *
- * @return Returns the mapper.
- */
- public RequestedAttributesMapper getRequestedAttributesMapper() {
- return requestedAttributesMapper;
- }
-
- /**
- * Set the current RequestedAttributesMapper.
- *
- * @param mapper what to set.
+ * @param registry the service for the decoding rules
*/
- public void setRequestedAttributesMapper(@Nullable final RequestedAttributesMapper mapper) {
- requestedAttributesMapper = mapper;
+ public AttributeMappingNodeProcessor(@Nonnull final ReloadableService<AttributeTranscoderRegistry> registry) {
+ transcoderRegistry = Constraint.isNotNull(registry, "AttributeTranscoderRegistry cannot be null");
}
-
- /**
- * Get the current AttributesMapper.
- *
- * @return Returns the mapper.
- */
- public SAML2AttributesMapper getAttributesMapper() {
- return attributesMapper;
- }
-
- /**
- * Set the current AttributesMapper.
- *
- * @param mapper what to set.
- */
- public void setAttributesMapper(@Nullable final SAML2AttributesMapper mapper) {
- attributesMapper = mapper;
- }
-
- /**
- * Inspect the service and see whether we need to reload the mappers.
- *
- * @throws FilterException if the mapping generation fails
- */
- protected void refreshMappers() throws FilterException {
- if (lastReload != null && lastReload.equals(attributeResolverService.getLastSuccessfulReloadInstant())) {
- // Nothing has changed since we last reloaded.
- return;
- }
-
- // Reload
- ServiceableComponent<AttributeResolver> component = null;
- RequestedAttributesMapper ram = null;
- SAML2AttributesMapper am = null;
+
+ /** {@inheritDoc} */
+ @Override public void process(final XMLObject metadataNode) throws FilterException {
+
+ ServiceableComponent<AttributeTranscoderRegistry> component = null;
+
try {
- // get date before we get the component. That way we'll not leak changes.
- final Instant when = attributeResolverService.getLastSuccessfulReloadInstant();
- component = attributeResolverService.getServiceableComponent();
- if (null == component) {
- if (!refreshFailed) {
- log.error("Requested Attributes Mapper: Invalid Attribute resolver configuration.");
+ if (metadataNode instanceof AttributeConsumingService) {
+ component = transcoderRegistry.getServiceableComponent();
+ if (component == null) {
+ log.error("Attribute transcoding service unavailable");
+ } else {
+ handleAttributeConsumingService(component.getComponent(), (AttributeConsumingService) metadataNode);
+ }
+ } else if (metadataNode instanceof EntityDescriptor) {
+ component = transcoderRegistry.getServiceableComponent();
+ if (component == null) {
+ log.error("Attribute transcoding service unavailable");
+ } else {
+ handleEntityDescriptor(component.getComponent(), (EntityDescriptor) metadataNode);
}
- refreshFailed = true;
- } else {
- final AttributeResolver attributeResolver = component.getComponent();
- ram = new RequestedAttributesMapper(attributeResolver);
- am = new SAML2AttributesMapper(attributeResolver);
-
- refreshFailed = false;
- lastReload = when;
}
} finally {
- if (null != component) {
+ if (component != null) {
component.unpinComponent();
}
}
- try {
- if (null != ram) {
- ram.initialize();
- }
- if (null != am) {
- am.initialize();
- }
- } catch (final ComponentInitializationException e) {
- throw new FilterException(e);
- }
- setRequestedAttributesMapper(ram);
- setAttributesMapper(am);
- }
-
- /** {@inheritDoc} */
- @Override public void process(final XMLObject metadataNode) throws FilterException {
- refreshMappers();
- if (metadataNode instanceof AttributeConsumingService) {
-
- handleAttributeConsumingService((AttributeConsumingService) metadataNode);
-
- } else if (metadataNode instanceof EntityDescriptor) {
- handleEntityDescriptor((EntityDescriptor) metadataNode);
- }
}
/**
* Look inside the {@link AttributeConsumingService} for any {@link RequestedAttribute}s and map them.
*
+ * @param registry the registry service
* @param acs the {@link AttributeConsumingService} to look at
*/
-//CheckStyle: ReturnCount OFF
- private void handleAttributeConsumingService(final AttributeConsumingService acs) {
+ private void handleAttributeConsumingService(@Nonnull final AttributeTranscoderRegistry registry,
+ @Nonnull final AttributeConsumingService acs) {
+
final List<RequestedAttribute> requestedAttributes = acs.getRequestAttributes();
- final RequestedAttributesMapper mapper = getRequestedAttributesMapper();
- if (null == requestedAttributes || requestedAttributes.isEmpty() || null == mapper) {
+ if (null == requestedAttributes || requestedAttributes.isEmpty()) {
return;
}
- final Multimap<String, IdPRequestedAttribute> maps = mapper.mapAttributes(requestedAttributes);
- if (null == maps || maps.isEmpty()) {
- return;
+
+ final Multimap<String,IdPAttribute> results = HashMultimap.create();
+ for (final RequestedAttribute req : requestedAttributes) {
+ try {
+ decodeAttribute(registry, req, results);
+ } catch (final AttributeDecodingException e) {
+ log.warn("Error decoding RequestedAttribute '{}'", req.getName(), e);
+ }
+ }
+
+ if (!results.isEmpty()) {
+ acs.getObjectMetadata().put(new AttributesMapContainer<>(results));
}
- acs.getObjectMetadata().put(new AttributesMapContainer<>(maps));
}
-//CheckStyle: ReturnCount ON
/**
* Look inside the {@link EntityDescriptor} for entities Attributes and map them.
*
+ * @param registry the registry service
* @param entity the entity
*/
//CheckStyle: ReturnCount OFF
- private void handleEntityDescriptor(final EntityDescriptor entity) {
- final SAML2AttributesMapper mapper = getAttributesMapper();
+ private void handleEntityDescriptor(@Nonnull final AttributeTranscoderRegistry registry,
+ @Nonnull final EntityDescriptor entity) {
final Extensions extensions = entity.getExtensions();
- if (null == extensions || null == mapper) {
+ if (null == extensions) {
return;
}
+
final List<XMLObject> entityAttributesList =
extensions.getUnknownXMLObjects(EntityAttributes.DEFAULT_ELEMENT_NAME);
if (null == entityAttributesList || entityAttributesList.isEmpty()) {
return;
}
- final List<Attribute> entityAttributes = new ArrayList<>();
+
+ final Multimap<String,IdPAttribute> results = HashMultimap.create();
+
for (final XMLObject xmlObj : entityAttributesList) {
if (xmlObj instanceof EntityAttributes) {
final EntityAttributes ea = (EntityAttributes) xmlObj;
- entityAttributes.addAll(ea.getAttributes());
+ for (final Attribute attr : ea.getAttributes()) {
+ try {
+ decodeAttribute(registry, attr, results);
+ } catch (final AttributeDecodingException e) {
+ log.warn("Error decoding RequestedAttribute '{}'", attr.getName(), e);
+ }
+ }
}
}
- final Multimap<String, IdPAttribute> maps = mapper.mapAttributes(entityAttributes);
- if (null == maps || maps.isEmpty()) {
- return;
+
+ if (!results.isEmpty()) {
+ entity.getObjectMetadata().put(new AttributesMapContainer<>(results));
}
- entity.getObjectMetadata().put(new AttributesMapContainer<>(maps));
}
//CheckStyle: ReturnCount ON
-}
+
+ /**
+ * Access the registry of transcoding rules to decode the input object.
+ *
+ * @param <T> input type
+ * @param registry registry of transcoding rules
+ * @param input input object
+ * @param results collection to add results to
+ *
+ * @throws AttributeDecodingException if an error occurs or no results were obtained
+ */
+ protected <T> void decodeAttribute(@Nonnull final AttributeTranscoderRegistry registry,
+ @Nonnull final T input, @Nonnull @NonnullElements @Live final Multimap<String,IdPAttribute> results)
+ throws AttributeDecodingException {
+
+ final Collection<Properties> rulesets = registry.getTranscodingProperties(input);
+
+ for (final Properties rules : rulesets) {
+ final AttributeTranscoder<T> transcoder = TranscoderSupport.getTranscoder(rules);
+ final IdPAttribute decodedAttribute = transcoder.decode(null, input, rules);
+ if (decodedAttribute != null) {
+ results.put(decodedAttribute.getId(), decodedAttribute);
+ }
+ }
+ }
+
+}
\ No newline at end of file
diff --git a/idp-saml-impl/src/main/java/net/shibboleth/idp/saml/saml2/profile/impl/MapRequestedAttributesInAttributeConsumingService.java b/idp-saml-impl/src/main/java/net/shibboleth/idp/saml/saml2/profile/impl/MapRequestedAttributesInAttributeConsumingService.java
index 6590239..d4f4d0c 100644
--- a/idp-saml-impl/src/main/java/net/shibboleth/idp/saml/saml2/profile/impl/MapRequestedAttributesInAttributeConsumingService.java
+++ b/idp-saml-impl/src/main/java/net/shibboleth/idp/saml/saml2/profile/impl/MapRequestedAttributesInAttributeConsumingService.java
@@ -22,9 +22,9 @@ import java.util.function.Function;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
-import net.shibboleth.idp.attribute.resolver.AttributeResolver;
+import net.shibboleth.idp.attribute.transcoding.AttributeTranscoderRegistry;
import net.shibboleth.idp.profile.AbstractProfileAction;
-import net.shibboleth.idp.saml.attribute.mapping.AttributesMapContainer;
+import net.shibboleth.idp.saml.attribute.transcoding.AttributesMapContainer;
import net.shibboleth.idp.saml.metadata.impl.AttributeMappingNodeProcessor;
import net.shibboleth.utilities.java.support.logic.Constraint;
import net.shibboleth.utilities.java.support.service.ReloadableService;
@@ -55,8 +55,8 @@ public class MapRequestedAttributesInAttributeConsumingService extends AbstractP
@Nonnull private Function<ProfileRequestContext, AttributeConsumingServiceContext>
attributeConsumingServiceContextLookupStrategy;
- /** The attribute resolver we use to map attributes. */
- @Nullable private ReloadableService<AttributeResolver> attributeResolverService;
+ /** The registry of decoding rules. */
+ @Nullable private ReloadableService<AttributeTranscoderRegistry> transcoderRegistry;
/** The context we use to get and put the {@link AttributeConsumingService}.*/
private AttributeConsumingServiceContext acsContext;
@@ -65,7 +65,6 @@ public class MapRequestedAttributesInAttributeConsumingService extends AbstractP
* Constructor.
*/
public MapRequestedAttributesInAttributeConsumingService() {
- super();
// At this point, by default the SAMLMetadataContext hangs off the SAMLPeerContext
attributeConsumingServiceContextLookupStrategy =
new ChildContextLookup(AttributeConsumingServiceContext.class).compose(
@@ -86,12 +85,12 @@ public class MapRequestedAttributesInAttributeConsumingService extends AbstractP
}
/**
- * Sets the service which does the attribute mapping.
+ * Sets the service which provides attribute decoding rules.
*
- * @param resolverService the service for the attribute resolver we are to derive unmapping info from
+ * @param registry the registry service
*/
- public void setResolverService(@Nonnull final ReloadableService<AttributeResolver> resolverService) {
- attributeResolverService = Constraint.isNotNull(resolverService, "AttributeResolver cannot be null");
+ public void setTranscoderRegistry(@Nonnull final ReloadableService<AttributeTranscoderRegistry> registry) {
+ transcoderRegistry = Constraint.isNotNull(registry, "AttributeResolver cannot be null");
}
/** {@inheritDoc} */
@@ -112,23 +111,23 @@ public class MapRequestedAttributesInAttributeConsumingService extends AbstractP
final AttributeConsumingService acs = acsContext.getAttributeConsumingService();
if (acs == null) {
- log.trace("{} no AttributeConsumingService to map", getLogPrefix());
+ log.trace("{} No AttributeConsumingService to map", getLogPrefix());
return;
}
- if (acs.getRequestAttributes().isEmpty() ||
- acs.getObjectMetadata().containsKey(AttributesMapContainer.class) ||
- acs.getParent() != null) {
- log.trace("{} skipping mapping for AttributeConsumingService", getLogPrefix());
+ if (acs.getRequestAttributes().isEmpty() || acs.getObjectMetadata().containsKey(AttributesMapContainer.class) ||
+ acs.getParent() != null) {
+ log.trace("{} Skipping decode of AttributeConsumingService", getLogPrefix());
// Nothing to map, already mapped, or attached to metadata (and hence already scanned)
return;
}
+
try {
- final AttributeMappingNodeProcessor processor = new AttributeMappingNodeProcessor(attributeResolverService);
- log.debug("{} mapping requested Attributes for generated AttributeConsumingService", getLogPrefix());
+ final AttributeMappingNodeProcessor processor = new AttributeMappingNodeProcessor(transcoderRegistry);
+ log.debug("{} Decoding RequestedAttributes for generated AttributeConsumingService", getLogPrefix());
processor.process(acs);
} catch (final FilterException e) {
- log.error("{} Error mapping Attributesresponding to request", getLogPrefix(), e);
+ log.error("{} Error decoding RequestedAttributes", getLogPrefix(), e);
ActionSupport.buildEvent(profileRequestContext, EventIds.RUNTIME_EXCEPTION);
}
}
--
To stop receiving notification emails like this one, please contact
the administrator of this repository.
More information about the commits
mailing list