RESTful WCF服务图像上传问题

时间:2009-03-20 01:42:08

标签: c# wcf rest

1 namespace Uploader  
2 {  
3     using System;  
4     using System.IO;  
5     using System.ServiceModel;  
6     using System.ServiceModel.Description;  
7     using System.ServiceModel.Web;  
8     using System.Drawing;  
9     using System.Drawing.Imaging;  
10     using System.Net;  
11     using System.Xml;  
12   
13     [ServiceContract(Namespace = "http://Uploader")]  
14     public interface IUploaderService  
15     {  
16         [OperationContract, WebInvoke(Method = "POST",UriTemplate = "File/{fileName}")]  
17         bool UploadFile(string fileName, Stream fileContents);  
18     }  
19   
20     [ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall)]  
21     public class UploaderService : IUploaderService  
22     {  
23         public bool UploadFile(string fileName, Stream fileContents)  
24         {  
25             return true;  
26         }  
27     }  
28   
29     class Program  
30     {  
31         static void Main()  
32         {  
33             var host = new   
34                 ServiceHost(typeof (UploaderService),   
35                 new Uri("http://localhost:8080/Uploader"));  
36             host.AddServiceEndpoint("Uploader.IUploaderService",   
37                 new WebHttpBinding(), "").Behaviors.Add(new WebHttpBehavior());  
38             try  
39             {  
40                 host.Open();  
41                 Console.WriteLine(host.BaseAddresses[0].AbsoluteUri + " running.");  
42                 Console.WriteLine();  
43                 var uri = "http://localhost:8080/Uploader/file.jpg";  
44                 var req = WebRequest.Create(uri) as HttpWebRequest;  
45                 if (req != null)  
46                 {  
47                     req.Method = "POST";  
48                     req.ContentType = "image/jpeg";  
49                     var reqStream = req.GetRequestStream();  
50                   
51                     var imageStream = new MemoryStream();  
52                     using (var i = Image.FromFile(@"c:\photo.jpg"))   
53                         i.Save(imageStream, ImageFormat.Jpeg);  
54                       
55                     var imageArray = imageStream.ToArray();  
56                     reqStream.Write(imageArray, 0, imageArray.Length);  
57                     reqStream.Close();  
58                     var resp = (HttpWebResponse)req.GetResponse();  
59                     var r = new XmlTextReader(resp.GetResponseStream());  
60                     if (r.Read())  
61                     {  
62                         Console.WriteLine(r.ReadString());      
63                     }  
64                 }  
65                 Console.WriteLine("Press <ENTER> to quit.");  
66                 Console.ReadLine();  
67             }  
68             catch (Exception ex)  
69             {  
70                 Console.WriteLine(ex.Message);  
71                 Console.ReadKey();  
72             }  
73             finally  
74             {  
75                 if (host.State == CommunicationState.Faulted)  
76                     host.Abort();  
77                 else  
78                     host.Close();  
79             }  
80         }  
81     }  
82 }  
83   
84   

嗨,希望你能帮忙......

我正在创建一个简单的应用程序(可能是网页),它将具有简单的用户界面,并将从外部设备上传文件,当用户将设备插入PC时,应用程序/网页将通过autorun.inf启动。 Web服务将执行将文件链接到管理系统等的复杂工作。这将使不能使用文件浏览的IT文盲用户能够将文件提交到管理系统......!

我遇到的问题是,当内容类型为image / jpeg时,我的RESTful服务器会给我400错误。 它适用于text / plain或text / xml(参见博客文章)

由于 Ĵ

1 个答案:

答案 0 :(得分:7)

您可以尝试覆盖任何内容类型,并使用IOperationBehavior将所有文件上传为application / octet-stream或text / plain。

public class WebContentTypeAttribute : Attribute, IOperationBehavior, IDispatchMessageFormatter
{
    private IDispatchMessageFormatter innerFormatter;
    public string ContentTypeOverride { get; set; }

    public WebContentTypeAttribute(string contentTypeOverride)
    {
        this.ContentTypeOverride = contentTypeOverride;
    }


    // IOperationBehavior
    public void Validate(OperationDescription operationDescription)
    {

    }

    public void ApplyDispatchBehavior(OperationDescription operationDescription, DispatchOperation dispatchOperation)
    {
        innerFormatter = dispatchOperation.Formatter;
        dispatchOperation.Formatter = this;
    }

    public void ApplyClientBehavior(OperationDescription operationDescription, ClientOperation clientOperation)
    {

    }

    public void AddBindingParameters(OperationDescription operationDescription, BindingParameterCollection bindingParameters)
    {

    }

    // IDispatchMessageFormatter
    public void DeserializeRequest(Message message, object[] parameters)
    {
        if (message == null)
            return;

        if (string.IsNullOrEmpty(ContentTypeOverride))
            return;

        var httpRequest = (HttpRequestMessageProperty)message.Properties[HttpRequestMessageProperty.Name];
        httpRequest.Headers["Content-Type"] = ContentTypeOverride;
    }

    public Message SerializeReply(MessageVersion messageVersion, object[] parameters, object result)
    {
        return innerFormatter.SerializeReply(messageVersion, parameters, result);
    }
}

您必须修改服务合同,使其看起来像这样

[OperationContract]
[WebInvoke(Method = "POST",UriTemplate = "File/{fileName}")]
[WebContentType("application/octet-stream")]
bool UploadFile(string fileName, Stream fileContents);  

虽然如果您从网页上传,数据不会以多部分/表格数据格式发布吗?