From 5e13abc92cbbe7aaf242f70e4708e67931ca4987 Mon Sep 17 00:00:00 2001 From: root Date: Wed, 31 Mar 2021 15:19:03 +0000 Subject: [PATCH] update idp config to 4.1.0 --- .../shibboleth-idp/conf/access-control.xml | 2 +- .../shibboleth-idp/conf/attribute-filter.xml | 111 ++++++++++- .../conf/attribute-resolver.xml | 107 ++++++++--- .../idp/shibboleth-idp/conf/idp.properties | 174 +++++++++++------- .../idp/shibboleth-idp/conf/ldap.properties | 59 +++--- Workbench/idp/shibboleth-idp/conf/logback.xml | 27 ++- .../conf/metadata-providers.xml | 149 ++++++++------- .../idp/shibboleth-idp/conf/relying-party.xml | 26 ++- .../idp/shibboleth-idp/conf/services.xml | 16 +- .../credentials/secrets.properties | 13 ++ .../edit-webapp/css/consent.css | 151 +++++++++++++++ .../shibboleth-idp/edit-webapp/css/logout.css | 18 ++ .../shibboleth-idp/edit-webapp/css/main.css | 166 +++++++++++++++++ .../edit-webapp/images/dummylogo-mobile.png | Bin 0 -> 8208 bytes .../edit-webapp/images/dummylogo.png | Bin 0 -> 13742 bytes .../edit-webapp/images/failure-32x32.png | Bin 0 -> 2580 bytes .../edit-webapp/images/success-32x32.png | Bin 0 -> 2448 bytes .../webproxy/container_files/httpd/index.html | 2 +- 18 files changed, 789 insertions(+), 232 deletions(-) create mode 100644 Workbench/idp/shibboleth-idp/credentials/secrets.properties create mode 100644 Workbench/idp/shibboleth-idp/edit-webapp/css/consent.css create mode 100644 Workbench/idp/shibboleth-idp/edit-webapp/css/logout.css create mode 100644 Workbench/idp/shibboleth-idp/edit-webapp/css/main.css create mode 100644 Workbench/idp/shibboleth-idp/edit-webapp/images/dummylogo-mobile.png create mode 100644 Workbench/idp/shibboleth-idp/edit-webapp/images/dummylogo.png create mode 100644 Workbench/idp/shibboleth-idp/edit-webapp/images/failure-32x32.png create mode 100644 Workbench/idp/shibboleth-idp/edit-webapp/images/success-32x32.png diff --git a/Workbench/idp/shibboleth-idp/conf/access-control.xml b/Workbench/idp/shibboleth-idp/conf/access-control.xml index e8cc5fb..1399b0d 100644 --- a/Workbench/idp/shibboleth-idp/conf/access-control.xml +++ b/Workbench/idp/shibboleth-idp/conf/access-control.xml @@ -34,7 +34,7 @@ - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + @@ -25,7 +115,7 @@ - + @@ -37,15 +127,15 @@ - - + + - + - - - + + + - - + + + diff --git a/Workbench/idp/shibboleth-idp/conf/attribute-resolver.xml b/Workbench/idp/shibboleth-idp/conf/attribute-resolver.xml index cd2fb55..a3f3451 100644 --- a/Workbench/idp/shibboleth-idp/conf/attribute-resolver.xml +++ b/Workbench/idp/shibboleth-idp/conf/attribute-resolver.xml @@ -1,4 +1,14 @@ + + @@ -24,55 +35,91 @@ - - - + + + + + + + - - - - - + + useStartTLS="%{idp.attribute.resolver.LDAP.useStartTLS:true}" + connectTimeout="%{idp.attribute.resolver.LDAP.connectTimeout}" + responseTimeout="%{idp.attribute.resolver.LDAP.responseTimeout}" + connectionStrategy="%{idp.attribute.resolver.LDAP.connectionStrategy}" + noResultIsError="true" + multipleResultsIsError="true" + excludeResolutionPhases="c14n/attribute" + exportAttributes="mail displayName sn givenName departmentNumber employeeNumber eduPersonEntitlement eduPersonAssurance"> + + + + + diff --git a/Workbench/idp/shibboleth-idp/conf/idp.properties b/Workbench/idp/shibboleth-idp/conf/idp.properties index 9a7e6fa..1710fb6 100644 --- a/Workbench/idp/shibboleth-idp/conf/idp.properties +++ b/Workbench/idp/shibboleth-idp/conf/idp.properties @@ -1,18 +1,47 @@ -# Load any additional property resources from a comma-delimited list -idp.additionalProperties= /conf/ldap.properties, /conf/saml-nameid.properties, /conf/services.properties +# Auto-load all files matching conf/**/*.properties +# Disable if you want to manually maintain a list of sources. +idp.searchForProperties=true + +# Load any "outside-tree" property sources from a comma-delimited list +idp.additionalProperties=/credentials/secrets.properties + +# In most cases (and unless noted in the surrounding comments) the +# commented settings in the distributed files document default behavior. +# Uncomment them and change the value to change functionality. +# +# Uncommented properties are either required or ship non-defaulted. # Set the entityID of the IdP -idp.entityID= https://idptestbed/idp/shibboleth +idp.entityID=https://idptestbed/idp/shibboleth + +# Set the file path which backs the IdP's own metadata publishing endpoint at /shibboleth. +# Set to empty value to disable and return a 404. +#idp.entityID.metadataFile=%{idp.home}/metadata/idp-metadata.xml # Set the scope used in the attribute resolver for scoped attributes -idp.scope= example.org +idp.scope=example.org # General cookie properties (maxAge only applies to persistent cookies) -#idp.cookie.secure = false +#idp.cookie.secure = true #idp.cookie.httpOnly = true #idp.cookie.domain = #idp.cookie.path = #idp.cookie.maxAge = 31536000 +# These control operation of the SameSite filter, which is off by default. +#idp.cookie.sameSite = None +#idp.cookie.sameSiteCondition = shibboleth.Conditions.FALSE + +# Enable cross-site request forgery mitigation for views. +idp.csrf.enabled=true +# Name of the HTTP parameter that stores the CSRF token. +#idp.csrf.token.parameter = csrf_token + +# HSTS/CSP response headers +#idp.hsts = max-age=0 +# X-Frame-Options value, set to DENY or SAMEORIGIN to block framing +#idp.frameoptions = DENY +# Content-Security-Policy value, set to match X-Frame-Options default +#idp.csp = frame-ancestors 'none'; # Set the location of user-supplied web flow definitions #idp.webflows = %{idp.home}/flows @@ -21,38 +50,44 @@ idp.scope= example.org #idp.views = %{idp.home}/views # Settings for internal AES encryption key +#idp.sealer.keyStrategy = shibboleth.DataSealerKeyStrategy #idp.sealer.storeType = JCEKS #idp.sealer.updateInterval = PT15M #idp.sealer.aliasBase = secret -idp.sealer.storeResource= %{idp.home}/credentials/sealer.jks -idp.sealer.versionResource= %{idp.home}/credentials/sealer.kver -idp.sealer.storePassword= password -idp.sealer.keyPassword= password +idp.sealer.storeResource=%{idp.home}/credentials/sealer.jks +idp.sealer.versionResource=%{idp.home}/credentials/sealer.kver # Settings for public/private signing and encryption key(s) # During decryption key rollover, point the ".2" properties at a second # keypair, uncomment in credentials.xml, then publish it in your metadata. -idp.signing.key= %{idp.home}/credentials/idp-signing.key -idp.signing.cert= %{idp.home}/credentials/idp-signing.crt -idp.encryption.key= %{idp.home}/credentials/idp-encryption.key -idp.encryption.cert= %{idp.home}/credentials/idp-encryption.crt +idp.signing.key=%{idp.home}/credentials/idp-signing.key +idp.signing.cert=%{idp.home}/credentials/idp-signing.crt +idp.encryption.key=%{idp.home}/credentials/idp-encryption.key +idp.encryption.cert=%{idp.home}/credentials/idp-encryption.crt #idp.encryption.key.2 = %{idp.home}/credentials/idp-encryption-old.key #idp.encryption.cert.2 = %{idp.home}/credentials/idp-encryption-old.crt # Sets the bean ID to use as a default security configuration set #idp.security.config = shibboleth.DefaultSecurityConfiguration -# To default to SHA-1, set to shibboleth.SigningConfiguration.SHA1 +# To downgrade to SHA-1, set to shibboleth.SigningConfiguration.SHA1 #idp.signing.config = shibboleth.SigningConfiguration.SHA256 +# The new install default for encryption is now AES-GCM. +idp.encryption.config=shibboleth.EncryptionConfiguration.GCM + +# Sets the default strategy for key agreement key wrap usage for credentials from metadata, +# if not otherwise configured on the security configuration +#idp.encryption.keyagreement.metadata.defaultUseKeyWrap = Default + # Configures trust evaluation of keys used by services at runtime -# Defaults to supporting both explicit key and PKIX using SAML metadata. -#idp.trust.signatures = shibboleth.ChainingSignatureTrustEngine -# To pick only one set to one of: -# shibboleth.ExplicitKeySignatureTrustEngine, shibboleth.PKIXSignatureTrustEngine -#idp.trust.certificates = shibboleth.ChainingX509TrustEngine -# To pick only one set to one of: -# shibboleth.ExplicitKeyX509TrustEngine, shibboleth.PKIXX509TrustEngine +# Internal default is Chaining, overriden for new installs +idp.trust.signatures=shibboleth.ExplicitKeySignatureTrustEngine +# Other options: +# shibboleth.ChainingSignatureTrustEngine, shibboleth.PKIXSignatureTrustEngine +idp.trust.certificates=shibboleth.ExplicitKeyX509TrustEngine +# Other options: +# shibboleth.ChainingX509TrustEngine, shibboleth.PKIXX509TrustEngine # If true, encryption will happen whenever a key to use can be located, but # failure to encrypt won't result in request failure. @@ -60,7 +95,7 @@ idp.encryption.cert= %{idp.home}/credentials/idp-encryption.crt # Configuration of client- and server-side storage plugins #idp.storage.cleanupInterval = PT10M -#idp.storage.htmlLocalStorage = false +idp.storage.htmlLocalStorage=true # Set to true to expose more detailed errors in responses to SPs #idp.errors.detailed = false @@ -78,7 +113,6 @@ idp.encryption.cert= %{idp.home}/credentials/idp-encryption.crt # Set to "shibboleth.StorageService" for server-side storage of user sessions #idp.session.StorageService = shibboleth.ClientSessionStorageService -idp.session.StorageService = shibboleth.StorageService # Size of session IDs #idp.session.idSize = 32 @@ -91,42 +125,29 @@ idp.session.StorageService = shibboleth.StorageService # Tolerate storage-related errors #idp.session.maskStorageFailure = false # Track information about SPs logged into -idp.session.trackSPSessions = true +idp.session.trackSPSessions=true # Support lookup by SP for SAML logout -idp.session.secondaryServiceIndex = true +idp.session.secondaryServiceIndex=true # Length of time to track SP sessions #idp.session.defaultSPlifetime = PT2H -# Regular expression matching login flows to enable, e.g. IPAddress|Password -idp.authn.flows= Password - -# Regular expression of forced "initial" methods when no session exists, -# usually in conjunction with the idp.authn.resolveAttribute property below. -#idp.authn.flows.initial = Password - -# Set to an attribute ID to resolve prior to selecting authentication flows; -# its values are used to filter the flows to allow. -#idp.authn.resolveAttribute = eduPersonAssurance - -# Default lifetime and timeout of various authentication methods -#idp.authn.defaultLifetime = PT60M -#idp.authn.defaultTimeout = PT30M - -# Whether to prioritize "active" results when an SP requests more than -# one possible matching login method (V2 behavior was to favor them) -#idp.authn.favorSSO = true - -# Whether to fail requests when a user identity after authentication -# doesn't match the identity in a pre-existing session. -#idp.authn.identitySwitchIsError = false - # Set to "shibboleth.StorageService" or custom bean for alternate storage of consent #idp.consent.StorageService = shibboleth.ClientPersistentStorageService +# Default consent auditing formats +#idp.consent.terms-of-use.auditFormat = %T|%SP|%e|%u|%CCI|%CCV|%CCA +#idp.consent.attribute-release.auditFormat = %T|%SP|%e|%u|%CCI|%CCV|%CCA + # Set to "shibboleth.consent.AttributeConsentStorageKey" to use an attribute # to key user consent storage records (and set the attribute name) -#idp.consent.userStorageKey = shibboleth.consent.PrincipalConsentStorageKey -#idp.consent.userStorageKeyAttribute = uid +#idp.consent.attribute-release.userStorageKey = shibboleth.consent.PrincipalConsentStorageKey +#idp.consent.attribute-release.userStorageKeyAttribute = uid +#idp.consent.terms-of-use.userStorageKey = shibboleth.consent.PrincipalConsentStorageKey +#idp.consent.terms-of-use.userStorageKeyAttribute = uid + +# Suffix of message property used as value of consent storage records when idp.consent.compareValues is true. +# Defaults to text displayed to the user. +#idp.consent.terms-of-use.consentValueMessageCodeSuffix = .text # Flags controlling how built-in attribute consent feature operates #idp.consent.allowDoNotRemember = true @@ -141,21 +162,36 @@ idp.authn.flows= Password #idp.consent.expandedMaxStoredRecords = 0 # Time in milliseconds to expire consent storage records. -#idp.consent.storageRecordLifetime = P1Y +# Leave commented out for the default of infinite +#idp.consent.storageRecordLifetime = + +# Path to use with External interceptor flow +#idp.intercept.External.externalPath = contextRelative:intercept.jsp + +# Policies to use with Impersonate interceptor flow +#idp.impersonate.generalPolicy = GeneralImpersonationPolicy +#idp.impersonate.specificPolicy = SpecificImpersonationPolicy + +# Picks outbound bindings more sensibly than based on metadata order +idp.bindings.inMetadataOrder=false # Whether to lookup metadata, etc. for every SP involved in a logout # for use by user interface logic; adds overhead so off by default. #idp.logout.elaboration = false -# Whether to require logout requests be signed/authenticated. +# Whether to require logout requests/responses be signed/authenticated. #idp.logout.authenticated = true +# Bean to determine whether user should be allowed to cancel logout +#idp.logout.promptUser=shibboleth.Conditions.FALSE + # Message freshness and replay cache tuning #idp.policy.messageLifetime = PT3M #idp.policy.clockSkew = PT3M # Set to custom bean for alternate storage of replay cache #idp.replayCache.StorageService = shibboleth.StorageService +#idp.replayCache.strict = true # Toggles whether to allow outbound messages via SAML artifact #idp.artifact.enabled = true @@ -166,33 +202,33 @@ idp.authn.flows= Password # Set to custom bean for alternate storage of artifact map state #idp.artifact.StorageService = shibboleth.StorageService -# Name of access control policy for various admin flows -idp.status.accessPolicy= AccessByIPAddress -idp.resolvertest.accessPolicy= AccessByIPAddress -idp.reload.accessPolicy= AccessByIPAddress - # Comma-delimited languages to use if not match can be found with the # browser-supported languages, defaults to an empty list. -idp.ui.fallbackLanguages= en,fr,de +idp.ui.fallbackLanguages=en,fr,de -# Storage service used by CAS protocol +# Storage service used by CAS protocol for chained proxy-granting tickets +# and when using server-managed "simple" TicketService. # Defaults to shibboleth.StorageService (in-memory) # MUST be server-side storage (e.g. in-memory, memcached, database) -# NOTE that idp.session.StorageService requires server-side storage -# when CAS protocol is enabled -idp.cas.StorageService=shibboleth.StorageService +#idp.cas.StorageService=shibboleth.StorageService # CAS service registry implementation class #idp.cas.serviceRegistryClass=net.shibboleth.idp.cas.service.PatternServiceRegistry -# Profile flows in which the ProfileRequestContext should be exposed -# in servlet request under the key "opensamlProfileRequestContext" -#idp.profile.exposeProfileRequestContextInServletRequest = SAML2/POST/SSO,SAML2/Redirect/SSO +# If true, CAS services provisioned with SAML metadata are identified via entityID +#idp.cas.relyingPartyIdFromMetadata=false -# F-TICKS auditing - set salt to include hashed username -#idp.fticks.federation=MyFederation -#idp.fticks.algorithm=SHA-256 -#idp.fticks.salt=somethingsecret +# F-TICKS auditing - set a salt to include hashed username +#idp.fticks.federation = MyFederation +#idp.fticks.condition = MyFTICKSCondition +#idp.fticks.algorithm = SHA-256 +#idp.fticks.salt = somethingsecret +#idp.fticks.loghost = localhost +#idp.fticks.logport = 514 + +# Set false if you want SAML bindings "spelled out" in audit log +idp.audit.shortenBindings=true #custom/added idp.loglevel.messages=INFO + diff --git a/Workbench/idp/shibboleth-idp/conf/ldap.properties b/Workbench/idp/shibboleth-idp/conf/ldap.properties index 726f145..57f1296 100644 --- a/Workbench/idp/shibboleth-idp/conf/ldap.properties +++ b/Workbench/idp/shibboleth-idp/conf/ldap.properties @@ -1,58 +1,69 @@ # LDAP authentication configuration, see authn/ldap-authn-config.xml +# Note, this doesn't apply to the use of JAAS ## Authenticator strategy, either anonSearchAuthenticator, bindSearchAuthenticator, directAuthenticator, adAuthenticator #idp.authn.LDAP.authenticator = anonSearchAuthenticator ## Connection properties ## -idp.authn.LDAP.ldapURL = ldap://directory:389 +idp.authn.LDAP.ldapURL=ldap://directory:389 idp.authn.LDAP.useStartTLS = false idp.authn.LDAP.useSSL = false -#idp.authn.LDAP.connectTimeout = 3000 +# Time in milliseconds that connects will block +#idp.authn.LDAP.connectTimeout = PT3S +# Time in milliseconds to wait for responses +#idp.authn.LDAP.responseTimeout = PT3S +# Connection strategy to use when multiple URLs are supplied, either ACTIVE_PASSIVE, ROUND_ROBIN, RANDOM +#idp.authn.LDAP.connectionStrategy = ACTIVE_PASSIVE ## SSL configuration, either jvmTrust, certificateTrust, or keyStoreTrust #idp.authn.LDAP.sslConfig = certificateTrust ## If using certificateTrust above, set to the trusted certificate's path -idp.authn.LDAP.trustCertificates = %{idp.home}/credentials/ldap-server.crt +idp.authn.LDAP.trustCertificates=%{idp.home}/credentials/ldap-server.crt ## If using keyStoreTrust above, set to the truststore path -idp.authn.LDAP.trustStore = %{idp.home}/credentials/ldap-server.truststore +idp.authn.LDAP.trustStore=%{idp.home}/credentials/ldap-server.truststore ## Return attributes during authentication -## NOTE: this is not used during attribute resolution; configure that directly in the -## attribute-resolver.xml configuration via a DataConnector's element -idp.authn.LDAP.returnAttributes = cn,businessCategory,mail +idp.authn.LDAP.returnAttributes=passwordExpirationTime,loginGraceRemaining,cn,mail ## DN resolution properties ## # Search DN resolution, used by anonSearchAuthenticator, bindSearchAuthenticator # for AD: CN=Users,DC=example,DC=org -idp.authn.LDAP.baseDN = ou=people,dc=internet2,dc=edu +idp.authn.LDAP.baseDN=ou=people,dc=internet2,dc=edu #idp.authn.LDAP.subtreeSearch = false -idp.authn.LDAP.userFilter = (uid={user}) +idp.authn.LDAP.userFilter=(uid={user}) # bind search configuration # for AD: idp.authn.LDAP.bindDN=adminuser@domain.com -idp.authn.LDAP.bindDN = cn=admin,dc=internet2,dc=edu -idp.authn.LDAP.bindDNCredential = password +idp.authn.LDAP.bindDN=cn=admin,dc=internet2,dc=edu # Format DN resolution, used by directAuthenticator, adAuthenticator # for AD use idp.authn.LDAP.dnFormat=%s@domain.com -idp.authn.LDAP.dnFormat = uid=%s,ou=people,dc=internet2,dc=edu +idp.authn.LDAP.dnFormat=uid=%s,ou=people,dc=example,dc=org + +# pool passivator, either none, bind or anonymousBind +#idp.authn.LDAP.bindPoolPassivator = none # LDAP attribute configuration, see attribute-resolver.xml -idp.attribute.resolver.LDAP.ldapURL = %{idp.authn.LDAP.ldapURL} -idp.attribute.resolver.LDAP.baseDN = %{idp.authn.LDAP.baseDN} -idp.attribute.resolver.LDAP.bindDN = %{idp.authn.LDAP.bindDN} -idp.attribute.resolver.LDAP.bindDNCredential = %{idp.authn.LDAP.bindDNCredential} -idp.attribute.resolver.LDAP.useStartTLS = %{idp.authn.LDAP.useStartTLS:true} -idp.attribute.resolver.LDAP.trustCertificates = %{idp.authn.LDAP.trustCertificates} -idp.attribute.resolver.LDAP.searchFilter = (uid=$requestContext.principalName) +# Note, this likely won't apply to the use of legacy V2 resolver configurations +idp.attribute.resolver.LDAP.ldapURL=%{idp.authn.LDAP.ldapURL} +idp.attribute.resolver.LDAP.connectTimeout=%{idp.authn.LDAP.connectTimeout:PT3S} +idp.attribute.resolver.LDAP.responseTimeout=%{idp.authn.LDAP.responseTimeout:PT3S} +idp.attribute.resolver.LDAP.connectionStrategy=%{idp.authn.LDAP.connectionStrategy:ACTIVE_PASSIVE} +idp.attribute.resolver.LDAP.baseDN=%{idp.authn.LDAP.baseDN:undefined} +idp.attribute.resolver.LDAP.bindDN=%{idp.authn.LDAP.bindDN:undefined} +idp.attribute.resolver.LDAP.useStartTLS=%{idp.authn.LDAP.useStartTLS:true} +idp.attribute.resolver.LDAP.trustCertificates=%{idp.authn.LDAP.trustCertificates:undefined} +idp.attribute.resolver.LDAP.searchFilter=(uid=$resolutionContext.principal) # LDAP pool configuration, used for both authn and DN resolution #idp.pool.LDAP.minSize = 3 #idp.pool.LDAP.maxSize = 10 #idp.pool.LDAP.validateOnCheckout = false #idp.pool.LDAP.validatePeriodically = true -#idp.pool.LDAP.validatePeriod = 300 -#idp.pool.LDAP.prunePeriod = 300 -#idp.pool.LDAP.idleTime = 600 -#idp.pool.LDAP.blockWaitTime = 3000 -#idp.pool.LDAP.failFastInitialize = false +#idp.pool.LDAP.validatePeriod = PT5M +#idp.pool.LDAP.validateDN = +#idp.pool.LDAP.validateFilter = (objectClass=*) +#idp.pool.LDAP.prunePeriod = PT5M +#idp.pool.LDAP.idleTime = PT10M +#idp.pool.LDAP.blockWaitTime = PT3S + diff --git a/Workbench/idp/shibboleth-idp/conf/logback.xml b/Workbench/idp/shibboleth-idp/conf/logback.xml index 817de02..25afcf5 100644 --- a/Workbench/idp/shibboleth-idp/conf/logback.xml +++ b/Workbench/idp/shibboleth-idp/conf/logback.xml @@ -14,7 +14,7 @@ - + @@ -71,9 +71,13 @@ - + /tmp/logidp-process + + ${idp.logfiles}/idp-process-%d{yyyy-MM-dd}.log.gz + ${idp.loghistory} + UTF-8 @@ -98,7 +102,7 @@ 0 - + WARN @@ -106,6 +110,10 @@ /tmp/logidp-warn + + ${idp.logfiles}/idp-warn-%d{yyyy-MM-dd}.log.gz + ${idp.loghistory} + UTF-8 @@ -126,9 +134,13 @@ - + /tmp/logidp-audit + + ${idp.logfiles}/idp-audit-%d{yyyy-MM-dd}.log.gz + ${idp.loghistory} + UTF-8 @@ -137,9 +149,13 @@ - + /tmp/logidp-consent-audit + + ${idp.logfiles}/idp-consent-audit-%d{yyyy-MM-dd}.log.gz + ${idp.loghistory} + UTF-8 @@ -173,3 +189,4 @@ + diff --git a/Workbench/idp/shibboleth-idp/conf/metadata-providers.xml b/Workbench/idp/shibboleth-idp/conf/metadata-providers.xml index c1f9f62..4126c67 100644 --- a/Workbench/idp/shibboleth-idp/conf/metadata-providers.xml +++ b/Workbench/idp/shibboleth-idp/conf/metadata-providers.xml @@ -1,92 +1,103 @@ - - - - - - - - - - - - - - + urn:oasis:names:tc:SAML:2.0:assertion http://docs.oasis-open.org/security/saml/v2.0/saml-schema-assertion-2.0.xsd + urn:oasis:names:tc:SAML:2.0:metadata http://docs.oasis-open.org/security/saml/v2.0/saml-schema-metadata-2.0.xsd + urn:oasis:names:tc:SAML:metadata:algsupport http://docs.oasis-open.org/security/saml/Post2.0/sstc-saml-metadata-algsupport-v1.0.xsd + http://www.w3.org/2000/09/xmldsig# http://www.w3.org/TR/2002/REC-xmldsig-core-20020212/xmldsig-core-schema.xsd + http://www.w3.org/2009/xmldsig11# http://www.w3.org/TR/2013/REC-xmldsig-core1-20130411/xmldsig11-schema.xsd + http://www.w3.org/2001/04/xmlenc# http://www.w3.org/TR/xmlenc-core/xenc-schema.xsd + http://www.w3.org/2009/xmlenc11# http://www.w3.org/TR/2013/REC-xmlenc-core1-20130411/xenc-schema-11.xsd" + sortKey="1"> - - - - - - - - - - + + + + + + + + + + + + + + + - + + + + + + + - --> - - + diff --git a/Workbench/idp/shibboleth-idp/conf/relying-party.xml b/Workbench/idp/shibboleth-idp/conf/relying-party.xml index 19ca696..44af797 100644 --- a/Workbench/idp/shibboleth-idp/conf/relying-party.xml +++ b/Workbench/idp/shibboleth-idp/conf/relying-party.xml @@ -27,21 +27,17 @@ - + - - + - - + + + @@ -72,4 +77,5 @@ - \ No newline at end of file + + diff --git a/Workbench/idp/shibboleth-idp/conf/services.xml b/Workbench/idp/shibboleth-idp/conf/services.xml index e5cceb5..714ed33 100644 --- a/Workbench/idp/shibboleth-idp/conf/services.xml +++ b/Workbench/idp/shibboleth-idp/conf/services.xml @@ -11,17 +11,14 @@ - %{idp.home}/conf/relying-party.xml %{idp.home}/conf/credentials.xml - %{idp.home}/system/conf/relying-party-system.xml %{idp.home}/conf/metadata-providers.xml - %{idp.home}/conf/generated/shibui-metadata-providers.xml - %{idp.home}/system/conf/metadata-providers-system.xml + %{idp.home}/conf/generated/shibui-metadata-providers.xml @@ -34,7 +31,6 @@ --> %{idp.home}/conf/attribute-registry.xml - %{idp.home}/system/conf/attribute-registry-system.xml %{idp.home}/conf/attributes/default-rules.xml %{idp.home}/conf/attribute-resolver.xml @@ -45,16 +41,10 @@ %{idp.home}/conf/saml-nameid.xml - %{idp.home}/system/conf/saml-nameid-system.xml %{idp.home}/conf/access-control.xml - %{idp.home}/system/conf/access-control-system.xml - - - - %{idp.home}/conf/cas-protocol.xml %{idp.home}/messages/messages - %{idp.home}/system/messages/messages - \ No newline at end of file + + diff --git a/Workbench/idp/shibboleth-idp/credentials/secrets.properties b/Workbench/idp/shibboleth-idp/credentials/secrets.properties new file mode 100644 index 0000000..913256f --- /dev/null +++ b/Workbench/idp/shibboleth-idp/credentials/secrets.properties @@ -0,0 +1,13 @@ +# This is a reserved spot for most properties containing passwords or other secrets. + +# Access to internal AES encryption key +idp.sealer.storePassword = password +idp.sealer.keyPassword = password + +# Default access to LDAP authn and attribute stores. +idp.authn.LDAP.bindDNCredential = password +idp.attribute.resolver.LDAP.bindDNCredential = %{idp.authn.LDAP.bindDNCredential:undefined} + +# Salt used to generate persistent/pairwise IDs, must be kept secret +#idp.persistentId.salt = changethistosomethingrandom + diff --git a/Workbench/idp/shibboleth-idp/edit-webapp/css/consent.css b/Workbench/idp/shibboleth-idp/edit-webapp/css/consent.css new file mode 100644 index 0000000..bab55df --- /dev/null +++ b/Workbench/idp/shibboleth-idp/edit-webapp/css/consent.css @@ -0,0 +1,151 @@ +.box { + width:600px; + margin-left: auto; + margin-right: auto; + margin-top: 50px; + background-color: white; + -webkit-box-shadow: 1px 1px 15px #999999; + -moz-box-shadow: 1px 1px 15px #999999; + box-shadow: 1px 1px 15px #999999; + -webkit-border-radius: 8px; + -moz-border-radius: 8px; + border-radius: 8px; + overflow: auto; + padding: 1.268em; +} + +body { + font-family:Verdana, Geneva, sans-serif; + font-size: 12px; +} + +h1 { + font-size: 13px; + padding-bottom: 12px; +} + +a { + color: #00247D; + text-decoration: underline; +} + +a:visited { + color: #00247D; + text-decoration: underline; +} + +a:focus, a:hover, a:active { + color: #F39800; + text-decoration: underline; +} + +#tou-content { + font-family:monospace; + width: 95%; + border: solid 1px #666; + margin: 4px; + padding: 10px; + overflow: hidden; +} + +#tou-content li{ + margin-bottom:10px; +} + +#tou-acceptance { + width: 95%; + border: solid 1px #666; + background-color: #F0F0F0; + margin: 4px; + padding: 10px; + text-align: left; + overflow: hidden; +} + +.service_name { + font-weight: bold; +} + +.service_description { + font-style: italic; +} + +.organization_name { +} + +#attributeRelease-consent { + width: 95%; + border: solid 1px #666; + background-color: #F0F0F0; + margin: 4px; + overflow: hidden; +} + +#attributeRelease { + width: 95%; + margin: 4px; + border: solid 1px black; + overflow: auto; +} + +#attributeRelease table { + border-collapse: collapse; + border: none 0px white; + width: 100%; +} + +#attributeRelease td { + padding: 3px 7px; + vertical-align: top; +} + +#attributeRelease th { + text-align: left; + font-size: 18px; + padding: 5px 7px; + background-color:#00247D; + color: white; +} + +#attributeRelease tr:nth-of-type(even) { + background-color: #E4E5E3; +} + +.federation_logo +{ + width: 50%; + float: left; + padding-top: 35px; + border: 0; +} +.organization_logo +{ + width: 50%; + float: right; + border: 0; +} + +.form-error { + padding: 0; + color: #B61601; +} + +/* Device specific styles */ +@media only screen and (max-device-width: 721px){ + .box { + width: auto; + box-shadow: none; + border-radius: 0; + -webkit-box-shadow: none; + -webkit-border-radius: 0; + -moz-box-shadow: none; + -moz-border-radius: 0; + padding: 0; + margin-top:0; + } + #tou-content, #tou-acceptance{ + /*width:87%;*/ + width:auto; + } +} + diff --git a/Workbench/idp/shibboleth-idp/edit-webapp/css/logout.css b/Workbench/idp/shibboleth-idp/edit-webapp/css/logout.css new file mode 100644 index 0000000..da91dfe --- /dev/null +++ b/Workbench/idp/shibboleth-idp/edit-webapp/css/logout.css @@ -0,0 +1,18 @@ +/* Success/Failure indicators for logout propagation. */ +li.logout { + line-height: 36px; + padding-left: 36px; +} +li.logout.success { + background: url(../images/success-32x32.png) no-repeat left center; +} +li.logout.failure { + background: url(../images/failure-32x32.png) no-repeat left center; +} +li.logout.pending{ + +} +li.logout.na { + background: url(../images/failure-32x32.png) no-repeat left center; +} + diff --git a/Workbench/idp/shibboleth-idp/edit-webapp/css/main.css b/Workbench/idp/shibboleth-idp/edit-webapp/css/main.css new file mode 100644 index 0000000..10f86c7 --- /dev/null +++ b/Workbench/idp/shibboleth-idp/edit-webapp/css/main.css @@ -0,0 +1,166 @@ +* { + margin: 0; + padding: 0; +} +header, footer, section, nav { + display: block; +} +html, body { + height: 100%; +} +body { + font-family:Verdana, Geneva, sans-serif; + font-size: 12px; + line-height: 1.5; + color: #717171; + background: #717171; +} +a:link, +a:visited { + text-decoration: none; + color: #717171; +} +img { + max-width: 100%; + margin-bottom: 12px; +} + +.wrapper { + background: #ffffff; +} + +.container { + position: relative; + left: 34%; + width: 540px; + margin-left: -270px; +} +.container-footer { + padding-top: 12px; +} +@media only screen and (max-width: 1020px) { + .container { + left: 45%; + } +} +@media only screen and (max-width: 650px) { + .container { + position: static; + margin: 0 auto; + width: 280px; + } +} + +header { + padding: 20px 0; +} + +.logo img { + border: none; +} +@media only screen and (max-width: 650px) { + .logo img { + display: none; + } + .logo { + background: url(../images/dummylogo-mobile.png) no-repeat top center; + display: block; + height: 115px; + width: 100px; + margin: 0 auto; + } +} + +.content { + padding-bottom: 80px; + overflow: hidden; +} + +.column { + float: left; +} +.column.one { + width: 50%; + margin-right: 48px; +} + +form { + width: 240px; + padding-bottom: 21px; +} +form label { /* labels are hidden */ + font-weight: bold; +} +form legend { + font-size:1.2em; + margin-bottom: 12px; +} +.form-element-wrapper { + margin-bottom: 12px; +} +.form-element { + width: 100%; + padding: 13px 12px; + border: none; + font-size: 14px; + border-radius: 4px; + -webkit-border-radius: 4px; + -moz-border-radius: 4px; +} +.form-field { + color: #B7B7B7; + border: 1px solid #B7B7B7; +} +.form-field-focus, +.form-field:focus, +input[type="text"]:focus { + color: #333333; + border-color: #333; +} +.form-button { + background: #B61601; + box-sizing: content-box; + -moz-box-sizing: content-box; + color: #ffffff; + cursor: pointer; +} +.form-button:hover { + background: #FF6400; +} +.form-error { + padding: 0; + color: #B61601; +} + +.list-help { + margin-top: 40px; /* offset padding on first anchor */ + list-style: none; +} +.list-help-item a { + display: block; + padding: 6px 0; +} +.item-marker { + color: #be0000; +} + +footer { + color: #ffffff; + font-size: 11px; + background: #717171; +} +.footer-text { + margin-bottom: 12px; +} +.footer-links a:link, +.footer-links a:visited { + color: #ffffff; + font-weight: bold; +} +.footer-links a:after { + content: "\00a0\00a0\00a0|\00a0\00a0"; +} +.footer-links a.last:after { + content: ""; +} + diff --git a/Workbench/idp/shibboleth-idp/edit-webapp/images/dummylogo-mobile.png b/Workbench/idp/shibboleth-idp/edit-webapp/images/dummylogo-mobile.png new file mode 100644 index 0000000000000000000000000000000000000000..8ba3c95a12a93606734df54750d674bee02eaa96 GIT binary patch literal 8208 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 L-jZ1QHv_zWT(g{@D_sziiBb#9|Q*$?+TTlYjE zifI5GVYdgM=&BImCN1UIFY2h=G=|56i8mbAdsj?uQsyzd(E9%t<$f163nb%EEgvr(4;XQ;F?^3W7W~NO=lcI)Jbv1KI zU;Q)6c0tN}TD;(OvAanSaSvncPHJ&(qjNKQj55ox28JRvgURc^Dy=1qk0E^D*isdH zFjh?$GW;o9DaYzjvS%#M60w_Qbp3Ta&on-d`zA6u6jPS$7PiXE%h8)(O+&oM_3k<| zQ*~-s$s~&Yw5C!m#E2G2L^zy-k9U3x>w}LqJ zq-F0zp$hU%zL!PVP+_fu4vpD#^7&5X#^;mavy|&d7Tzuwi z^%o0ctHPh`e5H8wN|FQ9zq$3^DD*b>i^>aaeYu)1(2c~5HPR={5Yyod;Ry3P^niXX zCgY|;G@Zrk&D~NJ{61&+>TOB$wuCYs!=7Uy6ZAV&?$+kFl`_QL$FMk^i_YG{PU;C( zK#$X7CMXjiTB$N6dYEBqh3APeAydv&$|@EWm(ts2vf^9fG`dR|C+}zV^SVZ8^+ZrQaj{`o^wj($ayi`m{LL zu8ip_H_|IgzRYNpp}ui7zIC(Hf;w) zIFoxH!Gb2b$;If}jg+0C&=P*Qy=KJ+*<{gfhGdh;{|by%-s=NoY$vJux?bbK(aWH7 ztG$&CxD)AhwD8<>k@dLj#MQ=aIaj4#D#BHtC8dv)@5*v7<-gMGdb<>>F(D)E}9D^vP z0{PRmR=8?GQdx+k_uj%r@*MUD?BWr_2;b2#>7>613vJh##NOs@%6JZCKR&>TQ1l|w zA3)d*>Xtio3lKQRDj60Mfzy58JI0d66E-HTp-7*pT*Ea(?Xlb`Wz>zE=aB0-;j$_0 zhb{)^hLCAo%(8t^fIoO<)kE0mDaq&-#+S6`1^I7<>$%n2tJ+2S_1iN@*+1 zn9YW4p;aOV7$)WL{O34F(l1D-o)GY2Dt|WD(_V{A>M!^&4dT;Ff1R!n@eG)87Q{~6 zta7uKw(ZqY1jO%$QO^UAEbHEY_~10~uSUwy9l{?ZM8B2P z#`mGfCywjR2+EWA%!(mR3D$8)WjaP{pR*gi9trA*=GV0%sr{Q}beYTs>1&iC*xZVJ zxYKqg&KzDytDC3K0wQts4LJq{)~Bv;sUYXtr&ismdRxfob~9;C6|`WLCp+hs($?vH z)p3NQ*xk<*zo@P z^#SU(ZvdY7%z+{56Q+trxEt2h^6v?8&p!G+_UBuU*Z2aH{08n_SI57!qwoW0(MyB( zP`LViMM&R6=H-iFNPfT8KX=O#U<^^)*jvH2khY?<;xyHs6yoDxSW|Gc&Xt7qRsO)y ztA`^8dn0%!|F@Oj-l~r_Xz6c|FTsb=8?`_bVdiHkFBXW}3(t2Q=LmZAk+k$X$#{RE zqy&P?n!_7n66;u=2_8lZBm^9xz@a{m%)W(Y*>9!o_bAOIC`*2TiqvQm0a zLd3@{V{Ex)l#LAH7y_0;v|WOCK`VDA_hN_=HT0ahF)6H)0GmbMVr-2XET@pRT9&mK zc@wvlMq*{BtHXpi)lI?RJ{M^pEK$ihB?5sMwK;s0n7 zdY%mOO8Jyrq@IO~RjM^u#?1YK8$2n*MZhmbkrY3Ovg8f*wSwNJ@Lp6c!S$*XjCS1h z{vu2{QQy4_;~cx;ZfSZu`-VB6N)1<{76s@=dR}0=jSKKn=QNJbKM?tu>&=P^0FmAT zInWaQ-%Lv3ix)lLyHKAsVG*G7R{*(4f0Ga@W){sO=*Q4PO~&ez0k1KCT+Pu272eEo zs!WQMy`ULj(reZXQADsE=NYxmrlp{NHh-FgNq?MPK4yFJL!`AIQkVnjmhahHY`)>K z{u5g9i%z5WvAuBaa?&-LLq5^=GGC+0LHgSwYwE#bi6h_gbsguUm=ZL?F2yYv zVjA2>FZ_KeQ#P{=(}|uUnLG)GP)5AV^L8wT(!Ot(E#V7!X>U3ybh_{sl*u)qa;xdodM~82 zCCC=tj>V8{Yn>0c=&jas9Pf*9?Lp77umfENX>VdK>N|yerfxjD^h4Mf&PT9#1+uJa z>}daivF z-e#FX@O!Du?N&&BmnbTz8K9tsVX1fpwzSv6gbz_F%)?@^4l~fxsrg{n+j_nN$~GSb zo5`h>8e`RhbowcF;4^6yQxH^MPy5if4B76Th)TprHlBy^`HT~=1^Y4kw9z`B@oO<{ zm8QL9&cT`T%@o(63`r;LO)3DJB^p*=cKd@x-@R934|^%U#3l7KYwE_gq-kJtC0t8( z!Pd9xBX;_8Va_0pD~(h+DWBF}GDwZxO|`?xOPeuaE;-~kMJ2*Io4UTq7sGB-NJN30Sv;! z)yj_%VIwqH72ky;8}daHTo(BR2-7?>NsYOs?qsO1L_FG=!qAdp^+Nan(=gtN#?ZY@ zQ%Rc3gLj^vV}RNt;XNmB$1x;>v^S|l7_yngUEd5vst0m;%uz6=#I_T@EWj-|ECQw1O^!)R-aZ4Z6YzWe2Q{w|)QWI5znr zL)1muHkl5?&iZuzW6CLd3q8nF>gzVSj$=qBX>VfDfTKnI&DrXGi6ZM&Cd>#bsb407 zWb|j7Pevrs$aGR;Gg9?Dgnr0wbQjo*=B`9)&36_329=8W?g<`9k*ii9p%4_&mZ(ECiNRU>v(2Y9gsG&)S_|lwiXp>4 z6-)NRGGf*Vn0H)>Y3wMCP7Rw&UL8mW*_3EQjFI*z#@mq$$CtO3ZMyi5XGpr7zDeOQ z+itMmrYBE>=o>h9IE8s(Mh4??T|0XGJgdkW9lI*F4R!8hNE)K4Pl=-{J`;^#H})bg zvHYEz1~eMXaR`=y-)$8xBNEupexMbQ&ggAPf&T~gFM2&ku^z<$0000k_v ze!{uv?%J#Nu8Zzo)w>^wR{x^#9-Ryw4i4`9XGK{}I5>FOe`9l0$24egqtMv?Z;`@(MK%9l74@Bd zPHkX%zdo2WV$HDZDIM()uAZLcnxOp+q&Z@5H?eS3;dD7~?YB2K9hUq~nk=U!c6jYJ zBW%xAEDJLfOlUe4N|vC=l~sWKfM;rXMWW!HgWS?0+q)v`yH`ZBNxwO@%Z0vJW7o>* zIF0uM_T8nEyPJiFuc&}N`+in$&B&%S^wlM2Q{MlzqE_*y zXc`KB@`hmChV-w*+-95}T5|ab>VF^8Q9w#7GoF0+20ix7`Q+ZEHxseji72Z;(xI8H zkeyZffa22Q_vHYA)u%GW##^J~lvaej^`ut5jm?1bTLIl>Yt*43d9ZTCdxGk7jj^k6 zx-ETvzjN0gn0N!;4k%_|c7h}SdqDY>4aGj>oPt(pipt3USCy7`V6O}C+UE=`?VVns zJWXiDUw2H9Z&bFF`X}T1)b!G)#Cu$Y>)B7;%v)6wh_@)XK4t^pi-q^K7DWF8S#m7# z`hZh9#&2(iVSb?PI}Qx#l5?~i`%|Ybil(Nx2xrCpkr|;zS{9n3v-F%F!)+l*#VLz{ z^4&C>VSz6<<_5VhYdS*Y+p_hfHg)W6_7T!NVaMTo6GF)rBTg2^mpHK2XO~zVW=wiG z-HwybSUPoyf3yakOUL3q8kbnL*s3!bOD1If=8zI3xu0K3wO~Tr>qDBAd6Y4;FSUIj zKH|u(UOfK{>HJ(th59v|m$PLGYG=Ic&yq7DY2`T)2hJKRsFu#;^!=;ydaPLNDt(XD>sN;rz$P>Ekg3P23PuPrAUk(!6%&AS$g+X{DDXJlkw}JWjZ}oh5=z zt2gaD28iUcfYWOD4yx**SJR#vd^9?jc#f8zM)9EpMVu?uhmq-Z7V&E4H&i)X(~r+? zJ%aZ(@yG-vz6CDN(IVZr5Fgbv82^G#Y4D{n%LJ+p5XL;P)x~$3nH20MZ>qtE3*bl>aX9iJv#f;C>@Kj%wM^~n#s%LQ?mhM`xd8ZGzxBY<5D zCtk(D$FwX*R*@Rk5=s5~U%b=A(HN2b{Wcyj@>GSFjUi$u1)e#P?drvf(Z;)W;F(m6 zo?c)1+pjoy$?+qn(F{_p1Ml1Nq&Jk^HCdSfV0J5!8~FhPOT1kyqbyk&-<^Fq**Sy9 zEY-eT4rVBgOi0Yhn%TthZzPKoj=)tBuGknz zL{O4t$(qjC9h|V@9(&}2U*QG|$K35a?l_6S$BCF#|0D4N4L?p@{lany%vZVNO6VjrCZaJ_u6He z%*2N2M#}F&^85g}cLn!WSS0NQ$+9*i@Zp%LE(y!>*c zF_UOMY5XYljPKyzDOB7DHTBk=h1MSKC7UHXnya0Ltu!^dIe&QKKP-1DlpWpYGe9&7 zE9q*I8cuwp1M$P{(ULN2Nsy*55s~rdHbcasrVa)QRS%0b;g?S(8QmLZ!+towp)&ZCPT}oVEAx(J`9QmNH6rX)X@N|BAEJ76QNSwo(0!X6J zS{sV{ve6t`A@Kd(P1gQPYWbHTM_1NHOKRCaOT4uB9gUx|PPT|RVkJJZlYs-DYnkqM zhiy?0O8qTsx7M^>M;j=_Q1_Exs-Kg9Z}qhjmT1O_&H<^M8zK>E=#h^hhZXD6z8CKO zVRS)h5yW*-?i2yuieNMvXTJBQMgHk+{qzvtmw1|`A7^cLFx2h`CzOO>jeyQ+cVyPi z<@P+m5gVecO+=smTk?S052(Z)lnYJVGU0oUxKZpL=JX7dZ&K|L&alJNK?B05rOEng zB3|bW(Kc+-vP@IQfQ?W$d#7JJ{U2$zDK1*0(Ntu!kVwi0w$Cp=({73}z;HN1p?OXY z`a*NO@q0$LlAo1GYtNWh>{#;whd4AUrxh|OW)n{3Dm))_?CjAJdS$QqWL9Ic%HCWX zDJ1wU@-368fGnzZrj)au!`R<^lo2O}&A@;M_10xtbO!m@N(lV`H`R&HL9tmF9G6)d zbvH1xPBMkq%buW#|4?+^d1}_)H1Z_&@amH9?z%U`eN^ixh)tyPWh&{<3WxdCr`N?m zDF3D!vZqX|#dHZxuK+Y@bpNEroATM?`AbT`yg|b3EW=JPv;-ct>tJ`D|-ClSvq`jGTTZ92Fks$78?asma#^^Ar zu_^88TZgn@IJ(%(zU|F|pm8mw*}K#jN_5^+stFV5Bs`~lP9#9HiK)s2egDn`)aHCV zyuUeI5aqOU5(5Z@VS%HiI*5YqX6>XhyG*fP=7yUv`2;tx7L?jS^nuD^s$&w(5SK|Y z$g$#^#7ufn-3Il$Ogg=oCi+^U2($cg%;ow5V4M3250^+2)hl{eyAS8(y>Cu1JY<;8 zNVfU&tY#nK$gl`#pvxF81BpJSiiMbzQWMTFs@h29uwTkwNXNlUalX##axCYE75{~? zt1|)Wp#5RnUps3{+XE@|r=}GeQvKI~;e744C5I^$-H0E_cJ#Sd;d@ai>vfA1Fxr`_2#f!0$29 z*x@JZ#o-;P!1xiDJ})DF3P`KmEVGK$E9QqY*dG6h!?4`IuG!K$@0HhY*K9pFww()R zHNAy2SrTnG%gky_E^w50_iwFhXThPV1H$^2QtjkFGaB=VCaG+h^F~DRx38>iRkB3) zWDbq4Y?ivQ7<;SU{+&r{0VFKxL#BrVxo3>_SX9skgU!{rpo#neRu8zQV;GdP>TEnT z3LC}SCcCx%+@QZTmidN`Z_(YY(}D#cJodPYnz8DMEzKo(CF{bgKaCjpM#I^v<6eMu zRv(h7G2P$kAZUC}FWe%3#o?tF8@h+lUArfls=+K4T9RBx@J;z9Qf;C+AM>3Lwob~_ zR$4M^nVqhizdPj-2e`553cAA~+n?gWf&6(`8U3;uAjnlIvpnw{0No&@<{V~7^ z=ORRu82-j4vtT8kmw3U8T9ILg2L-$hn2Cg+;8wc9xub&b`Pa#q;vl1oQRH&O$=kr9 z!%N%JCRFELeCOQ6ohaPfQAWnOG6akUEK*iv(ufa=d za@kCloT|>qA1tq#m?)34Iby78N^?4KGeBL2M8}sXgP^&)ZAz%hrfHJD@o{;5+MpEmJ6|2dBMB-Nz&W0PX^YDZQ*pPJm^e z_8XP^mWZjb6E7_EX75{pgWnNuwdfG=7rpLcq*UhOS!NPEFA#|yt|Rb)099Uom0J-| zUU%~$?ngZmW{+wm`f8B?s3vBh@2}g}dl$1@+WKgUiLm*Aar0=c0{0;cjKWRE4r9~- znQ$1Rgllb>*3E{WOwJRgg&>z#a}|S6AIjB@mxxCuz}cTJ$uY11V+P83Dk0H@cL0#T zOaQh~|4B3>17f^bw6nJ#mPi#yoyGHuIo7r{?8WYHzKCXw;+w)yu60$ zi_-iiV*UlDrw7gGExCI*cH~;F@<=iCdfu^fym$Hv!H)P*&|5nBcA)G=B^Qa?@Bw_l zn!dF~-lkWmqQa+tKfZ`Y2{agI7(WXB+?{t=2Wl+7nTtpm>G#>l^m*m);xqk}6#oX8 zA$}+R?f$C+2-0h&Z#ljeNxBa=>hZ?%aw!`vlk_p=boMLqT`^qQoGNMMsI`-wgh?J+ zcLF*R6;s?r`K3vJcU{iY*6~{^)MGp}MJ$=~8FSBmP3Ob;-mW$TL=s4-Azn7ucns{v z4L#0+w=_^9Gc(-PTfBd)6ZY-JGydtn?b-STgRI}rtyQ?5N3ig;S^MADmG0{~92US& zWjAA>P3GlqsiHyBLXR>)XqZOqQbkDoxRW+fl~N++OzlD8j5w4D&Pftyi0685lFP^H z&b2*-^cS|jg!pd_?=+cT(;;GK3-6JpI@tM{Cr|Z6X$5_g;LLhwrjDrnC+=uXb^Q^3 zz(~*a^D@2|IF#B3CL^uzv@=!5i`*EOC0-&}T^AiDJlpayZM?}>I8p?8Rb#lhs{Wa> zru>@zj=~EfjU0rX`{bsF1EaiS{%C%GTS`3p$DNCEcaG2W7y?Z2TC>U(lsu`?#SmA^ zBPcmrLv8x&7V6w$1ieaO<~*FRd-A*o0J&orn-A&{6~3(OZ)zTwv=ecfXRuZ%xm1$5 zaK0|!6&*AwlayR~m_bfGkwe@<@TR+;mN&G$8X8 z{x9uW9*)A~;na2?Mcb!cxSTBe@|{{iUGLH<*9TMAKjlkz6C-k?j=9Wa>tO876YoME z($2&%wrQnALSOjg^xQ&*TK;-gf4aMLB>l73+-Tiw*SU3LZdO%{V1XI#OhNLJoKgLe zEU~acstqxx$L%Edx#(o;P>63DI&@iP{RDuo0L{gfAAIay+;M94LH%~_eO21*<%<~! z6V$G(KlVhq_GKJz$&U6X#S4AE(7Dgb6^Z7Jz+0VGP-W5KF(4CkwcBX%&d zj+gM3$GITnY?AGHe3S@i6RW77eFqi2s#(D7kbLIGeWVC}8w7cq%Jg%UBJON@ww(RG z%5c9U3fGkUi5EZb4ke+?oG2KUdQhu;qb@q(>D6VW8%}h84fTE;3{rTIT}?#YZ^p2^819WDsa1)ktpL zkr@E)bV7yti8%|#XKlJ)+^TxVAL{6O%QfQ6@T9x>9R20A`Eg`#GmG|mDx8;XcDn`8wJJ@4 zJl~cLtb>!eh>p^3)jN2JkU2h@WA8#fVJ0|Ks*XdC9s{yl*2V(ZI)$lH)hUS&;T?MI zmRX7r*eg)JS&D12+3$YAAJQU{HcP0i2iva#>x3Z(SoNtxN(Zj2AOlYsg1SZ(D=hR6 zzHu~h%UUR$Z_;^9FSlFjxB|%iHy{hgE4q=mn^8A8QYG1jOJ)f_plHuGl7pXav%4P_ zYIwGaHD&I{DzE6@^W)^F>v~Kbf z5HFB#Lo4Yxp+fuJG^VH~rO&Xu8WODUL4o3#eq zfpK?^Io_>#4NnghFfxVOwSw7Lx@OgBK5C!v8Mo*2%U;quy7sPR)pLUJ(HW-yBK!ly zSCRG^0Qmnf@MA*)#e1A*T_9ua=YP<7A;y0IIdN3Rch&zQCyl}*RM}cQ)Q#GJ*e)IW z_hl3T9#7o>4?V(hjj$N5fOWn`14PqW)Y{LVGq%VJE{XuyWjcwtQ3-5LUiL=~9-rBS z#2?iq-Za}x4KohYb#yJ~#wvK2A8Hj6K^gTXCvAEc8zzB5TEIBRl$1)z2JtrAQV0Rr zy6U8<=Vlp7^)e@aV^>8>qkGt_jr~jKR@X~u!Y(p{UIuXO4KK)SIlU()W>B2$myg zSWt%4&`9zzhbYp4QP49}a)2!o%}whL%~kOYn*J&qK$Uz|P0Kg(kSRFdZ1-9Q@a_FpsUNy2Z#s*))k;H=c&3Vvz1F^<5OnZXgalw)@R0K*^E9oO7 z^KoalLb^JaxXQCpJovnb(@T6(hK)dS>_;fJ`2F*x6NqhA z*5#71VvKd2_uE<^k1(jUjQyF>$L#Z?r16`UV>xyBL`(J5)Iv==Vy)S0O8diH??XB7 z^h%>qPl#u&tiYyEAOK3a>!MrVrKL)C2ed}&(2ay>5l#Opgqae&eL;BG1|zS20e4`9 zDzI%jZ;7hwJ@6lz{8q@2vLo2r9y-dv7{}N0SMGK!i@){0WU@0lT$ti&O#yZUjK>v< z#u2;2SJe@rIB<)(k%U-wov+)34ZP>RA365D_h1;H(Gu6QDOzdd?@Da;057 zSw`e`M~<&i1Yh>jMi}v!`xHWa`V*<^Emdm;PS9B^V!r763`MDC!R-S3r)4}Yhx?z# zdUTkxM{)%UQy8g!aor@xIgvpS%G^ zy!KzQ9DXd4+e9_5X7_mKZf`9o-AJs9#eqzYa!STplDe1ci^8FjeF@UmFv4O2uOD|7 zOY6Pc`IOku8ye)a(Y?~f-_P~h+n=U1#8lq?lF?J0zBxSH>T&b?!IeWT4H;dYNW_M@t;Q_0~Sqs=}l(Bd5IsXQ_dnDn!h)d zs6Euff%wwIN@`NU#d~7V^&2xzhft(-Zn5FCz$6&%BZGIibUebQe{$b@vAeBsK^c{J zWR#c+-oH%8F`^WTL0ZA7e_Z00GH8W?S>z{06*Z~X;d!J!YVfd6W@D0l%+KHO_eC`d z=OjHI74s5aqj!S5YN)bEval7dPN$(VAzCUX4d%zW^+oj;2+q{OKW|cMrxhIfnIF)a zLZT&lCeE^JN1jyc%LU0HT9n+F2Waxo_y>#vI`KM8LKfg#@r9m2jQ9mTOLk%`NDHym zkKb=16QWdPD`mE|GPUEXM~ijE9FwcDo>(4wtyI~O_KPdA*2i{ak{AMCMgMI}fq7Nr zZ9)N&gyFgHAHEy|07k($`l-A_+gC#$!M`o=Ysng^`Hc>RO@u3m)MbEu&J3aI#mn`U z#9K^P!$RKI!0_Ks-w41qgx11(IlKp(DHdm3C*=hO0?EXH5{iu+qVQ5|_ZQ&WC1u(K ze}H5*(c`@BRNo}~%r$H@@zx`vN_MtFj;yvi9$n$%=bz6LQX0l&29U1oI zMwLEcK;nQMYD{IXdi()orNV-6a3g(HtHDtB&0- zk9kn?^3t&j7j!@k&6GyuqTEk?HV}1i61QvvHMJJ{SRxGf@T8PxAUBndNTv} z00?JDw+>3!)Nh?^$w>|)BaP<|_h%vl`vvhDOH#Mhe!G?mN{FE0yVIs_bD~uQ6-_xP zQsD+!XFS$cLQwYa!V44*S{S4Tppp3p(3n%Q;l=zN97`C|Qc%R&kfPM{VMOT-KzF(z z4-CHK8O(~fu0*q4ut>D)$bR=MuCD*4`Q%6VzBE^X{5b#Rohd)=-r`7*q*&gEWj>#% z8tgW`V9^;sw=cQ(?vr%~f44&x;MW0-N&Luxm6uF+c*E_}I4E|O-IDd*+{7N2a?iIK%dE^faiiBFqBh92sb>U*K*sqO* ze`9!d1TrE#pqb=$<3Wr3D6UrRA4BXZPmkKz+o1m?0u zKxrJ&dVU=5jEnO|7D#-{;hZV{`kL9+$x}grRdgp8*ZWQ^oKtXWjecb2m*DgnSIV+h z4^7&QG1Ohs3ij+butHwA`1WI^x-YptES?y|8eapPjuQYz_6=(Fz+Qi-6!vICOodh>ca zbeHoB`g;a4Uc0BU0@{udiRO(RThtSd;rwh|EfzZyl8jsK$AGA$gX{al*{1g6+~W5G zR@C>bl5-NfZ?zA#O^xln*?L4hwjLvv{9xtg>2G_!r)=Ci5>r=d(`I@7yCXIot*9d= zLkpeG$mG@1I`3){v^!uD+vS6hUw}^3L%&dRio8M(f7gfr*DIcDK&x68-WkYVY2$=a zK24`9v%OS4lF(ZtvB&W&CbTH&@AY3RAx;DH&iWU2GA=PDfMUuDaJrHEHcdJ^5f;)Bq(J`YQA5z6OX>agcFDd~?F?XiH$ zF@Vw2N3TeEGZTUbaMJ?y!{?AhV0{4iu)O5wWW4*@WWi8uA_&YFU{>W%A_<9RGJ)h z3<+Dg96W);W$N4vw$3XyY`QS%?=bsu?LdvZ<~dp|uGx!4UxIMoR&z0?@IA%Q4RAX?fJG2=A8l4F0Y@h%QS$V)G+!9Ue zoJavfiNEXynyxF28``f>$eUQMC3D2(QY`pQq@0!~pL-cCwht*qpM~Y{wkPny_w!)+ z7JvbMgLen?SAR}aX#Su?a+hg{4tg49E>&z*JX=V4D7XK9)gKkL(}hh*90kecMW`DFss3deuuq#asLG((gU$W@1_E5}34g^t7D=OC2?bZiStXso ztdLc=6<-{kUs6l7yM?>=lW+QQYzUwI6ZQ4`P%1$z1Yt|Ij10niWBO5@O;qADZG@ zoUrQ@k$i?5Av17n+s(B??v_?0uHoNC|e{RX}= z|1`-oP{H`}R|HmfL%hA2J6E~cYC>NMukDwJ9mjBF;u8swgB20Njbi#w$vw^2Jb0s@ zIj5$#cHSqB$Rp#P)xLUdGq-nd2Uo)m8v1slp>KU2xhw{X*1{mBKQx#vv{1e_12;JW z5MA$`Rgin}omFJuc1`q3Yh|ca416LeGEwTqO#EFL=c3UpGsokGj5=#PIYmtt3|_pE zAWoGWE2!w};leubvShc1G2PQfG!*ctkNJl+6EQ}b^?2|9df?37)|EUs9OxGbGhE4^N}B%YZffM| zCt5-6??jNK~Z{XzV z^%UJbb?%=JJ`90!hlE80w7FHU@Q>?G8Bz%J%pP8PVjorM{aznl!cU(XNCrRgyTy8x z{<1w!=I_r}FTB(WdN*OWdh3@NJ>@yk%z4blae<34-^%M`Z1!Zz0*!NN(&7|nz6*{y?pFR~3lKh$eKLOz}gy5Kz zZ^%S#qy+vyN#PyRKU}Ag>+ah^#D8MLD(QccLf!BKpRVqYE`8EJS`_*&Du z2l59~yP-J|i6$@e6$9L@cwyYAt*v)?%muT!2Sm#v!Nt?;r8P~p(>LoiiZ0S0iC`1K zEF)bP=FKs{z}Ym`_9ll;&`KUuCtA61` z%T;S(n&36CrO$GWpVL6N^tw|KYS^Wx-)yMmrSfC$9V!!Fg`$t#rH$OPz`4mG*7*v@ zXNORPv-P6&4$k^`%ZI#U46-(-YET2_d^IAS{IBfc-_Wzi&1-`nq@AjT<2{$|m^-kC z(h>J64hwxGyV>=OyviNpj(rsg*PVou`=^%uNE1j?hqt|dIfA5IBYdktCPII z&6@)lEk~!zj7SR z3J!hisT|N<6j(C1DOydqvL;*5M`~Y^!99275!Rmrk;|UZ3%GxNmW}K4KTYXUEWa8E z-|@7}AlW{spnk^U`aM`->kCgAt6&a0M%%Hs?vqk_#WtW%7`)lJ?RzhGenZb*D@gm4 z=*Z|q66@MLQtbXb*cAqBO+*; zsiX1dW;;l)p)ACvL>>S5=SuqdD6R3o4Rp{|kaup!S^pjN)jY-QEn}g_k&Wq3mpTc5 z&y}B$2|OJp+flE6n_}w+^3p{=ufI@HnJEBL@v}dM{c)z@sn_8Wl#Rmhb;V_=1;^^L z(9cJv`Rz-yf1>%xRgaU-l$PEAg))a*-%K#6j)do%0N0!j>Jaf@SDjdXhI8~kK%E$2 z*?hZ1N+=lLExnE?_i5UL-?JEsUkz042^7VDPjk%mf=Zc$!bA5a-bdO|5mc0KKFFQ_ zH|`5LL-G+~lT7+YO0d+db>29nWyy}oA+J`Et(~((x`Wn0#8GW(-3+wV!MuJA*GzF~ zN2WA;wq%t#6_NlB4F#2CPR#SicETR4eWC9yHp4W3oL~x%E?k5@{=TKCxi&5_3(HSy z-@ZI#6yAwIoy{1h-V!+M| zsEstGOyexgOuX6BTl=j5*=c($=ELtD{XFi+2*)v>tJ^kxe`>UvR=y#n+K~S5JQy~C zfeiBWUHVFg4oc-C6s{b~2WrJHKX`|!8xDQcX)rwus^mGr!fPc|1mSW=+f3;`N+wPw z9oJfxc9*>CTDqgyliLSAjZAb&mwmsF8Ke@FPH}#-9O`~){Wn|IGN=hTVa6J+keugE z2ly!yfR&bw$_MoUVk(_et3cHA48TZb@1oh;XD;)kRG#7L!+i{Of{s;OC}Viw5ZsHB znL*AT`blW=vO5i?z!#9J<09vV0E%sEH4*I^mM;nwc^wL7d_9-A3MY6LMZkj)@RhCk z-okqZye<*R|2vlisU>+T3(}OOhKYF~aBIGuY%$@4>)1()s*ogzEcvTx_Xqp(f=#@L zKb!%&y^3>0w1!$)pdJZCq@m{r+3Mx!{D(Ir_ExOMxa&`)?lR|rqvtG(>t7d#EDY=8_7>n}x&|das@VzyN%)~NP1`d#Y%S=> z?}pRuuRPQKx8;Q2j` zf`cMroV>a)vT9-Y^3sQgOi0Y$Fec|{hfv0T|qSLQNLsOYx8JjISrXzD0h zHKD5mTZ{~Jj6PiUs|c{g^@@-7!H2BPCIEc}>xMLHtFk*2I)5j-F_uVTbAbP z{+wUXwqEfG)Ke0Z??cq0rI?vKR@^YhPwo%%#tzi`gU5}Xv59wcGHBb>+OGuBn!QRB$_+>5HFxNL^2 zp<+~Sm1_C|V7d)QQtU;`q%e-I4>>U^GTp!vfidmi$;zWvoVN0iGrsS3)&H~!sn++} zs;B)*r*l6&Ky?co2JL;O|K1t6E*#S;^w*g8YN|kV*33EorBm^gA#y?Ba|Q-JW5dNL7>4B zAO(O+oO7-}WXmV6v3QMB}of%XFkKSrI;BJy>o2O*P z{V1D~=^a)&yJ~qwVibbTE6td_=o6Ga;x4z{NUk_Q>JifnBVB8nJklJ)9auNk&CEtz z2i7ywS+EaM1L+xZkLiq?z*LzGlt2iB&ESxB#qS0wL+d-?tTd9ZdcAYQ zpLPz{A@Oc$p|dD6Z!VIpy;u^XHBLJsCK3wUdT0S8Bx(GwY~oh5o2Iu$9>nhs%UK3@ zJ617AN7o5slk`Ww!%<-D55yT!tEKLrawX;Z-634d){AwhZ*?ZJCC&Soe^X02a+`+V;j3M{ zwJI#1ZJWtZ1IVnMi!>^wHZ7jSvTKH$C*DtEb8J$H1^5qDePei3%Fy(&XSg#nT?@2> zI?cFUMQ2oPOok;<{l%Xl%+W#g>z3EimUg zl(2Jc5_HcGXoK#zoibds=6$uyh7rj!InI^^Ia#R390WXX`>W{H-8sX%kx0&ZH#i7L#s(qZ<*X}Y zYcIt?e6bs&$Oz^2-<|bTms}eGd21rk(Fzx5K9+XdAk=i z^hOsXZ?5%5Eh(48`=*!vm6ZNx(`A33I_GmPzwh^Xe$V&$p7T4OlkDx~stZTLVKA7k zyBlpibVVtT=~JOI7#sT*x@dswT^(WP8%-&1JEsxEn=X=JZ>Zii0#lS1OVMD!#Ffb1rbHqq5VC* zQBHgz8)b>Lz~a$VI0}WL2w9=PdYa2uIyACFhl@l}01mf(`*!Sh5|%Fv!x6}2G7e9~ z5s4TGfdOM8MGP?}5;U8b_V9AfFqpY=LhiM?@u3RE8#pe{^Jm<;3Sj3E3bB(WsVRDeAGw zc>fcPo`wL%W$l%cGPO86?E9-E90_?duuP>rB$J>bm|v$_5>4%ASU3ldb- zPZN`gPJAw3=o7_YvXzCYC~Bd}Xq8OBuVmB`YD5+j0HZ^;vY8^arv*JT)w}P=2*as` zDY&1aDbSk$c=B1C&=?v+#HJGQ1WOD7kHHh@1QI~N10)g!HwmLwfimMHWHUs3A)U|X zQdKT^${~t`h4u-qI^rvtf>W*|wRJVIXjM^Y)l%UQ^V=7I3cqM5>x99ylig_!bbp;1 zKMt4fJ7>JJ;ILPOzClHk$HMIRS>C%~giBc|@_2bL!Xe#-cJ4?vvc;6Pcp=)7w*F-6 zD>^$l++wR^&_0LRhCVvj>8naluWJQ@!c(JX1cmjD96NEo zW01@3xg~K(ICGssN4H@qu??1DfwEl|C*j#5OcFCBaau>u@tmLe(|zjt=lmAD8F9K5 zv2w|&BUQQk_DbwFU_`H1*4Ziq+?5e~ZLHB92C}(Z8l2)Rv^JG+7dt#3WPb4hE?b9o zttm47=aAip)I7sR*Yi2MUx-btvqrGPjebPrOI_|jWKE8)z0@B`2D}GvTjopj>gRVo zYT_5H(8A>$xpkC-G>NZ(_1)3s%7%;UU+wISQ&fILj9muV*GH83fePfVMWzw>9 z7#AJVXNw{~`%m6P-l?l&QGcB8jxZcdxUqC|uOd+vxLkYTs!r4gSXEJr$H5KbX&NDG zY&sj78gLF%^8>iW5kPZ@W9wg|7jHGwkpM@#x*1PIvM?VabvdTI!D6t$xoeu#oS1fSa!D{`x8Qp(|>A`4W>noZ@t8I-NI zIT}u-W$XIu+kI!jfCa&TUcyb!o*svj+iwP zYduy+#>GfyCa+A|a(>^Z!T1Dm_2MTT!2ACkN6f9G=drHKbgM3D8j*<4mOE=^M@t% zBP~PCC4otadPeO&UPEOW(H zz;_K-QHzNkmRDxS(vz(gPs_VYZr-2pFmb=1?qG3Ko8Ve$GB3P~{BAM)W`(B5%Y|=e z8&r`7G+156uSfnHRwO?p+&h|1a|v`hl)1VrluyM$sx&aTY2Vn)yB-S6uK zmH5ZuK^F}QJkv@l_Zd~59G-fU#%Ya7ObXoGDfyVSU{OipU4y!f_sZT>{zZy^BN-yJ zM=yJQTo!c419@!N{A?{d;aWJZH@9VY2hj^T#LhD{>{e*|1m#!!y+jbZe-t@uv%t!E zVBPP}XCw>+wUdq6FWl1g;$nf+H1nPeHys<%qNKCM#tU#avcj%YHukr;e(Gr*Ti%eK zbSD3y&lYz*&_46a$AH4Vc$=N*F+{s#$63_Ab- literal 0 HcmV?d00001 diff --git a/Workbench/idp/shibboleth-idp/edit-webapp/images/success-32x32.png b/Workbench/idp/shibboleth-idp/edit-webapp/images/success-32x32.png new file mode 100644 index 0000000000000000000000000000000000000000..aa512048d8fe96fc4b37db81fc5354a80b191bdd GIT binary patch literal 2448 zcmZ{m2|QHY8^?zk%2pAglrf@DWj16PGnO$zqR6fo%P@nPJI!3pq(Tvyx4bCtL{YZ4 zNhMmeP_Gu!Sh7U2Z;2u;gi`%yq&I(W-TOKBp7T7v?|IJioO?c>o4DP{RzY^9ECd2k zu(u<*h~9888pts1yx0(k+;VY~fMlFjgFv7HnyV-1 z>9`da2+&dfK|lZn#icVvY6t|+#fiFf3g{2#(!&{S9G8HYRp3N@u^Ekk&q}~B0>aaA zJKP#zQQ(_UhA0feTow+8<5@w$I2Y39Ib1X%AgCb7#G%m~4hO|CKmn`}G}hGA6phhG z>+2&$3M6|k1N7%28EozEll+*6L}3TAXiSg>FyP{O{R4mqkbppl1O0o=t&`6DHxPq8 zmz5|#G}oVr#-cFjUqK)(_~-Kej}m)+i&40=-(X_TcWky8-`9v2RTSq41kr-`lKer6 zxjqKF35mrZF<4iu0S=4785!fz3p777oTaT<6n_w4xdK4A`F0wY5>6Kn;RYzt{hgh! zm_pqyJ-DsJ8~_OcsUB7V9_7>F3)P>Rl*oAUr}my&HoDn(NOY z3(N~Cub+N%;~&g?<3hmmSHOJZJV3k=xYTB9QIuag7J}A5IKbM$^be$n z>otqaGc8olhVlAcn0byl5RVpr%k#eN?+0hrDmpplvZ5XRaSF|4EBG4+AP}j8_9QD; zPnimjuy9u!<*$QX^!1?w&KK6hny7}^R^tgdYe|WMxCD^j79YC30haudp~btLr)YI7 zzujG@4VDX6@@nraaV6#U+B(7lVLDUQq*&!Vymy*QTc=qRdo1(go6$xO;^~39e*B;r zd$1<`mgECuL&Y>ENKsEOu6#5(KnZ?1qWKB&h*45Bj3oKj^d?~-Ki=TFnv0-dilNrx zE+oM0ses}Tf~=ZX^FGzSbg>o(p5AfvSZzqt-r?MFnLA~#Y>cfkoQbI22b+0!11y$Q zo5YP28eMGvcBA%!{EK^r4Bepz?p=&68A@7?t!x`xNffd+#QyKbqD=Lz2un=GR49F%^l{3JnVvhDN6dftf% z6C=Z{w;Pv)?c9Z5QM9LN)va+McICukgu=P9+wq(jdbZi;axHVBExAr`ulZr`Cunk| z{2|SAicL2Kunoa4xmf6dSfMQtlL+gqtkUJ?`Fm*sd6{jgc+bbu1)1fo9p~!XqbySU z7S$1;{kknFU-PoAbVGyPRW9kBz25zx?3#<*(VK1?ucaP)daB~G{H~BaWXBnei>`_< zzw&)Oc~p$xWrVx{mF0AQ`Aj60qMrNtimICPg{0w|GMYO={=Q(#gOjPc!d20|lE$WB zvC2M&t<4bv-8ucXcl(&2+b(;T=Dp z&kMF3T~QQswAyZh;r!4!jXIr>cR3R^vqkqz8B&ATYbN8NoRhfqiQWN7d+f{ZfRx!~=H`Kdk zjXgO(GUBi1y%w8~2x)aA4*K%`vbP}1v3@_`xQ z8Wk#Ad+nJN^rPp~UBIZ>AG+@vY58PH`eW^)rUJSAq*Lh~_MQ6<^n`MyB`(%lj;)i) zZrU9ctveE8cE`1cAi0(Kcx!G8U$A7&+2U2swO5e?fdj)wJOUVgh4(WantA|Ln=`*S ztvRC+?sxW{hK?36L0fKFqf_I2$YNX8ik*oCfxPE7e@!Lq$3N3%5$-!iPjk}~H1(e3JW8|mni?ect|u$@skp0p+~#p2 z4my5tS6Nh=LMbqt*|yXRvpGY3;tZD>%PDQ+v$J1;UwDrPQ92`P%L>1xf9agLLaSNx zv~E@INg5?$#8BS4!k+IiW(hZ)NpNs$Sl#i^c=fL7)VhmF61(7 z4@BH4{JPGwMQO=&{E$)~qW z&a75NaAbno>wLYT&*x@oEzE=8RUSnb lg!m33->y9S*<*Ne#$rJETbE67eUWelcome to the InCommon TAP Workbench!
Shibboleth SAML Identity Provider and Service Providers: