17. April 2007 00:43
I recently received a question from someone having some trouble with impersonation:
"When I set the attribute impersonateCallerForAllOperations="true" in the web.config files, I obtain an InvalidOperationException saying that the operation does not allow impersonation."
Fortunately, this is an easy problem to solve.
There are three impersonation options for operations in WCF that are encapsulated by the enumeration System.ServiceModel.ImpersonationOption:
- Allowed - Impersonation is supported when credentials are available and ImpersonateCallerForAllOperations is set to true.
- Not Allowed - Impersonation is not supported and an exception will occur if ImpersonateCallerForAllOperations is set to true.
- Required - Impersonation is required. It is not optional and an exception will occur if the credentials are not available or ImpersonateCallerForAllOperations is set to false.
By default, WCF applies Not Allowed as the impersonation option for a given operation. In order to enable impersonation, it is necessary to specify Required or Allowed via an OperationBehavior as shown below:
[OperationBehavior(Impersonation = ImpersonationOption.Allowed)]
If you separate your contract and implementation (and I hope you do), keep in mind the OperationBehavior cannot be applied to the contract. It has to be applied to the implementation. Rather than placing it on the appropriate method in your interface, it would be placed on the appropriate method in the class that implements the interface. In other words, it goes with your service implementation rather than your service contract.
It is also necessary to set the ImpersonateCallerForAllOperations property to true in the Service Authorization Behavior. The easiest way to accomplish this is by creating a behavior in your configuration file and referencing it from your service. An example is shown below:
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<system.serviceModel>
<behaviors>
<serviceBehaviors>
<behavior name="MyBehavior">
<serviceAuthorization impersonateCallerForAllOperations="false" />
</behavior>
</serviceBehaviors>
</behaviors>
<services>
<service behaviorConfiguration="MyBehavior" name="MyService">
<endpoint
address="service"
binding="wsHttpBinding"
name="MyHttpBinding"
contract="MyServiceContract" />
<host>
<baseAddresses>
<add baseAddress="http://localhost:8000/myService/" />
</baseAddresses>
</host>
</service>
</services>
</system.serviceModel>
</configuration>
This should get your impersonation up and running.
7dd754e8-7551-40fb-8c4b-9dc2acdd9c66|1|5.0
By: Jeff Barnes
Category:
Tags: