Edit: 7/5/11 - This sample has been updated and posted on MSDN Code Gallery - Windows Workflow Foundation (WF4) - Role Based Security for Workflow Services
The other day somebody asked me how they could secure a Workflow Service. Specifically what they wanted to do was to allow one or two Windows Accounts to be able to access the service on the Intranet. The other requirement was to simply list the allowed identities in the configuration file. So I decided to tackle this project and put it on endpoint.tv
After investigating this here is the solution I came up with. It starts with a WCF Workflow Service project. (Note: This code would work with any WCF service, not just Workflow Services)
I then added an appKey value to the web.config with the list of allowed identities.
<add key="ServiceAllow" value="REDMOND\rojacobs,ROJACOBS-PC\Administrators"/>
Next I added a class that is derived from ServiceAuthorizationManager and implemented a role check for the identity to see if I had a match with my list.
public class ServiceAuthz : ServiceAuthorizationManager
private String serviceAllows;
String allowString = System.Configuration.ConfigurationManager.AppSettings["ServiceAllow"];
serviceAllows = allowString.Split(',');
protected override bool CheckAccessCore(OperationContext operationContext)
var authCtx = operationContext.ServiceSecurityContext.AuthorizationContext;
var identities = (List<System.Security.Principal.IIdentity>)(authCtx.Properties["Identities"]);
foreach (var ident in identities)
var windowsIdent = ident as System.Security.Principal.WindowsIdentity;
if (windowsIdent != null)
var windowsPrincipal = new System.Security.Principal.WindowsPrincipal(windowsIdent);
foreach (String allow in serviceAllows)
Boolean fInRole = windowsPrincipal.IsInRole(allow);
By default, the Workflow Service doesn’t include any configuration so it will use basicHttpBinding which will not pass credentials. So I simply added a protocol mapping section to web.config <system.serviceModel> section to cause it to use wsHttpBinding instead which will pass the Windows credentials by default.
<add scheme ="http" binding="wsHttpBinding"/>
"WorkflowServiceWindowsAuthZ.ServiceAuthz, WorkflowServiceWindowsAuthZ" />