using System; using System.IO; using System.Net; using System.Xml.Serialization; using System.Collections.Generic; using System.Linq; using System.Text; namespace TestUpload { public delegate void UploadCallback(ImageShackUploadDetails details, Exception e); public class ImageShackUploader { class UploadState { public HttpWebRequest Request { get; set; } public UploadCallback Callback { get; set; } } public static void UploadImage(string filename, UploadCallback callback) { if (callback == null) throw new ArgumentNullException("callback", "upload is asynchronous and must provide a callback"); try { HttpWebRequest request = GetImageShackRequest( filename, "http://iload2.imageshack.us/upload_api.php?swfupload=1&cookie=&optsize=resample&ulevel=&nocache=29632"); request.BeginGetResponse( new AsyncCallback(GetImageShackResponse), new UploadState() { Request = request, Callback = callback }); } catch (Exception e) { callback(null, e); } } private static HttpWebRequest GetImageShackRequest(string fileName, string webPostAddress) { // the request header HttpWebRequest imageShackWebRequest = WebRequest.Create(webPostAddress) as HttpWebRequest; imageShackWebRequest.Method = "POST"; string boundary = "----------" + DateTime.Now.Ticks.ToString("x"); imageShackWebRequest.ContentType = @"multipart/form-data; boundary=" + boundary; FileInfo fileToUploadInfo = new FileInfo(fileName); if (!fileToUploadInfo.Exists) { throw new FileNotFoundException("The specified file doesn't seem to exist.", fileName); } string contentType; switch (fileToUploadInfo.Extension.ToLower()) { case ".jpg": contentType = "image/jpg"; break; case ".jpeg": contentType = "image/jpeg"; break; case ".gif": contentType = "image/gif"; break; case ".png": contentType = "image/png"; break; case ".bmp": contentType = "image/bmp"; break; case ".tif": contentType = "image/tiff"; break; case ".tiff": contentType = "image/tiff"; break; default: contentType = "image/unknown"; break; } // build up the post message header. StringBuilder sb = new StringBuilder(); sb.Append("--"); sb.Append(boundary); sb.Append("\r\n"); sb.Append("Content-Disposition: form-data; name=\""); sb.Append("fileupload"); sb.Append("\"; filename=\""); sb.Append(fileToUploadInfo.Name); sb.Append("\""); sb.Append("\r\n"); sb.Append("Content-Type: "); sb.Append(contentType); sb.Append("\r\n"); sb.Append("\r\n"); string imagePostHeader = sb.ToString(); byte[] imagePostHeaderBytes = Encoding.UTF8.GetBytes(imagePostHeader); // trailing boundary string as a byte array byte[] trailingBoundaryBytes = Encoding.ASCII.GetBytes("\r\n--" + boundary + "\r\n"); FileStream imageFileStream = new FileStream(fileToUploadInfo.FullName, FileMode.Open, FileAccess.Read); imageShackWebRequest.ContentLength = imagePostHeaderBytes.Length + imageFileStream.Length + trailingBoundaryBytes.Length; Stream httpRequestStream = imageShackWebRequest.GetRequestStream(); httpRequestStream.Write(imagePostHeaderBytes, 0, imagePostHeaderBytes.Length); int bytesRead = 0; byte[] imageFileBuffer = new Byte[checked((uint)Math.Min(4096, (int)imageFileStream.Length))]; while ((bytesRead = imageFileStream.Read(imageFileBuffer, 0, imageFileBuffer.Length)) != 0) httpRequestStream.Write(imageFileBuffer, 0, bytesRead); httpRequestStream.Write(trailingBoundaryBytes, 0, trailingBoundaryBytes.Length); imageFileStream.Dispose(); return imageShackWebRequest; } private static void GetImageShackResponse(IAsyncResult ar) { Stream rstream = null; UploadState state = (UploadState)ar.AsyncState; try { HttpWebResponse response = (HttpWebResponse)state.Request.EndGetResponse(ar); rstream = response.GetResponseStream(); ImageShackUploadDetails details = ExtractImageDetails(rstream); state.Callback(details, null); rstream.Dispose(); } catch (Exception e) { state.Callback(null, e); } finally { if (rstream != null) rstream.Dispose(); } } public static ImageShackUploadDetails ExtractImageDetails(Stream stream) { XmlSerializer serializer = new XmlSerializer(typeof(ImageShackUploadDetails)); ImageShackUploadDetails details = null; try { details = (ImageShackUploadDetails)serializer.Deserialize(stream); } catch (Exception e) { Console.WriteLine(e.Message); } return details; } } }