Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

...

IdP (Identity Provider): A web-based system that can authenticate a user on behalf of another system called SP (for Service Provider).

...

Here we discuss key items in the various configuration files; not only the items that need to be modified but also those that deserve an explanation.

Apache Configuration

Note: Apache version should be 2.4.10 or higher so that the local address request field gets populated for use in the back-end code. (see: https://bz.apache.org/bugzilla/show_bug.cgi?id=56661). If it isn't populated the back-end fails with an NPE when looking for the local address in the request.

/etc/httpd/conf.d/sp.conf

ServerName should be set to your SP host's name, for instance my-shibboleth-sp-host.net:

ServerName shrine-sso-node01.catalyst.harvard.edu

The following tells Apache to proxy all calls to URLs starting with "shrine-api" to http://127.0.0.1:8009/shrine-api/ over the AJP protocol. Therefore we need to set up Tomcat to listen for AJP traffic on port 8009 (see Tomcat Configuration below)

ProxyPass "/shrine-api/" "ajp://<YOUR_HOST>:8009/shrine-api/".   (TODO: does it really have to use <YOUR_HOST> instead of 127.0.0.1? in any case need to match line above)

The following tells Apache to use Shibboleth for authentication for any URL starting with "shrine-api":

<LocationMatch "/shrine-api/">
  AuthType shibboleth
  ShibRequestSetting requireSession 1
  Require valid-user local

The following tells Shibboleth to make the attributes it collects from the IdP available as request attributes in Tomcat. This is recommended over using the ShibUseHeaders option which sends the information as request headers. see https://shibboleth.atlassian.net/wiki/spaces/SHIB2/pages/2577072327/NativeSPApacheConfig.

  ShibUseEnvironment On

  ShibUseHeaders Off

</LocationMatch>

Shibboleth Configuration

Shibboleth consists of a Daemon plus an apache module. These must be configured for Shibboleth to intercept certain requests (see Apache Configuration above). When a request is intercepted, Shibboleth will decide whether the user (1) needs to login at the configured IdP (which will present a login form to the user), or (2) is already logged in (and Shibboleth will let the request be served as if it wasn't there to intercept it)

/etc/shibboleth/shibboleth2.xml

entityID: the ID of our Service Provider (SP)

Our current version of the Shrine application does not support the use of Request headers. However if you decide to go that way instead of using AJP and request attributes, the following paragraph is pertinent:

REMOTE_USER: how the REMOTE_USER attribute will be populated, in the form of a list of attribute names. Note that "ecommonsid" which is specific to HMS IT, comes first, so for this environment REMOTE_USER will be set to the value of "ecommonsid". Otherwise, the first attribute name from the list which matches the name of an attribute returned by the IdP will be used.

"attributePrefix" must be set to "AJP_" so that the attributes from the "attribute-map.xml" file (see below) are passed to Tomcat as request attributes (as opposed to request headers). See also server.xml on the same topic.

See: https://shibboleth.atlassian.net/wiki/spaces/SP3/pages/2067400159/JavaHowTo

See: https://stackoverflow.com/questions/63505670/apache-cant-connect-to-new-tomcat-9-ajp

<ApplicationDefaults entityID="https://shrine-sso-node01.catalyst.harvard.edu"
  signing="true"
  attributePrefix="AJP_"
>

if using request headers instead of request attributes, include the following in the ApplicationDefaults element:

REMOTE_USER="ecommonsid eppn uid persistent-id targeted-id"

Sessions configuration documentation is available at https://shibboleth.atlassian.net/wiki/spaces/SP3/pages/2065334342/Sessions

...

Shibboleth Configuration

Shibboleth consists of a Daemon plus an apache module. These must be configured for Shibboleth to intercept certain requests (see Apache Configuration above). When a request is intercepted, Shibboleth will decide whether the user (1) needs to login at the configured IdP (which will present a login form to the user), or (2) is already logged in (and Shibboleth will let the request be served as if it wasn't there to intercept it)

/etc/shibboleth/shibboleth2.xml

entityID: the ID of our Service Provider (SP)

Our current version of the Shrine application does not support the use of Request headers. However if you decide to go that way instead of using AJP and request attributes, the following paragraph is pertinent:

REMOTE_USER: how the REMOTE_USER attribute will be populated, in the form of a list of attribute names. Note that "ecommonsid" which is specific to HMS IT, comes first, so for this environment REMOTE_USER will be set to the value of "ecommonsid". Otherwise, the first attribute name from the list which matches the name of an attribute returned by the IdP will be used.

"attributePrefix" must be set to "AJP_" so that the attributes from the "attribute-map.xml" file (see below) are passed to Tomcat as request attributes (as opposed to request headers). See also server.xml on the same topic.

See: https://shibboleth.atlassian.net/wiki/spaces/SP3/pages/2067400159/JavaHowTo

See: https://stackoverflow.com/questions/63505670/apache-cant-connect-to-new-tomcat-9-ajp

<ApplicationDefaults entityID="https://shrine-sso-node01.catalyst.harvard.edu"
  signing="true"
  attributePrefix="AJP_"
>

if using request headers instead of request attributes, include the following in the ApplicationDefaults element:

REMOTE_USER="ecommonsid eppn uid persistent-id targeted-id"

Sessions configuration documentation is available at https://shibboleth.atlassian.net/wiki/spaces/SP3/pages/2065334342/Sessions

<!--
Controls session lifetimes, address checks, cookie handling, and the protocol handlers.
You MUST supply an effectively unique handlerURL value for each of your applications.
The value defaults to /Shibboleth.sso, and should be a relative path, with the SP computing
a relative value based on the virtual host. Using handlerSSL="true", the default, will force
the protocol to be https. You should also set cookieProps to "https" for SSL-only sites.
Note that while we default checkAddress to "false", this has a negative impact on the
security of your site. Stealing sessions via cookie theft is much easier with this disabled.
--> 
<Sessions lifetime="28800" timeout="3600" relayState="ss:mem"
checkAddress="true" handlerSSL="true" cookieProps="https">

The following specifies the entityID of the IdP to use for authentication. We also specify that we speak only SAML2 protocol.

            <SSO entityID="http://sso.med.harvard.edu/adfs/services/trust">
SAML2
</SSO>

When logging out, only log out of the local Shibboleth session.

<Logout>Local</Logout>

Setting the status-reporting-service URL (relative to the hostname) to "/Shibboleth.sso/Status"

<Handler type="Status" Location="/Status"/>

Setting the session diagnostic service to "/Shibboleth.sso/Session"

<Handler type="Session" Location="/Session" showAttributeValues="true"
contentType="application/json"
/>

The IdP's metadata is stored in a file called idp-metadata.xml. It should be obtained from the IdP admin/maintainer.

<MetadataProvider type="XML" validate="true" path="idp-metadata.xml"/>

The attribute-map.xml file (as set by the "path" xml attribute) will specify which attributes are extracted from the IdP's response and the name of the request headers or attributes they will be available as to the java code. More on this file later.

<AttributeExtractor type="XML" validate="true" reloadChanges="false" path="attribute-map.xml"/>

We left this and the file it points to unchanged:

<AttributeResolver type="Query" subjectMatch="true"/>
<AttributeFilter type="XML" validate="true" path="attribute-policy.xml"/>

This points to the key pair we created above:

<CredentialResolver type="File" key="/etc/shibboleth/sp-key.pem" certificate="/etc/shibboleth/sp-cert.pem"/>

We left this and the files it points to unchanged:

<SecurityPolicyProvider type="XML" validate="true" path="security-policy.xml"/>
<ProtocolProvider

The following specifies the entityID of the IdP to use for authentication. We also specify that we speak only SAML2 protocol.

            <SSO entityID="http://sso.med.harvard.edu/adfs/services/trust">
SAML2
</SSO>

When logging out, only log out of the local Shibboleth session.

<Logout>Local</Logout>

Setting the status-reporting-service URL (relative to the hostname) to "/Shibboleth.sso/Status"

<Handler type="Status" Location="/Status"/>

Setting the session diagnostic service to "/Shibboleth.sso/Session"

...

The IdP's metadata is stored in a file called idp-metadata.xml. It should be obtained from the IdP admin/maintainer.

<MetadataProvider type="XML" validate="true" reloadChanges="false" path="protocols.xml"/>

If needed, refer to shibboleth2.xml.dist

/etc/shibboleth/idp-metadata.xml

...

Get from your IdP (Probably do not (need to) distribute ours)

/etc/shibboleth/attribute-map.xml

...

IMPORTANT: you must specify at least one attribute whose id is "remoteUser". The Shrine SP code will look for a request attribute of that id to populate the user name in the code (which appears in the user account "badge" at the top-right corner of the UI). It will also be used as a key for any 3rd party supplemental info, such as the Profiles API at HMS. In the present case, the attribute which maps to remoteUser is "ecommonsId" because that is what the HMS iDP returns, along with "Email", "Firstname" and "Lastname".

<Attributes xmlns="urn:mace:shibboleth:2.0:attribute-map" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<!-- The 'name' attributes need to match exactly what your IdP sends in
its response to your (successful) AuthnRequest

E.g.
-->
<Attribute name="ecommonsId" id="remoteUser"/>
<Attribute name="Email" id="email"/>
<Attribute name="Firstname" id="firstname"/>
<Attribute name="Lastname" id="lastname"/>

</Attributes>

Apache Configuration

Note: Apache version should be 2.4.10 or higher so that the local address request field gets populated for use in the back-end code. (see: https://bz.apache.org/bugzilla/show_bug.cgi?id=56661). If it isn't populated the back-end fails with an NPE when looking for the local address in the request.

/etc/httpd/conf.d/sp.conf

ServerName should be set to your SP host's name, for instance my-shibboleth-sp-host.net:

ServerName shrine-sso-node01.catalyst.harvard.edu

The following tells Apache to proxy all calls to URLs starting with "shrine-api" to http://127.0.0.1:8009/shrine-api/ over the AJP protocol. Therefore we need to set up Tomcat to listen for AJP traffic on port 8009 (see Tomcat Configuration below)

ProxyPass "/shrine-api/" "ajp://<YOUR_HOST>:8009/shrine-api/".   (TODO: does it really have to use <YOUR_HOST> instead of 127.0.0.1? in any case need to match line above)

The following tells Apache to use Shibboleth for authentication for any URL starting with "shrine-api":

<LocationMatch "/shrine-api/">
  AuthType shibboleth
  ShibRequestSetting requireSession 1
  Require valid-user local

The following tells Shibboleth to make the attributes it collects from the IdP available as request attributes in Tomcat. This is recommended over using the ShibUseHeaders option which sends the information as request headers. see https://shibboleth.atlassian.net/wiki/spaces/SHIB2/pages/2577072327/NativeSPApacheConfig.

  ShibUseEnvironment On

  ShibUseHeaders Off

</LocationMatch>

Tomcat Configuration

/opt/shrine/tomcat/conf/server.xml

<AttributeExtractor type="XML" validate="true" reloadChanges="false" path="attribute-map.xml"/>

We left this and the file it points to unchanged:

<AttributeResolver type="Query" subjectMatch="true"/>
<AttributeFilter type="XML" validate="true" path="attribute-policy.xml"/>

This points to the key pair we created above:

<CredentialResolver type="File" key="/etc/shibboleth/sp-key.pem" certificate="/etc/shibboleth/sp-cert.pem"/>

We left this and the files it points to unchanged:

...

If needed, refer to shibboleth2.xml.dist

File idp-metadata.xml

Get from your IdP (Probably do not (need to) distribute ours)

File attribute-map.xml

IMPORTANT: you must specify at least one attribute whose id is "remoteUser". The Shrine SP code will look for a request attribute of that id to populate the user name in the code (which appears in the user account "badge" at the top-right corner of the UI). It will also be used as a key for any 3rd party supplemental info, such as the Profiles API at HMS. In the present case, the attribute which maps to remoteUser is "ecommonsId" because that is what the HMS iDP returns, along with "Email", "Firstname" and "Lastname".

...

Tomcat Configuration

Tomcat should accept requests on port 8009, but only from localhost, and redirect to the SSL port 6443.

...

<Connector protocol="org.apache.coyote.ajp.AjpNio2Protocol" 
               proxyName="shrine-sso-node01"
               enableLookups="true"
               address="0.0.0.0"
               allowedRequestAttributesPattern=".*"
               port="8009" 
               secretRequired="false"
               redirectPort="6443" />

...

SP Metadata

/var/www/html/sp-metadata.xml

The entityId attribute specifies who we are

...