asp.net webapi (selfhost) Implementation of file synchronization or asynchronous upload _ practical skills

Source: Internet
Author: User
Tags baseuri file upload json net serialization serialization

Objective
We have talked about using angularjs upload to Webapi in the process, and we have in the MVC series on the file upload, this article combined with Mvc+webapi file synchronization or asynchronous upload, and in the meantime review CSS and JS,MVC as the client, And WEBAPI uses the Selfhost mode that does not depend on IIS as the server to receive the client's files and the process is implemented using AJAX, let's take a look.

Sync upload

Needless to say, we look directly at the page.

<div class= "Container" >
 <div>
  @if (viewbag.success!= null)
  {
   <div class= "alert Alert-danger "role=" alert >
    <strong> succeeded!</strong> successfully uploaded. <a href= "@ViewBag. Success" Target= "_ Blank ">open file</a>
   </div>
  }
  else if (viewbag.failed!= null)
  {
   <div class=" Alert Alert-danger "role=" alert >
    <strong> failed!</strong> @ViewBag. Failed
   </div>
  }
 </div>
 @using (Html.BeginForm ("Syncupload", "Home", FormMethod.Post, new {role = "form", enctype = "multipart /form-data ", @style =" margin-top:50px; "}))
 {
  <div class= "Form-group" > <input type= "file" id= "
   file" name= "file"/>
  </div>
  <input type= "Submit" value= "Submit" class= "btn btn-primary"/>
 }
</div>

The above we upload directly after uploading the status to display view upload file path and access, it is so simple. Here we come to MVC background logic

  [HttpPost] public actionresult syncupload (httppostedfilebase file) {using (var client = new HttpClient ()) { using (var content = new Multipartformdatacontent ()) {byte[] Bytes = new Byte[file.
     Inputstream.length + 1]; File.
     Inputstream.read (Bytes, 0, bytes.length);
            var filecontent = new Bytearraycontent (Bytes); Sets the attachment in the request header to the file name so that it can be fetched in webapi fileContent.Headers.ContentDisposition = new System.Net.Http.Headers.ContentDispositionHeaderValue ("attachment") {FileName = file.
     FileName}; Content.
     ADD (filecontent);
     var requesturi = "Http://localhost:8084/api/upload/post"; var result = client. Postasync (RequestUri, content).
     result; if (result. StatusCode = = System.Net.HttpStatusCode.Created) {//Get to upload file address and render to view to access var m = result. Content.readasstringasync ().
      result;
      var list = jsonconvert.deserializeobject<list<string>> (M); viewbag.success = list.

     FirstOrDefault ();
   }  else {viewbag.failed = "upload failed, status code:" + result. StatusCode + ", Reason:" + result. Reasonphrase + ", error message:" + result.
     Content.tostring ();
  }} return View ();
 }

Note: the above will get to the file byte stream array to be passed to the multipartformdatacontent , otherwise the file data will not be obtained when passed to Webapi.

Now that we've done this in MVC, let's take a look at what we need to do in Webapi.

(1) First of all, it is necessary to determine whether the uploaded data is mimetype type.

 if (! Request.Content.IsMimeMultipartContent ())
 {
  throw new httpresponseexception ( Httpstatuscode.unsupportedmediatype);
 }

(2) We definitely need to regenerate a file name to avoid duplication, using GUIDs or date or other.

 String name = Item. Headers.ContentDisposition.FileName.Replace ("\" "," ");
 String newfilename = Guid.NewGuid (). ToString ("N") + path.getextension (name);

(3) We need to use this type of multipartfilestreamprovider to set up the upload path and write the file into this.

 var Provider = new Multipartfilestreamprovider (rootpath);
 var task = Request.Content.ReadAsMultipartAsync (Provider) .....

(4) Return the uploaded file address.

  return Request.createresponse (httpstatuscode.created, Jsonconvert.serializeobject (Savedfilepath));
The step-by-step resolution is so much that the assembly code is as follows:

  Public task 

Note: the item above. LocalFilename for E:\Documents\Visual Studio 2013\projects\webapireturnhtml\webapireturnhtml\upload\bodypart_ fa01ff79-4a5b-40f6-887f-ab514ec6636f, because at this point we renamed the file name, so we need to move the file to the address of our renamed file.

The whole process is so simple, let's take a look at the demo results.

At this time incredibly wrong, a bit intriguing, in the server is to return the following JSON string

Copy Code code as follows:
list<string> Savedfilepath = new list<string> ();

There is an error in deserializing this time, and then look at the error message on the page:

Unable to convert string to List<string> This is not one by one, okay, let me see what the returned string looks like, "When you put the mouse up", look at the following:

When you click View , the results are as follows:

The correct JSON is returned when you click on the View button, and here we find that json.net serialization is also problematic, so that when deserializing, the returned string needs to be processed and converted to the correct JSON string to be deserialized, as follows:

  var m = result. Content.readasstringasync (). result;
      m = M.trimstart (' \ ");
      m = m.trimend (' \ ");
      m = m.replace ("\", "");
      var list = jsonconvert.deserializeobject<list<string>> (M);

The final page appears as follows:

Here our sync upload to the end, which use json.net to do the reverse serialization of the problem, the first time encountered json.net deserialization problem, more exotic, inexplicable.

Asynchronous upload

The so-called asynchronous upload is only the use of Ajax upload, here is to review the script or Razor view, the following is only the view of the changes, for asynchronous upload I took advantage of the asynchronous API in Jquery.form.js, see the following code:

<script src= "~/scripts/jquery-1.10.2.min.js" ></script> <script src= "~/scripts/jquery.form.js" > </script> <script src= "~/scripts/bootstrap.min.js" ></script> <link href= "~/content/" Bootstrap.min.css "rel=" stylesheet "/> <div class=" container "style=" margin-top:30px "> <div id=" Success " Style= "Display:none;" > <div class= "alert Alert-danger" role= "alert" > <strong> upload Success </strong><span style= "Margin-rig ht:50px; " ></span><a href= "" target= "_blank" id= "linkaddr" > File access address </a> </div> </div> <div ID = "Fail" style= "Display:none"; > <div class= "alert Alert-danger" role= "alert" > <strong> upload failed </strong> </div> &LT;/DIV&G

T </div> @using (Ajax.beginform ("Asyncupload", "Home", new Ajaxoptions () {HttpMethod = "POST"}, new {enctype = "mul
Tipart/form-data ", @style =" margin-top:10px; "})) {<div class= "Form-group" > <input type= "file" Name= "fiLe "id=" fu1 "/> </div> <div class=" Form-group "> <input type=" Submit "class=" btn btn-primary "value=" Upload "/> </div>} <div class=" Form-group "> <div class=" Progress "id=" Progress "style=" Display:none; " > <div class= "Progress-bar" >0%</div> </div> <div id= "status" ></div> </div> &L
  T;style>. Progress {position:relative;
  width:400px;
  border:1px solid #ddd;
 padding:1px;
  }. progress-bar {width:0px;
  height:40px;
 Background-color: #57be65;
  } </style> <script> (function () {var bar = $ ('. Progress-bar ');
  var percent = $ ('. Progress-bar ');
    $ (' form '). Ajaxform ({beforesend:function () {$ ("#progress"). Show ();
    var percentvalue = ' 0% ';
    Bar.width (Percentvalue);
   Percent.html (Percentvalue);
    }, Uploadprogress:function (event, Position, total, percentcomplete) {var percentvalue = percentcomplete + '% ';
    Bar.width (Percentvalue); PercenT.html (Percentvalue);
    }, Success:function (d) {var percentvalue = ' 100% ';
    Bar.width (Percentvalue);
    Percent.html (Percentvalue);
   $ (' #fu1 '). Val (');
     }, Complete:function (XHR) {if (Xhr.responsetext!= null) {$ ("#linkAddr"). Prop ("href", xhr.responsetext);
    $ ("#success"). Show ();
    else {$ (' #fail '). Show ();
 }
   }
  });
})();

 </script>

Let's take a screenshot and look at the upload process.

Upload in:

Upload complete:

Of course, the 100% is only for small files in real-time upload, if the big file is certainly not real-time, using other components to achieve more appropriate, here I just learn to learn only this.

Note: here also need to repeat, before the MVC upload has been described, MVC default upload file is limited, so more than its limit, you can not upload, you need to do the following settings

(1) In IIS 5 and IIS 6, the default file upload maximum of 4 megabytes, when the uploaded file size of more than 4 megabytes, you will get an error message, but we set the file size by such as down.

<system.web>
  
 

(2) In IIS 7+, the default file upload maximum of 28.6 megabytes, when the default size is exceeded, the same will get error message, but we can set the file upload size (also to be set as above).

<system.webServer>
 <security>
  <requestFiltering>
   <requestlimits Maxallowedcontentlength= "2147483647"/>
  </requestFiltering>
 </security>
</ System.webserver>

Summary

In this section we've learned how to isolate MVC from Webapi to upload, At the same time we also find that there is a problem with json.net when deserializing, and we note that when the JSON string returned by deserialization is not a standard JSON string when one by one corresponds, we need to do the following for the returned JSON string (perhaps there are other scenarios).

var jsonstring = "returned JSON string";
jsonstring = Jsonstring.trimstart (' \ ");
jsonstring = jsonstring.trimend (' \ ");
jsonstring = Jsonstring.replace ("\", "");

The next step is to prepare the system to learn about SQL Server and Oracle. Rest, rest!

The above is the entire content of this article, I hope to help you learn, but also hope that we support the cloud habitat community.

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.