zoukankan      html  css  js  c++  java
  • [原]RESTful Web Service之以HTTP PUT方式调用WCF服务

    昨天突然想到一个问题,在RESTful Web Service中,如何修改一个对象呢,怎么看都不像是通过把一个复杂对象分解为Uri的参数的形式来上传到服务器上的。又看了微软提供的WCF的示例代码《高级 Web 编程》,其中倒有一段代码貌似和我的需求一致:
    代码
        [OperationContract]
        [WebInvoke(Method 
    = "PUT", UriTemplate = "{id}")]
        Customer UpdateCustomer(
    string id, Customer newCustomer);

    这里从客户端传上来一个Customer类型的对象newCustomer,而不是完全把Customer分解成简单类型传上来。但是还是感觉这不是我想要的代码,因为这个Customer类型还是太“具体”,为每一个PUT动作都设计一个方法并不是我想要的。而且,如果离开了.NET平台,离开了DataContract,DataMember调用是不是会变的复杂呢(这个我现在也没有去研究,希望知道的兄弟指教一二),我心中希望的这种调用,最好就像Google Data API中的AtomEntry一样,使用一个AtomEntry.Update(),就可以把自已更新到服务器上去,而不是为每一个类型都去做自已的更新方法。既然Google能做到,那一定是实现的办法。

    通过反复的查询MSDN,终于找到了一个可以被WCF当然数据契约接收的“通用”类型:

    代码
    [DataContractAttribute]
    public abstract class SyndicationItemFormatter

    很显然,这是一个抽象类,它的继承层次如下:

    System.Object
        System.ServiceModel.Syndication.SyndicationItemFormatter
        System.ServiceModel.Syndication.Atom10ItemFormatter
        System.ServiceModel.Syndication.Rss20ItemFormatter

    再进一步,又发现了下面的这个类型:

    代码
    public class Atom10ItemFormatter<TSyndicationItem> : Atom10ItemFormatter
    where TSyndicationItem : new(), SyndicationItem

    MSDN解释如下:

    一个用于在 SyndicationItem派生类与 Atom 1.0 格式之间来回序列化的类。

    备注:

    使用此类可以序列化SyndicationItem 派生类的实例,以及从包含 Atom 1.0 项的 XML 文档创建SyndicationFeed 派生类的实例。如果必须序列化SyndicationItem实例,请改用Atom10ItemFormatter格式化程序。

    如果把Atom10ItemFormatter<TSyndicationItem>做为WCF服务方法的参数类型,再使用HTTP 的PUT方式把数据推到WCF服务的方法上,这个Atom10ItemFormatter<TSyndicationItem>应该会将推进来的XML数据自动转换成SyndicationItem对象吧,试试看:

    随例建一个Syndication Service项目,然后将IFeed1.cs修改为如下代码所示:

    代码
        [ServiceContract]
        [ServiceKnownType(
    typeof(Atom10FeedFormatter))]
        [ServiceKnownType(
    typeof(Rss20FeedFormatter))]
        
    public interface IFeed1
        {

            [OperationContract]
            [WebGet(UriTemplate 
    = "get", BodyStyle = WebMessageBodyStyle.Bare)]
            SyndicationFeedFormatter CreateFeed();

            [OperationContract]
            [WebInvoke(Method 
    = "PUT", RequestFormat = WebMessageFormat.Xml, UriTemplate = "up")]
            
    void Update(Atom10ItemFormatter<SyndicationItem> item);
        }

    接下来再修改Feed1.cs,为其添加Update方法:

    代码
            public void Update(Atom10ItemFormatter<SyndicationItem> item)
            {
                
    using (System.IO.StreamWriter file = new System.IO.StreamWriter(@"C:\a.txt"true))
                {
                    file.WriteLine(item.Item.Title.Text);
                } 
            }

    为了观察是否得到了客户端PUT来的数据,我做了一个简单的Log,把PUT来的SyndicationItem的Title写入到一个文本文件。

    有了服务端,还得有个客户端,新建一个控制台应用程序,将main.cs修改为如下所示:

    代码
            static void Main(string[] args)
            {
                HttpWebRequest req 
    = (HttpWebRequest)WebRequest.Create("http://localhost:8731/Design_Time_Addresses/RESTfulTest/Feed1/up");
                req.Method 
    = "PUT";
                SyndicationItem item 
    = new SyndicationItem("think8848""Item Content"new Uri("http://Item/Alternate/Link"), "itemID", DateTimeOffset.Now);
                MemoryStream ms 
    = new MemoryStream();
                XmlWriter writer 
    = XmlWriter.Create(ms);
                item.SaveAsAtom10(writer);
                writer.Close();
                req.ContentLength 
    = ms.Length;
                req.ContentType 
    = "text/html";
                Stream sw 
    = req.GetRequestStream();
                sw.Write(ms.ToArray(), 
    0, (int)ms.Length);
                WebResponse resp 
    = req.GetResponse();
                Stream s 
    = resp.GetResponseStream();
                StreamReader sr 
    = new StreamReader(s);
                Console.WriteLine(sr.ReadToEnd());
                resp.Close();
                Console.ReadLine();
            

    Go!Go!Go! Start new instance

    观察下c:\a.txt中有没有东西:

    示例代码下载

    参考文章:http://social.msdn.microsoft.com/Forums/en/wcf/thread/c2f7a08e-3af8-4ea6-8eab-03eb07951de4

    推荐博客:http://www.robbagby.com/blog

  • 相关阅读:
    taro 列表渲染
    taro 事件处理
    taro 项目、代码说明
    taro 开发注意点
    taro 知识点
    taro 学习资料
    egg 官方文档之:框架扩展(Application、Context、Request、Response、Helper的访问方式及扩展)
    node 学习资料
    node api 之:fs
    node api 之:stream
  • 原文地址:https://www.cnblogs.com/think8848/p/1614520.html
Copyright © 2011-2022 走看看