I deployed OpenAM and created hosted IDP. Then I want to configure NodeJs as Service Provider and implement SSO with passport-saml. For this, I have to register my node.js application as a remote service provider.
I have two questions:
In order to register NodeJs application as a remote service provider, I must tell to OpenAM URL where metadata is located. How I can get metadata with passport-saml ?
How to configure passport-saml to work with OpenAM?
I configured passport-saml like this :
return new SamlStrategy(
{
entryPoint: "http://ndcdr001s:8081/OpenAM-12.0.0/saml2/jsp/idpSSOInit.jsp?"
+ "metaAlias=/idp"
+ "&spEntityID=http://ndcui.local:9000/metadata/",
callbackUrl: 'http://ndcui.local:9000/login/callback/',
logoutUrl: "http://ndcdr001s:8081/OpenAM-12.0.0/saml2/jsp/idpSingleLogoutInit.jsp?"
+ "binding=urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect"
+ "&RelayState=http://ndcui.local:9000/saml/logout/callback",
issuer: 'http://ndcui.local:9000/'
},
function (profile, done) {
return done(null,
{
id: profile.id,
email: profile.email,
// displayName: profile.cn,
// firstName: profile.givenName,
// lastName: profile.sn,
sessionIndex: profile.sessionIndex,
saml: {
nameID: profile.nameID,
nameIDFormat: profile.nameIDFormat,
token:profile.getAssertionXml()
}
});
});
Then I registered "http://ndcui.local:9000/metadata/" as SP in OpenAM.
I created metadata for SP manually like this: and put under the this link "http://ndcui.local:9000/metadata/"
<EntityDescriptor xmlns="urn:oasis:names:tc:SAML:2.0:metadata" xmlns:ds="http://www.w3.org/2000/09/xmldsig#" entityID="http://ndcui.local:9000/metadata/">
<SPSSODescriptor protocolSupportEnumeration="urn:oasis:names:tc:SAML:2.0:protocol">
<SingleLogoutService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect" Location="http://ndcui.local:9000/logout" Response_Location="http://ndcui.local:9000/saml/logout/callback"/>
<AssertionConsumerService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST" Location="http://ndcui.local:9000/login/callback" index="0"/>
<AssertionConsumerService Binding="urn:oasis:names:tc:SAML:1.0:profiles:browser-post" Location="http://ndcui.local:9000/login/callback" index="1"/>
<AssertionConsumerService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Artifact" Location="http://ndcui.local:9000/login/callback" index="2"/>
<AssertionConsumerService Binding="urn:oasis:names:tc:SAML:1.0:profiles:artifact-01" Location="http://ndcui.local:9000/login/callback" index="3"/>
<AssertionConsumerService Binding="urn:oasis:names:tc:SAML:2.0:profiles:holder-of-key:SSO:browser" Location="http://ndcui.local:9000/login/callback" index="4"/>
</SPSSODescriptor>
<ContactPerson contactType="technical">
<GivenName>Administrator</GivenName>
<EmailAddress>noreply@example.org</EmailAddress>
</ContactPerson>
</EntityDescriptor>
And my routes:
app.get('/metadata', function (req, res) {
//Send custom metadata
res.type('application/xml');
res.sendfile(__dirname + "/metadata.xml");
}
);
app.get("/login", passport.authenticate('saml',
{
successRedirect: "/",
failureRedirect: "/login",
})
);
app.post('/login/callback', passport.authenticate('saml',
{
failureRedirect: '/',
failureFlash: true
}),
function (req, res) {
res.redirect('/');
}
);
app.get('/logout', auth.requiresLogin, function (req, res) {
req.user.nameID = req.user.saml.nameID;
req.user.nameIDFormat = req.user.saml.nameIDFormat;
samlStrategy.logout(req, function (err, request) {
if (!err) {
res.redirect(request);
}
});
});
app.get('/saml/logout/callback', auth.requiresLogin, function (req, res) {
//Logout user
req.logout();
res.redirect('/');
});
Link to full Implementation (you will want to google translate the page)