Cod*_*ike 4 .net c# wcf authorization
我有一个使用自定义的WCF服务ServiceAuthorizationManager.自定义身份验证管理器已设置为处理Windows和Forms身份验证.
但是,如果我连接到设置为UserNameauth 的客户端,我似乎无法在任何地方找到用户名.
客户端代码如下所示:
this.ClientCredentials.UserName.UserName = "user";
this.ClientCredentials.UserName.Password = "pass";
this.Open();
this.MyMethod(); // my actual contract method
this.Close();
Run Code Online (Sandbox Code Playgroud)
然后在服务器上,我有我的自定义身份验证管理器:
public sealed class AppAuthorizationManager : ServiceAuthorizationManager
{
public override bool CheckAccess(OperationContext operationContext, ref Message message)
{
// would like to check user/pwd here...
}
}
Run Code Online (Sandbox Code Playgroud)
这可能吗?
Thread.CurrentPrincipal未设置,operationContext.ServiceSecurityContext.PrimaryIdentity 没有设定.operationContext.ServiceSecurityContext.AuthorizationContext.ClaimSets 是空的. 用户/密码应该在任何地方可用吗?或者我是否还要添加自定义UsernamePasswordValidator?
更新:所以我添加了一个自定义UserNamePasswordValidator和一个IAuthorizationPolicy.我更新的WCF配置如下所示:
<behavior name="Server2ServerBehavior">
<serviceMetadata httpGetEnabled="true" />
<serviceDebug includeExceptionDetailInFaults="true" />
<serviceAuthorization principalPermissionMode="Custom" serviceAuthorizationManagerType="MyApp.AuthManager, MyApp">
<authorizationPolicies>
<add policyType="MyApp.TokenAuthorizationPolicy, MyApp" />
</authorizationPolicies>
</serviceAuthorization>
<serviceCredentials>
<userNameAuthentication customUserNamePasswordValidatorType="MyApp.PFUserNameValidator, MyApp" />
</serviceCredentials>
</behavior>
Run Code Online (Sandbox Code Playgroud)
如果我在所有3个类中设置断点,WCF会抛出异常:
LogonUser failed for the 'username' user. Ensure that the user has a valid Windows account.
at System.IdentityModel.Selectors.WindowsUserNameSecurityTokenAuthenticator.ValidateUserNamePasswordCore(String userName, String password)
Run Code Online (Sandbox Code Playgroud)
在任何一个运行之前.嗯...
这通常在UsernamePasswordValidator中处理- 这是您唯一可以访问密码的地方.然而,这是不是你设置的委托-这将是在IAuthorizationPolicy的Evaluate方法,它可能看起来是这样的:
bool IAuthorizationPolicy.Evaluate(
EvaluationContext evaluationContext, ref object state)
{
IList<IIdentity> idents;
object identsObject;
if (evaluationContext.Properties.TryGetValue(
"Identities", out identsObject) && (idents =
identsObject as IList<IIdentity>) != null)
{
foreach (IIdentity ident in idents)
{
if (ident.IsAuthenticated &&
ident.AuthenticationType == TrustedAuthType)
{
evaluationContext.Properties["Principal"]
= //TODO our principal
return true;
}
}
}
if (!evaluationContext.Properties.ContainsKey("Principal"))
{
evaluationContext.Properties["Principal"] = //TODO anon
}
return false;
}
Run Code Online (Sandbox Code Playgroud)
(TrustedAuthType密码验证器的名称在哪里)
有了这个,线程的主体将被设置,我们可以识别自己(并使用基于角色的安全性等)