How to produce XML output using WCF service?

前端 未结 2 2025
误落风尘
误落风尘 2021-01-03 05:13

I\'ve set up the following interface.

[ServiceContract]
public interface IService1
{
  [OperationContract]
  String Ping();
}

Its implement

相关标签:
2条回答
  • 2021-01-03 05:53

    If you define your service endpoint as a WebHttp endpoint (a.k.a. REST endpoint), you'll get what you want. The easiest way to do that is to use the WebServiceHostFactory in your svc file:

    Service1.svc.

    <%@ ServiceHost Language="C#" Debug="true" Service="YourNamespace.Service1"
                    Factory="System.ServiceModel.Activation.WebServiceHostFactory" %>
    

    Or you can define the endpoint without the factory, by defining that it will use the webHttpBinding and have a <webHttp/> behavior:

    <system.serviceModel>
      <behaviors>
        <endpointBehaviors>
          <behavior name="MyBehavior">
            <webHttp/>
          </behavior>
        </endpointBehaviors>
      </behaviors>
      <services>
        <service name="YourNamespace.Service1">
          <endpoint address=""
                    behaviorConfiguration="MyBehavior"
                    binding="webHttpBinding"
                    contract="YourNamespace.IService1" />
        </service>
      </services>
    </system.serviceModel>
    

    Update: Since some people were having issues, I wrote a full example of using XMLHttpRequest to talk to the service listed above. The code can be found at https://github.com/carlosfigueira/WCFQuickSamples/tree/master/WCFForums/QuickWebCode1 (look for StackOverflow_13345557), and it's mostly listed here.

    Service code (notice that I'm using JSON as the response, but XML works just as well):

    namespace StackOverflow_13345557
    {
        [ServiceContract]
        public interface IService1
        {
            [WebGet(ResponseFormat = WebMessageFormat.Json)]
            string Ping();
            [WebGet(ResponseFormat = WebMessageFormat.Json)]
            string PingWithParameters(int a, string b);
        }
    
        public class Service1 : IService1
        {
            public string Ping()
            {
                return "Hello";
            }
    
            public string PingWithParameters(int a, string b)
            {
                return string.Format("Hello {0} - {1}", a, b);
            }
        }
    }
    

    .SVC file - notice no usage of the Factory attribute, since I'm defining the endpoint via configuration:

    <%@ ServiceHost Language="C#" Debug="true" Service="StackOverflow_13345557.Service1"
                    CodeBehind="StackOverflow_13345557.svc.cs" %>
    

    web.config:

    <system.serviceModel>
      <services>
        <service name="StackOverflow_13345557.Service1">
          <endpoint address=""
                    behaviorConfiguration="WithWebHttp"
                    binding="webHttpBinding"
                    bindingConfiguration="WithJSONP"
                    contract="StackOverflow_13345557.IService1" />
        </service>
      </services>
      <behaviors>
        <endpointBehaviors>
          <behavior name="WithWebHttp">
            <webHttp/>
          </behavior>
        </endpointBehaviors>
      </behaviors>
      <bindings>
        <webHttpBinding>
          <binding name="WithJSONP" crossDomainScriptAccessEnabled="true" />
        </webHttpBinding>
      </bindings>
    </system.serviceModel>
    

    HTML page accessing service (body only):

    <body>
        <script type="text/javascript">
            function StackOverflow_13345557_Test(passParameters) {
                var baseUrl = "/StackOverflow_13345557.svc";
                var cacheBuster = new Date().getTime(); // to prevent cached response; development only
                var url;
                if (passParameters) {
                    url = baseUrl + "/PingWithParameters?a=123&b=john+doe&_=" + cacheBuster;
                } else {
                    url = baseUrl + "/Ping?_=" + cacheBuster;
                }
                var xhr = new XMLHttpRequest();
                xhr.onreadystatechange = function () {
                    if (xhr.readyState == 4) {
                        document.getElementById("result").innerText = xhr.responseText;
                    }
                }
    
                xhr.open('GET', url, true);
                xhr.send();
            }
        </script>
        <input type="button" value="StackOverflow 13345557 (no params)" onclick="StackOverflow_13345557_Test(false);" /><br />
        <input type="button" value="StackOverflow 13345557 (with params)" onclick="StackOverflow_13345557_Test(true);" /><br />
        <div id='result'></div>
    </body>
    

    One more update: added a self-contained, minimal project at https://skydrive.live.com/redir?resid=99984BBBEC66D789!6355 with the code listed above.

    0 讨论(0)
  • 2021-01-03 05:55

    I finally got totally PO and went off to business full contact. This is what I've produced - it works on my machine and I hope it's not a local phenomenon. :)

    IRestService.cs - the declaration, what your code promises to a contacting client

    [ServiceContract]
    public interface IRestService
    {
      [OperationContract]
      [WebInvoke(Method = "GET", 
        ResponseFormat = WebMessageFormat.Xml, 
        BodyStyle = WebMessageBodyStyle.Wrapped, 
        UriTemplate = "xml/{id}")]
      String XmlData(String id);
    
      [OperationContract]
      [WebInvoke(Method = "GET", 
        ResponseFormat = WebMessageFormat.Json, 
        BodyStyle = WebMessageBodyStyle.Wrapped, 
        UriTemplate = "json/{id}")]
      String JsonData(String id);
    }
    

    RestService.svc.cs - the implementation, what your code actually does to the client

    public class RestService : IRestService
    {
      public String XmlData(String id)
      {
        return "Requested XML of id " + id;
      }
    
      public String JsonData(String id)
      {
        return "Requested JSON of id " + id;
      }
    }
    

    Web.config - the configuration, what your code is handled as on the way to the client

    <configuration>
    
      <system.web>
        <compilation debug="true" targetFramework="4.0" />
      </system.web>
    
      <system.serviceModel>
        <services>
          ...
        </services>
        <behaviors>
        </behaviors>
      </system.serviceModel>
    
    </configuration>
    

    services - contents of the tag describing the service's nature

    <service name="DemoRest.RestService" 
             behaviorConfiguration="ServiceBehavior">
      <endpoint address="" binding="webHttpBinding" 
                contract="DemoRest.IRestService" 
                behaviorConfiguration="web"></endpoint>
    </service>
    

    behaviors - contents of the tag describing the behavior of the service and the end-point

    <serviceBehaviors>
      <behavior name="ServiceBehavior">
        <serviceMetadata httpGetEnabled="true"/>
        <serviceDebug includeExceptionDetailInFaults="true"/>
      </behavior>
    </serviceBehaviors>
    
    <endpointBehaviors>
      <behavior name="web">
        <webHttp/>
      </behavior>
    </endpointBehaviors>
    

    Index.html - the executor, what your code can be called as

    <html>
      <head>
        <script>
          ...
        </script>
        <style>
          ...
        </style>
      </head>
      <body>
        ...
      </body>
    </html>
    

    script - contents of the tag describing the executable in JavaScript

    window.onload = function () {
      document.getElementById("xhr").onclick = function () {
        var xhr = new XMLHttpRequest();
        xhr.onload = function () { alert(xhr.responseText); }
        xhr.open("GET", "RestService.svc/xml/Viltersten");
        xhr.send();
      }
    }
    

    style - contents of the tag describing the appearance

    .clickable
    {
      text-decoration: underline;
      color: #0000ff;
    }
    

    body - contents of the tag describing the markup structure

    <ul>
      <li>XML output <a href="RestService.svc/xml/123">
        <span class="clickable">here</span></a></li>
      <li>JSON output <a href="RestService.svc/json/123">
        <span class="clickable">here</span></a></li>
      <li>XHR output <span id="xhr" class="clickable">here</span></li>
    

    Everything is stored in a project called DemoRest. I created my own files for declaration and implementation of the service, removing the default ones. The directives of using as well as the XML version declaration are omitted for spacial reasons.

    Now the response can be retrieved using the following URL.

    localhost:12345/RestService.svc/xml/Konrad
    localhost:12345/RestService.svc/json/Viltersten
    
    1. Does anybody else get it to work too?
    2. Any suggestions on improvement or clarification?
    0 讨论(0)
提交回复
热议问题