I am trying to extend an existing ASP.NET application with a WCF service. The service must require authentication via the same Membership Provider that the rest of the site uses.
Here's the web.config file:
<configuration>
<system.web>
<compilation debug="true" targetFramework="4.5.2" />
<httpRuntime targetFramework="4.5.2" />
<authentication mode="Forms">
<forms name=".MyAppAuthentication" timeout="5760" slidingExpiration="true" />
</authentication>
<roleManager enabled="true" defaultProvider="AspNetSqlRoleProvider">
<providers>
<clear />
<add name="AspNetSqlRoleProvider" type="System.Web.Security.SqlRoleProvider" connectionStringName="UsersContext" applicationName="MyApp" />
</providers>
</roleManager>
<membership defaultProvider="AspNetSqlMembershipProvider">
<providers>
<clear/>
<add name="AspNetSqlMembershipProvider" type="System.Web.Security.SqlMembershipProvider" connectionStringName="UsersContext" enablePasswordRetrieval="false" enablePasswordReset="true" requiresQuestionAndAnswer="false" requiresUniqueEmail="false" maxInvalidPasswordAttempts="10" minRequiredPasswordLength="6" minRequiredNonalphanumericCharacters="0" passwordAttemptWindow="10" applicationName="MyApp"/>
</providers>
</membership>
</system.web>
<system.serviceModel>
<serviceHostingEnvironment aspNetCompatibilityEnabled="true" multipleSiteBindingsEnabled="true" />
<bindings>
<wsHttpBinding>
<binding name="MembershipBinding">
<security mode="TransportWithMessageCredential">
<transport clientCredentialType="None" />
<message clientCredentialType="UserName"/>
</security>
</binding>
</wsHttpBinding>
</bindings>
<behaviors>
<serviceBehaviors>
<behavior name="MembershipBehaviour">
<serviceMetadata httpGetEnabled="true" httpsGetEnabled="true" />
<serviceDebug includeExceptionDetailInFaults="false"/>
<serviceAuthorization roleProviderName="AspNetSqlRoleProvider" principalPermissionMode="UseAspNetRoles" />
<serviceCredentials>
<userNameAuthentication userNamePasswordValidationMode="MembershipProvider" membershipProviderName="AspNetSqlMembershipProvider" />
</serviceCredentials>
</behavior>
</serviceBehaviors>
</behaviors>
<services>
<service name="ServiceTestBackend.Services.TestService" behaviorConfiguration="MembershipBehaviour">
<endpoint address="" binding="wsHttpBinding" bindingConfiguration="MembershipBinding" contract="ServiceTestBackend.Services.ITestService" />
</service>
</services>
</system.serviceModel>
<connectionStrings>
<add name="UsersContext" connectionString="data source=.;initial catalog=MyApp.Accounts;integrated security=True;MultipleActiveResultSets=True;App=EntityFramework" providerName="System.Data.SqlClient" />
</connectionStrings>
</configuration>
The code of the service is very simple:
public class TestService : ITestService
{
public string FindUser()
{
var user = Membership.GetUser();
return user.UserName;
}
}
And the client is just about as simple
var client = new TestService.TestServiceClient();
client.ClientCredentials.UserName.UserName = "username";
client.ClientCredentials.UserName.Password = "password";
var acc = client.FindUser();
The server is invoked, but the method fails because Membership.GetUser()
returns null
.
Am I missing anything in the configuration?