public string ReplacePicture(Stream stream, string photoId)
{
string boundary = "FLICKR_MIME_" + DateTime.Now.ToString("yyyyMMddhhmmss");
HttpWebRequest req = (HttpWebRequest)HttpWebRequest.Create(ReplaceUrl);
req.UserAgent = "Mozilla/4.0 FlickrNet API (compatible; MSIE 6.0; Windows NT 5.1)";
req.Method = "POST";
if( Proxy != null ) req.Proxy = Proxy;
req.Referer = "http://www.flickr.com";
req.KeepAlive = false;
req.Timeout = HttpTimeout * 100;
req.ContentType = "multipart/form-data; boundary=" + boundary + "";
StringBuilder sb = new StringBuilder();
Hashtable parameters = new Hashtable();
parameters.Add("photo_id", photoId);
parameters.Add("api_key", _apiKey);
parameters.Add("auth_token", _apiToken);
string[] keys = new string[parameters.Keys.Count];
parameters.Keys.CopyTo(keys, 0);
Array.Sort(keys);
StringBuilder HashStringBuilder = new StringBuilder(_sharedSecret, 2 * 1024);
foreach(string key in keys)
{
HashStringBuilder.Append(key);
HashStringBuilder.Append(parameters[key]);
sb.Append("--" + boundary + "\r\n");
sb.Append("Content-Disposition: form-data; name=\"" + key + "\"\r\n");
sb.Append("\r\n");
sb.Append(parameters[key] + "\r\n");
}
sb.Append("--" + boundary + "\r\n");
sb.Append("Content-Disposition: form-data; name=\"api_sig\"\r\n");
sb.Append("\r\n");
sb.Append(Md5Hash(HashStringBuilder.ToString()) + "\r\n");
// Photo
sb.Append("--" + boundary + "\r\n");
sb.Append("Content-Disposition: form-data; name=\"photo\"; filename=\"image.jpeg\"\r\n");
sb.Append("Content-Type: image/jpeg\r\n");
sb.Append("\r\n");
UTF8Encoding encoding = new UTF8Encoding();
byte[] postContents = encoding.GetBytes(sb.ToString());
byte[] photoContents = new byte[stream.Length];
stream.Read(photoContents, 0, photoContents.Length);
stream.Close();
byte[] postFooter = encoding.GetBytes("\r\n--" + boundary + "--\r\n");
byte[] dataBuffer = new byte[postContents.Length + photoContents.Length + postFooter.Length];
Buffer.BlockCopy(postContents, 0, dataBuffer, 0, postContents.Length);
Buffer.BlockCopy(photoContents, 0, dataBuffer, postContents.Length, photoContents.Length);
Buffer.BlockCopy(postFooter, 0, dataBuffer, postContents.Length + photoContents.Length, postFooter.Length);
req.ContentLength = dataBuffer.Length;
Stream resStream = req.GetRequestStream();
int j = 1;
int uploadBit = Math.Max(dataBuffer.Length / 100, 50*1024);
int uploadSoFar = 0;
for(int i = 0; i < dataBuffer.Length; i=i+uploadBit)
{
int toUpload = Math.Min(uploadBit, dataBuffer.Length - i);
uploadSoFar += toUpload;
resStream.Write(dataBuffer, i, toUpload);
if( (OnUploadProgress != null) && ((j++) % 5 == 0 || uploadSoFar == dataBuffer.Length) )
{
OnUploadProgress(this, new UploadProgressEventArgs(i+toUpload, uploadSoFar == dataBuffer.Length));
}
}
resStream.Close();
HttpWebResponse res = (HttpWebResponse)req.GetResponse();
XmlSerializer serializer = _uploaderSerializer;
StreamReader sr = new StreamReader(res.GetResponseStream());
string s= sr.ReadToEnd();
sr.Close();
StringReader str = new StringReader(s);
FlickrNet.Uploader uploader = (FlickrNet.Uploader)serializer.Deserialize(str);
if( uploader.Status == ResponseStatus.OK )
{
return uploader.PhotoId;
}
else
{
throw new FlickrException(uploader.Error);
}
}