We are currently working on a single sign-on project through ADFS using the SAML token.
The basic rule that this project should follow:
1. The agent logs into Windows using its credentials.
2. The agent enters the web application (relying party)
3. The web application must redirect to STS in ADFS (Active Directory is an identity provider) and log in using the credentials that the agent used in its Windows authentication (seamless authentication).
4. Therefore, the STS login page should not be displayed , and the user should be authenticated
. 5. After that, you need to get a complaint and a security token so that we can authorize the agent.
Actual result:
1. The redirect is performed for the first time, and re-authentication is required (IE authentication page and Firefox \ Chrome authentication page).


- It can authenticate with all kinds of domain users, and not just with an authenticated Windows user.
- After the first login to the sts login page, authentication is again not required. However, we do not want a second authentication. Only when logging into Windows (true only for IE).
Customized Environment:
1. Domain controller + ADFS 3.0 server on one computer (Win2k12R2)
2. Web Application Machines (Win2k12 + IIS8.5)
3. Cars are in the same domain
ADFS Configuration:



Relying Party Configuration:


IE configuration:



Web Application Configuration:
Authentication:
ASP.Net Project:
Web configuration file:
<?xml version="1.0" encoding="utf-8"?> <configuration> <configSections> <section name="entityFramework" type="System.Data.Entity.Internal.ConfigFile.EntityFrameworkSection, EntityFramework, Version=5.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" /> <section name="system.identityModel" type="System.IdentityModel.Configuration.SystemIdentityModelSection, System.IdentityModel, Version=4.0.0.0, Culture=neutral, PublicKeyToken=B77A5C561934E089" /> <section name="system.identityModel.services" type="System.IdentityModel.Services.Configuration.SystemIdentityModelServicesSection, System.IdentityModel.Services, Version=4.0.0.0, Culture=neutral, PublicKeyToken=B77A5C561934E089" /> </configSections> <connectionStrings> <add name="DefaultConnection" providerName="System.Data.SqlClient" connectionString="Data Source=(LocalDb)\v11.0;Initial Catalog=aspnet-TestApp-20150730141753;Integrated Security=SSPI;AttachDBFilename=|DataDirectory|\aspnet-TestApp-20150730141753.mdf" /> </connectionStrings> <location path="FederationMetadata"> <system.web> <authorization> <allow users="*" /> </authorization> </system.web> </location> <system.web> <authorization> <deny users="?" /> </authorization> <authentication mode="None" /> <compilation debug="true" targetFramework="4.5" /> <httpRuntime targetFramework="4.5" /> <pages> <namespaces> <add namespace="System.Web.Optimization" /> </namespaces> <controls><add assembly="Microsoft.AspNet.Web.Optimization.WebForms" namespace="Microsoft.AspNet.Web.Optimization.WebForms" tagPrefix="webopt" /></controls></pages> <profile defaultProvider="DefaultProfileProvider"> <providers> <add name="DefaultProfileProvider" type="System.Web.Providers.DefaultProfileProvider, System.Web.Providers, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" connectionStringName="DefaultConnection" applicationName="/" /> </providers> </profile> <membership defaultProvider="DefaultMembershipProvider"> <providers> <add name="DefaultMembershipProvider" type="System.Web.Providers.DefaultMembershipProvider, System.Web.Providers, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" connectionStringName="DefaultConnection" enablePasswordRetrieval="false" enablePasswordReset="true" requiresQuestionAndAnswer="false" requiresUniqueEmail="false" maxInvalidPasswordAttempts="5" minRequiredPasswordLength="6" minRequiredNonalphanumericCharacters="0" passwordAttemptWindow="10" applicationName="/" /> </providers> </membership> <roleManager defaultProvider="DefaultRoleProvider"> <providers> <add name="DefaultRoleProvider" type="System.Web.Providers.DefaultRoleProvider, System.Web.Providers, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" connectionStringName="DefaultConnection" applicationName="/" /> </providers> </roleManager> <sessionState mode="InProc" customProvider="DefaultSessionProvider"> <providers> <add name="DefaultSessionProvider" type="System.Web.Providers.DefaultSessionStateProvider, System.Web.Providers, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" connectionStringName="DefaultConnection" /> </providers> </sessionState> </system.web> <system.webServer> <modules> <add name="FixedWSFederationAuthenticationModule" type="TestApp.FixedWSFederationAuthenticationModule, TestApp" preCondition="managedHandler" /> <add name="SessionAuthenticationModule" type="System.IdentityModel.Services.SessionAuthenticationModule, System.IdentityModel.Services, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" preCondition="managedHandler" /> </modules> </system.webServer> <system.identityModel> <identityConfiguration saveBootstrapContext="true"> <audienceUris> <add value="https://ccsp12.pj12.loc/testapp" /> </audienceUris> <issuerNameRegistry type="System.IdentityModel.Tokens.ConfigurationBasedIssuerNameRegistry, System.IdentityModel, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089"> <trustedIssuers> <add thumbprint="91992FCF8B03FF9BD98A259FE93B92620E9DD89A" name="http://sts.pj12.loc/adfs/services/trust" /> </trustedIssuers> </issuerNameRegistry> <certificateValidation certificateValidationMode="None" /> </identityConfiguration> </system.identityModel> <system.identityModel.services> <federationConfiguration> <cookieHandler requireSsl="false" /> <wsFederation passiveRedirectEnabled="true" issuer="https://sts.pj12.loc/adfs/ls/" realm="https://ccsp12.pj12.loc/testapp/" reply="https://ccsp12.pj12.loc/testapp/" requireHttps="true" /> </federationConfiguration> </system.identityModel.services> <entityFramework> <defaultConnectionFactory type="System.Data.Entity.Infrastructure.SqlConnectionFactory, EntityFramework" /> </entityFramework> </configuration>
C # code:
namespace TestApp { public partial class _Default : Page { protected void Page_Load(object sender, EventArgs e) { // local variables string claimsTypes = string.Empty; string claimsValues = string.Empty; string claimsValueTypes = string.Empty; string claimsSubjectNames = string.Empty; string claimsIssuers = string.Empty; // initialize claims and identity ClaimsPrincipal claimsPrincipal = Thread.CurrentPrincipal as ClaimsPrincipal; ClaimsIdentity claimsIdentity = Thread.CurrentPrincipal.Identity as ClaimsIdentity; BootstrapContext bootstrapContext = ClaimsPrincipal.Current.Identities.First().BootstrapContext as BootstrapContext; if (claimsPrincipal != null) { signedIn.Text = "You are signed in."; foreach (Claim claim in claimsPrincipal.Claims) { claimsTypes = string.Concat(claimsTypes, "; ", claim.Type); claimsValues = string.Concat(claimsValues, "; ", claim.Value); claimsValueTypes = string.Concat(claimsValueTypes, "; ", claim.ValueType); claimsSubjectNames = string.Concat(claimsSubjectNames, "; ", claim.Subject.Name); claimsIssuers = string.Concat(claimsIssuers, "; ", claim.Issuer); } //claims principals claimType.Text = claimsTypes; claimValue.Text = claimsValues; claimValueType.Text = claimsValueTypes; claimSubjectName.Text = claimsSubjectNames; claimIssuer.Text = claimsIssuers; // ClaimsIdentity isUserAuthenticated.Text = claimsIdentity.IsAuthenticated.ToString(); authenticationType.Text = claimsIdentity.AuthenticationType; claimName.Text = claimsIdentity.Name; // Token // known bug : http://stackoverflow.com/questions/13514553/wif-4-5-bootstrapcontext-security-token-null SecurityToken token = null; if (bootstrapContext.SecurityToken != null) { token = bootstrapContext.SecurityToken; } else if (!bootstrapContext.Token.Equals(string.Empty)) { var handlers = FederatedAuthentication.FederationConfiguration.IdentityConfiguration.SecurityTokenHandlers; token = handlers.ReadToken(new XmlTextReader(new StringReader(bootstrapContext.Token))); } SamlSecurityToken sst = token as SamlSecurityToken; tokenId.Text = sst.Id; tokenAssertionId.Text = sst.Assertion.AssertionId; tokenIssuer.Text = sst.Assertion.Issuer; } else { signedIn.Text = "You are not signed in."; } } }