Reivindicações de reivindicações são nulas quando atinge o serviço WCF

StackOverflow https://stackoverflow.com/questions/3450206

  •  27-09-2019
  •  | 
  •  

Pergunta

Atualmente, estou implementando uma solução de autenticação federada usando: um STS passivo para emitir tokens, um site que hospeda um aplicativo Silverlight e serviços WCF para o aplicativo Silverlight.

Até agora sou capaz:

  • Ser redirecionado para o STS
  • Faça login e seja redirecionado para o site
  • Exibir as reivindicações no site acessandoHttpContext.Current.User.Identity as IClaimsIdentity;

No web.config do site, adicionei os dois módulos WIF necessários (no IIS 7)

<modules runAllManagedModulesForAllRequests="true">

        <add name="WSFederationAuthenticationModule" type="Microsoft.IdentityModel.Web.WSFederationAuthenticationModule, Microsoft.IdentityModel, Version=3.5.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" preCondition="managedHandler"/>
        <add name="SessionAuthenticationModule" type="Microsoft.IdentityModel.Web.SessionAuthenticationModule, Microsoft.IdentityModel, Version=3.5.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" preCondition="managedHandler"/>

    </modules>

Eu também configurei a seção Microsoft.IdentityModel do web.config para usar minha própria implementação de reivindicações de autenticação e reivindicação de sathorization manager.

<service name="Rem.Ria.PatientModule.Web.WebService.PatientService">
        <claimsAuthenticationManager type ="Rem.Infrastructure.WIF.RemClaimsAuthenticationManager"/>
        <claimsAuthorizationManager type ="Rem.Infrastructure.WIF.RemClaimsAuthorizationManager"/>
      </service>

Minha reivindicação de retenção está simplesmente definindo o thread.CurrentPrincipal é um principal válido é fornecido.

class RemClaimsAuthenticationManager : ClaimsAuthenticationManager
    {
        public override IClaimsPrincipal Authenticate ( string resourceName, IClaimsPrincipal incomingPrincipal )
        {

            if ( incomingPrincipal.Identity.IsAuthenticated )
            {
                Thread.CurrentPrincipal = incomingPrincipal;
            }
            return incomingPrincipal;
        }
    }
}

O problema é que, quando minha reivindicação de autorização é chamada, o context.principal.Identity não contém uma identidade válida com as reivindicações, nem o thread.CurrentPrincipal.

Alguma ideia?

Foi útil?

Solução

Você não precisa definir o thread.CurrentPrincipal porque o módulo de sessão fará isso por você. Você precisará acessá -lo através do httpcontext.current.user porque o thread.principal geralmente é definido em um encadeamento diferente daquele que está acessando seu serviço porque são dois módulos diferentes no IIS. Temos um exemplo disso em nosso próximo livro que você pode conferir em nosso Site CodePlex.

Hth

Outras dicas

O código de amostra a seguir mostra uma classe de amostra que herda a reivindicação de autenticação. Ele apenas recebe o IClaimsPrincipal de entrada e passa pelas reivindicações, exceto a reivindicação de nome, que é modificada. Isso não define o príncipe atual no encadeamento atual, como no seu exemplo.

Minha implementação de teste é a seguinte:

public class CustomClaimsAuthenticationManager : ClaimsAuthenticationManager
{
public CustomClaimsAuthenticationManager()
{

}

public override IClaimsPrincipal Authenticate(string resourceName, 
IClaimsPrincipal   incomingPrincipal)
{
    var outgoingIdentity = GetClaimsAsPassthrough(incomingPrincipal);
    return outgoingIdentity; 
}

private IClaimsPrincipal GetClaimsAsPassthrough(IClaimsPrincipal incomingPrincipal)
{
    if (!incomingPrincipal.Identity.IsAuthenticated)
    {
        return incomingPrincipal; 
    }

    var ingoingClaims = incomingPrincipal.Identity as IClaimsIdentity; 

    ClaimsIdentity outgoingIdentity = new ClaimsIdentity(new List<Claim>
    {
        new Claim(ClaimTypes.Name, (incomingPrincipal.Identity.Name + " 
        a very cool guy"))
    }, incomingPrincipal.Identity.AuthenticationType);

    foreach (var claim in ingoingClaims.Claims.Where(
    c => c.ClaimType != ClaimTypes.Name))
    {
        outgoingIdentity.Claims.Add(claim.Copy()); 
    }

    return new ClaimsPrincipal(new List<ClaimsIdentity> { outgoingIdentity }); 
 }

}
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top