Note that there are some explanatory texts on larger screens.

plurals
  1. POHow does one set the location header to a UriTemplate of another service in WCF 4.0 REST without magic strings?
    primarykey
    data
    text
    <p>Consider the following two WCF 4.0 REST services:</p> <pre><code>[ServiceContract] [AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)] [ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall)] public class WorkspaceService { [WebInvoke(UriTemplate = "{id}/documents/{name}", Method = "POST")] public Document CreateWorkspaceDocument(Stream stream, string id, string name) { /* CreateDocument is omitted as it isn't relevant to the question */ Document response = CreateDocument(id, name, stream); /* set the location header */ SetLocationHeader(response.Id); } private void SetLocationHeader(string id) { Uri uri = new Uri("https://example.com/documents/" + id); WebOperationContext.Current.OutgoingResponse.SetStatusAsCreated(uri); } /* methods to delete, update etc */ } [ServiceContract] [AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)] [ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall)] public class DocumentService { [WebGet(UriTemplate = "{id}")] public Document GetDocument(string id) { } /* methods to delete, update etc */ } </code></pre> <p>In essence, when someone creates a document in a workspace, the Location header is set to the location of the document, which is essentially is the same as invoking the <code>DocumentService.GetDocument</code> operation.</p> <p>My global.asax looks as follows:</p> <pre><code>public class Global : HttpApplication { private void Application_Start(object sender, EventArgs e) { RegisterRoutes(); } private void RegisterRoutes() { var webServiceHostFactory = new WebServiceHostFactory(); RouteTable.Routes.Add(new ServiceRoute("workspaces", webServiceHostFactory, typeof (WorkspaceService))); RouteTable.Routes.Add(new ServiceRoute("documents", webServiceHostFactory, typeof (DocumentService))); /* other services */ } } </code></pre> <p>The implementation of <code>WorkspaceService.SetLocationHeader</code> as it makes some assumptions about how routing was setup. If I was to change the route of <code>DocumentService</code> then the resulting Uri will be incorrect. If I changed the UriTemplate of <code>DocumentService.GetDocument</code>, then the resulting Uri will be incorrect too.</p> <p>If WorkspaceService and DocumentService was merged into one service, I could have written <code>SetLocationHeader</code> as follows:</p> <pre><code>var itemTemplate = WebOperationContext.Current.GetUriTemplate("GetDocument"); var uri = itemTemplate.BindByPosition(WebOperationContext.Current.IncomingRequest.UriTemplateMatch.BaseUri, id); WebOperationContext.Current.OutgoingResponse.SetStatusAsCreated(uri); </code></pre> <p>How would one write <code>WorkspaceService.SetLocationHeader</code> such that it will use the routing table defined in Global.asax and UriTemplates to return the Uri for the GetDocument operation of the DocumentService? </p> <p>I'm using plain old WCF 4.0 (not the WCF Web API).</p>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload