As context: I am trying to implement SAML2.0 authentication using ITfoxtec.Identity.Saml2 library. I want to use multiple certificates for one Service Provider, because different clients could login to Service Provider and each of them can have its own certificate. I need a third-party login service have possibility to choose among the list of certificates from my Service Provider metadata.xml when SAML request happened. Does ITfoxtec.Identity.Saml2 library support this possibility or are there some workarounds how it can be implemented?. Thank You
Asked
Active
Viewed 804 times
1 Answers
3
You would normally have one Saml2Configuration. But in your case I would implement some Saml2Configuration logic, where I can ask for a specific Saml2Configuration with the current certificate (SigningCertificate/DecryptionCertificate). This specific Saml2Configuration is then used in the AuthController.
The metadata (MetadataController) would then call the Saml2Configuration logic to get a list of all the certificates.
Something like this:
public class MetadataController : Controller
{
private readonly Saml2Configuration config;
private readonly Saml2ConfigurationLogic saml2ConfigurationLogic;
public MetadataController(IOptions<Saml2Configuration> configAccessor, Saml2ConfigurationLogic saml2ConfigurationLogic)
{
config = configAccessor.Value;
this.saml2ConfigurationLogic = saml2ConfigurationLogic;
}
public IActionResult Index()
{
var defaultSite = new Uri($"{Request.Scheme}://{Request.Host.ToUriComponent()}/");
var entityDescriptor = new EntityDescriptor(config);
entityDescriptor.ValidUntil = 365;
entityDescriptor.SPSsoDescriptor = new SPSsoDescriptor
{
WantAssertionsSigned = true,
SigningCertificates = saml2ConfigurationLogic.GetAllSigningCertificates(),
//EncryptionCertificates = saml2ConfigurationLogic.GetAllEncryptionCertificates(),
SingleLogoutServices = new SingleLogoutService[]
{
new SingleLogoutService { Binding = ProtocolBindings.HttpPost, Location = new Uri(defaultSite, "Auth/SingleLogout"), ResponseLocation = new Uri(defaultSite, "Auth/LoggedOut") }
},
NameIDFormats = new Uri[] { NameIdentifierFormats.X509SubjectName },
AssertionConsumerServices = new AssertionConsumerService[]
{
new AssertionConsumerService { Binding = ProtocolBindings.HttpPost, Location = new Uri(defaultSite, "Auth/AssertionConsumerService") }
},
AttributeConsumingServices = new AttributeConsumingService[]
{
new AttributeConsumingService { ServiceName = new ServiceName("Some SP", "en"), RequestedAttributes = CreateRequestedAttributes() }
},
};
entityDescriptor.ContactPerson = new ContactPerson(ContactTypes.Administrative)
{
Company = "Some Company",
GivenName = "Some Given Name",
SurName = "Some Sur Name",
EmailAddress = "some@some-domain.com",
TelephoneNumber = "11111111",
};
return new Saml2Metadata(entityDescriptor).CreateMetadata().ToActionResult();
}
private IEnumerable<RequestedAttribute> CreateRequestedAttributes()
{
yield return new RequestedAttribute("urn:oid:2.5.4.4");
yield return new RequestedAttribute("urn:oid:2.5.4.3", false);
}
}

Anders Revsgaard
- 3,636
- 1
- 9
- 25
-
1Thank you so much for responding that quick. It's very helpful, i will try your solution. As a workaround i tried to initialize in Startup.cs many config classes which i inherited from your class Saml2Configuration. That allowed to use different configs when i create Saml requests and it worked – Oleg Kornieiev Nov 21 '19 at 15:24
-
Good to hear that also your workaround worked. If you think the response was helpful and can be helpful for others, then please rate the answer. – Anders Revsgaard Nov 22 '19 at 09:20
-
1It's helpful, I rated the answer, but I have not enough reputation to make it visible for others :) – Oleg Kornieiev Nov 22 '19 at 12:32