本文介绍的是如何使用Membership 和 Role Provider 来控制 WCF 调用方法的权限。
比如我们有一个WCF Method 叫 GetData(int num),然后我们只允许Role = "Administrator"的用户来调用它,这就是本文要介绍的。
首先,我们先建立一个Solution,Solution里面有两个Project,一个是我们的WCF Service叫MyService,另外是一个客户端的Web Project,叫 MyClientApp, 在MyClientApp下有个Default.aspx,来调用MyService.
里面的MyService是默认建立的WCF Service,这里我们不介绍如何写一个简单的WCF 程序。
重要的是,在我们的方法GetData(int value)上加上这么一句话
-
[PrincipalPermission(SecurityAction.Demand, Role = "Administrator")]
意思是我们只允许Administrator Role的用户来调用GetDate这个方法
整个的代码为
-
[PrincipalPermission(SecurityAction.Demand, Role = "Administrator")]
-
public string GetData(int value)
-
{
-
return string.Format("You entered: {0}", value);
-
}
当运行Default.aspx的时候,我们看到这样的结果。
aspnet_regsql建立Membership 数据库。
完成后修改MyService里面的Web.config,在这里一定看好,不是MyClientApp,而是MyService的web.config
添加如下
-
<connectionStrings>
-
<add name="WCFDemoConnection"
-
connectionString="Data Source=localhost;Initial Catalog=WCFDemo;User ID=sa;Password=9ijn)OKM;"
-
providerName="Sql.Data.SqlClient" />
-
</connectionStrings>
-
<roleManager enabled="true" defaultProvider="AspNetSqlRoleProvider" >
-
<providers>
-
<remove name="AspNetSqlRoleProvider" />
-
<remove name="AspNetWindowsTokenRoleProvider" />
-
<add connectionStringName="WCFDemoConnection"
-
applicationName="WCFDemo"
-
name="AspNetSqlRoleProvider"
-
type="System.Web.Security.SqlRoleProvider" />
-
</providers>
-
</roleManager>
-
<membership defaultProvider="AspNetSqlProvider" >
-
<providers>
-
<remove name="AspNetSqlMembershipProvider" />
-
<add connectionStringName="WCFDemoConnection"
-
applicationName="WCFDemo"
-
minRequiredPasswordLength="2"
-
minRequiredNonalphanumericCharacters="0"
-
requiresQuestionAndAnswer="false"
-
requiresUniqueEmail=" false"
-
name="AspNetSqlProvider"
-
type="System.Web.Security.SqlMembershipProvider "
-
enablePasswordRetrieval="true"
-
passwordFormat="Encrypted"
-
maxInvalidPasswordAttempts="20"/>
-
</providers>
-
</membership>
-
<machineKey validationKey="0D9EA75EE7CEF839CACB3DBAC68F420060EC381F315C2C12A80DBBBE7A8ED02079B8371B0654F11549248F58E55B5E74051DC888BA978BE1D733CF452511ECB7 " decryptionKey="BD9A8F945ACCB35EAB54542B771D34CFFE01F026A5FC5857A4253FAA20EA207F" validation="SHA1" decryption=" AES" />
选择MyService的Project,然后进入到ASP.NET Web Site Administration Tool的界面,在里面建立两个Role,一个Administrator,一个是User
然后我们在建立两个User,一个是Administrator group里面的admin,密码Password,一个是User group里面的user1,密码是Password
在MyService\web.config,进行修改,这里我们暂时不做Certificate Check, 所以我们使用NoCheck.
-
<behaviors>
-
-
<serviceBehaviors>
-
-
<behavior>
-
<serviceAuthorization principalPermissionMode="UseAspNetRoles" roleProviderName="AspNetSqlRoleProvider">
-
</serviceAuthorization>
-
<serviceMetadata httpGetEnabled="true" />
-
<serviceDebug includeExceptionDetailInFaults="false" />
-
<serviceCredentials>
-
<clientCertificate >
-
<authentication certificateValidationMode="PeerOrChainTrust" revocationMode="NoCheck"/>
-
<certificate findValue="localhost" storeLocation="LocalMachine" storeName="My" x509FindType="FindBySubjectName" />
-
</clientCertificate>
-
<serviceCertificate findValue="localhost" storeLocation="LocalMachine" storeName="My" x509FindType="FindBySubjectName" />
-
<userNameAuthentication userNamePasswordValidationMode="MembershipProvider"
-
membershipProviderName="AspNetSqlProvider" />
-
</serviceCredentials>
-
</behavior>
-
</serviceBehaviors>
-
</behaviors>
在MyClientApp端进,Add Reference,自动生成web.config,
进行测试,输入正确的用户名密码
-
try
-
{
-
ServiceReference1.Service1Client client = new ServiceReference1.Service1Client();
-
client.ClientCredentials.ServiceCertificate.Authentication.CertificateValidationMode = System.ServiceModel.Security.X509CertificateValidationMode.None;
-
client.ClientCredentials.UserName.UserName = "admin";
-
client.ClientCredentials.UserName.Password = "Password";
-
Response.Write(client.GetData(5));
-
}
-
catch (Exception ex)
-
{
-
Response.Write(ex.Message);
-
}
输入另外User group内User1,
-
try
-
{
-
ServiceReference1.Service1Client client = new ServiceReference1.Service1Client();
-
client.ClientCredentials.ServiceCertificate.Authentication.CertificateValidationMode = System.ServiceModel.Security.X509CertificateValidationMode.None;
-
client.ClientCredentials.UserName.UserName = "user1";
-
client.ClientCredentials.UserName.Password = "Password";
-
Response.Write(client.GetData(5));
-
}
-
catch (Exception ex)
-
{
-
Response.Write(ex.Message);
-
}