Skip to content

Instantly share code, notes, and snippets.

@daserzw
Last active October 18, 2022 05:14
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save daserzw/3a9250b3331ebf26f44281ed32e8e3ee to your computer and use it in GitHub Desktop.
Save daserzw/3a9250b3331ebf26f44281ed32e8e3ee to your computer and use it in GitHub Desktop.
IDEM Shibboleth Active Directory Attribute Resolver
<?xml version="1.0" encoding="UTF-8"?>
<AttributeResolver
xmlns="urn:mace:shibboleth:2.0:resolver"
xmlns:sec="urn:mace:shibboleth:2.0:security"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="urn:mace:shibboleth:2.0:resolver http://shibboleth.net/schema/idp/shibboleth-attribute-resolver.xsd
urn:mace:shibboleth:2.0:security http://shibboleth.net/schema/idp/shibboleth-security.xsd">
<!-- ========================================== -->
<!-- Attribute Definitions -->
<!-- ========================================== -->
<AttributeDefinition xsi:type="Simple" id="surname" sourceAttributeID="sn">
<Dependency ref="myLDAP" />
<DisplayName xml:lang="en">Surname</DisplayName>
<DisplayName xml:lang="it">Cognome</DisplayName>
<DisplayDescription xml:lang="en">Surname of user</DisplayDescription>
<DisplayDescription xml:lang="it">Cognome utente</DisplayDescription>
<AttributeEncoder xsi:type="SAML2String" name="urn:oid:2.5.4.4" friendlyName="sn" encodeType="false" />
</AttributeDefinition>
<AttributeDefinition xsi:type="Simple" id="sAMAccountName" sourceAttributeID="sAMAccountName">
<Dependency ref="myLDAP" />
</AttributeDefinition>
<AttributeDefinition xsi:type="Simple" id="uid" sourceAttributeID="sAMAccountName">
<Dependency ref="sAMAccountName" />
<DisplayName xml:lang="en">UserID</DisplayName>
<DisplayName xml:lang="it">UserID</DisplayName>
<DisplayDescription xml:lang="en">User Identifier</DisplayDescription>
<DisplayDescription xml:lang="it">Identificativo di questo utente</DisplayDescription>
<AttributeEncoder xsi:type="SAML2String" name="urn:oid:0.9.2342.19200300.100.1.1" friendlyName="uid" encodeType="false" />
</AttributeDefinition>
<AttributeDefinition scope="%{idp.scope}" xsi:type="Scoped" id="eduPersonScopedAffiliation" sourceAttributeID="eduPersonAffiliation">
<Dependency ref="eduPersonAffiliation" />
<DisplayName xml:lang="en">Scoped Affiliation</DisplayName>
<DisplayName xml:lang="it">Affiliazione con ambito</DisplayName>
<DisplayDescription xml:lang="en">Affiliation Scoped: Type of affiliation with Home Organization with scope</DisplayDescription>
<DisplayDescription xml:lang="it">Affiliazione con ambito: ruolo ricoperto con dominio dell'Organizzazione</DisplayDescription>
<AttributeEncoder xsi:type="SAML2ScopedString" name="urn:oid:1.3.6.1.4.1.5923.1.1.1.9" friendlyName="eduPersonScopedAffiliation" encodeType="false" />
</AttributeDefinition>
<AttributeDefinition xsi:type="Simple" id="eduPersonEntitlement" sourceAttributeID="eduPersonEntitlement">
<Dependency ref="myLDAP" />
<DisplayName xml:lang="en">Entitlement</DisplayName>
<DisplayName xml:lang="it">Entitlement</DisplayName>
<DisplayDescription xml:lang="en">Entitlement: URI (either URL or URN) that indicates a set of rights to specific resources based on an agreement across the releavant community</DisplayDescription>
<DisplayDescription xml:lang="it">Entitlement: URI (URL o URN) che rappresenta diritti specifici d'accesso validi in tutta la community</DisplayDescription>
<AttributeEncoder xsi:type="SAML2String" name="urn:oid:1.3.6.1.4.1.5923.1.1.1.7" friendlyName="eduPersonEntitlement" encodeType="false" />
</AttributeDefinition>
<AttributeDefinition xsi:type="Simple" id="memberOf" sourceAttributeID="memberOf">
<Dependency ref="myLDAP" />
</AttributeDefinition>
<AttributeDefinition xsi:type="ScriptedAttribute" id="eduPersonAffiliation">
<Dependency ref="myLDAP" />
<Dependency ref="memberOf" />
<DisplayName xml:lang="en">Affiliation</DisplayName>
<DisplayName xml:lang="it">Affiliazione</DisplayName>
<DisplayDescription xml:lang="en">Affiliation: Type of affiliation with Home Organization</DisplayDescription>
<DisplayDescription xml:lang="it">Affiliazione: Tipo di relazione mantenuta con la propria organizzazione</DisplayDescription>
<AttributeEncoder xsi:type="SAML2String" name="urn:oid:1.3.6.1.4.1.5923.1.1.1.1" friendlyName="eduPersonAffiliation" encodeType="false" />
<!-- The script, wrapped in a CDATA section so that special XML characters don't need to be removed -->
<Script><![CDATA[
if (typeof memberOf != "undefined" && memberOf != null ){
for ( i = 0; memberOf != null && i < memberOf.getValues().size(); i++ ){
value = memberOf.getValues().get(i);
if (value.indexOf("CN=federation-idp-affiliation-staff") > -1){
eduPersonAffiliation.addValue("staff");
}
if (value.indexOf("CN=federation-idp-affiliation-member") > -1){
eduPersonAffiliation.addValue("member");
}
if (value.indexOf("CN=federation-idp-affiliation-affiliate") > -1){
eduPersonAffiliation.addValue("affiliate");
}
}
}
]]></Script>
</AttributeDefinition>
<AttributeDefinition scope="%{idp.scope}" xsi:type="Scoped" id="eduPersonPrincipalName" sourceAttributeID="sAMAccountName">
<Dependency ref="sAMAccountName" />
<DisplayName xml:lang="en">eduPersonPrincipalName</DisplayName>
<DisplayName xml:lang="it">eduPersonPrincipalName</DisplayName>
<DisplayDescription xml:lang="en">Unique and persistent Identifier of a person</DisplayDescription>
<DisplayDescription xml:lang="it">Identificativo unico persistente di questo utente</DisplayDescription>
<AttributeEncoder xsi:type="SAML2ScopedString" name="urn:oid:1.3.6.1.4.1.5923.1.1.1.6" friendlyName="eduPersonPrincipalName" encodeType="false" />
</AttributeDefinition>
<AttributeDefinition xsi:type="Simple" id="commonName" sourceAttributeID="cn">
<Dependency ref="myLDAP" />
<DisplayName xml:lang="en">CommonName</DisplayName>
<DisplayName xml:lang="it">Nome e Cognome</DisplayName>
<DisplayDescription xml:lang="en">One or more names that should appear in white-pages-like applications of this person</DisplayDescription>
<DisplayDescription xml:lang="it">Nome e Cognome proprio di una persona</DisplayDescription>
<AttributeEncoder xsi:type="SAML2String" name="urn:oid:2.5.4.3" friendlyName="cn" encodeType="false" />
</AttributeDefinition>
<AttributeDefinition xsi:type="SAML2NameID" nameIdFormat="urn:oasis:names:tc:SAML:2.0:nameid-format:persistent" id="eduPersonTargetedID" sourceAttributeID="persistentID">
<Dependency ref="myStoredId" />
<DisplayName xml:lang="en">Opaque per-service identifier eduPersonTargetedID</DisplayName>
<DisplayName xml:lang="it">Identificatore opaco diverso per ogni servizio eduPersonTargetedID</DisplayName>
<DisplayDescription xml:lang="en">Opaque per-service identifier eduPersonTargetedID</DisplayDescription>
<DisplayDescription xml:lang="it">Identificatore opaco diverso per ogni servizio eduPersonTargetedID</DisplayDescription>
<AttributeEncoder xsi:type="SAML2XMLObject" name="urn:oid:1.3.6.1.4.1.5923.1.1.1.10" friendlyName="eduPersonTargetedID" encodeType="false" />
</AttributeDefinition>
<AttributeDefinition xsi:type="Simple" id="email" sourceAttributeID="mail">
<Dependency ref="myLDAP" />
<DisplayName xml:lang="en">E-mail</DisplayName>
<DisplayName xml:lang="it">E-mail</DisplayName>
<DisplayDescription xml:lang="en">E-mail: Preferred address for email to be sent to this person</DisplayDescription>
<DisplayDescription xml:lang="it">E-mail: Indirizzo e-mail preferito dall'utente</DisplayDescription>
<AttributeEncoder xsi:type="SAML2String" name="urn:oid:0.9.2342.19200300.100.1.3" friendlyName="mail" encodeType="false" />
</AttributeDefinition>
<AttributeDefinition xsi:type="Simple" id="schacHomeOrganization" sourceAttributeID="schacHomeOrganization">
<Dependency ref="staticAttributes" />
<DisplayName xml:lang="en">Institution Domain</DisplayName>
<DisplayName xml:lang="it">Dominio Istituzione</DisplayName>
<DisplayDescription xml:lang="en">Domain of the institution</DisplayDescription>
<DisplayDescription xml:lang="it">Dominio dell'istituzione</DisplayDescription>
<AttributeEncoder xsi:type="SAML2String" name="urn:oid:1.3.6.1.4.1.25178.1.2.9" friendlyName="schacHomeOrganization" encodeType="false" />
</AttributeDefinition>
<AttributeDefinition xsi:type="Simple" id="givenName" sourceAttributeID="givenName">
<Dependency ref="myLDAP" />
<DisplayName xml:lang="en">Nome</DisplayName>
<DisplayName xml:lang="it">Nome</DisplayName>
<DisplayDescription xml:lang="en">Given name of a person</DisplayDescription>
<DisplayDescription xml:lang="it">Nome proprio di una persona</DisplayDescription>
<AttributeEncoder xsi:type="SAML2String" name="urn:oid:2.5.4.42" friendlyName="givenName" encodeType="false" />
</AttributeDefinition>
<AttributeDefinition xsi:type="ScriptedAttribute" id="displayName">
<Dependency ref="myLDAP" />
<Dependency ref="commonName" />
<Dependency ref="givenName" />
<Dependency ref="surname" />
<DisplayName xml:lang="en">Display name</DisplayName>
<DisplayName xml:lang="it">Nome visualizzato</DisplayName>
<DisplayDescription xml:lang="en">Preferred name of a person to be used when displaying entries</DisplayDescription>
<DisplayDescription xml:lang="it">Nome che una persona preferisce visualizzare</DisplayDescription>
<AttributeEncoder xsi:type="SAML2String" name="urn:oid:2.16.840.1.113730.3.1.241" friendlyName="displayName" encodeType="false" />
<Script>
<![CDATA[
logger = Java.type("org.slf4j.LoggerFactory").getLogger("net.shibboleth.idp.attribute.resolver.displayNameBuilder");
valueType = Java.type("net.shibboleth.idp.attribute.StringAttributeValue");
// This implementation composes the value of the attribute displayName
// from the values of the attributes givenName and surname.
// check existance of commonName attribute and use it to generate displayName attribute
if (commonName != null && commonName.getValues().size() > 0) {
cn = commonName.getValues().get(0);
} else {
cn = null;
}
// compose value from givenName and surname
// check whether givenName and surname exist
if (givenName != null && givenName.getValues().size() > 0) {
gn = givenName.getValues().get(0);
} else {
gn = null;
}
if (surname != null && surname.getValues().size() > 0) {
sn = surname.getValues().get(0);
} else {
sn = null;
}
if (typeof displayName == 'undefined' || displayName.getValues().size() < 1) {
logger.info("No displayName in LDAP found, creating one");
if (cn != null) {
displayName.addValue(new valueType(cn));
logger.info('displayName final value: ' + displayName.getValues().get(0));
} else if (sn != null && gn != null) {
displayName.addValue(new valueType(gn + ' ' + sn));
logger.info('displayName final value: ' + displayName.getValues().get(0));
} else if (sn != null) {
displayName.addValue(new valueType(sn));
logger.info('displayName final value: ' + displayName.getValues().get(0));
} else if (gn != null) {
displayName.addValue(new valueType(gn));
logger.info('displayName final value: ' + displayName.getValues().get(0));
}
} else {
logger.info('displayName had value: ' + displayName.getValues().get(0));
}
]]>
</Script>
</AttributeDefinition>
<AttributeDefinition xsi:type="Simple" id="schacHomeOrganizationType" sourceAttributeID="schacHomeOrganizationType">
<Dependency ref="staticAttributes" />
<DisplayName xml:lang="en">Home organization type (international)</DisplayName>
<DisplayName xml:lang="it">Tipo dell'organizzazione di appartenenza (internazionale)</DisplayName>
<DisplayDescription xml:lang="en">Home Organization Type: Type of a Home Organization</DisplayDescription>
<DisplayDescription xml:lang="it">Tipo dell'organizzazione di appartenenza</DisplayDescription>
<AttributeEncoder xsi:type="SAML2String" name="urn:oid:1.3.6.1.4.1.25178.1.2.10" friendlyName="schacHomeOrganizationType" encodeType="false" />
</AttributeDefinition>
<!-- ========================================== -->
<!-- Data Connectors -->
<!-- ========================================== -->
<!-- LDAP Connector -->
<DataConnector id="myLDAP" xsi:type="LDAPDirectory"
ldapURL="%{idp.attribute.resolver.LDAP.ldapURL}"
baseDN="%{idp.attribute.resolver.LDAP.baseDN}"
principal="%{idp.attribute.resolver.LDAP.bindDN}"
principalCredential="%{idp.attribute.resolver.LDAP.bindDNCredential}"
useStartTLS="%{idp.attribute.resolver.LDAP.useStartTLS:true}"
trustFile="%{idp.attribute.resolver.LDAP.trustCertificates}">
<FilterTemplate>
<![CDATA[
%{idp.attribute.resolver.LDAP.searchFilter}
]]>
</FilterTemplate>
<ReturnAttributes>%{idp.attribute.resolver.LDAP.returnAttributes}</ReturnAttributes>
</DataConnector>
<!-- Data Connector for eduPersonTargetedID -->
<DataConnector id="myStoredId" xsi:type="StoredId"
generatedAttributeID="persistentID"
sourceAttributeID="%{idp.persistentId.sourceAttribute}"
salt="%{idp.persistentId.salt}"
queryTimeout="0">
<Dependency ref="%{idp.persistentId.sourceAttribute}"/>
<BeanManagedConnection>MyDataSource</BeanManagedConnection>
</DataConnector>
<DataConnector id="staticAttributes" xsi:type="Static">
<Attribute id="schacHomeOrganization">
<Value>%{idp.scope}</Value>
</Attribute>
<Attribute id="schacHomeOrganizationType">
<Value>urn:schac:homeOrganizationType:int:university</Value>
</Attribute>
</DataConnector>
</AttributeResolver>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment