微信傳送永久圖片素材介面----詳解
本文采用倒敘模式.
我寫這個主要是因為微信開發文件的說明實在太坑了,為了更多.NET 開發人員能順利上傳微信圖片素材,分享一下:
先看看最後的呼叫成功的方法:
/// <summary>
/// 傳送永久圖片素材
/// </summary>
/// <param name="filename">檔案絕對路徑</param>
public static void PushtPicture(string filename)
{
var accessToken = new WxHelper().totalAccessToken;
var postUrl = string.Format("https://api.weixin.qq.com/cgi-bin/material/add_material?access_token={0}", accessToken);
NameValueCollection myCol =new NameValueCollection();
//MD,第三個引數必須是media,,否則上傳失敗,真操蛋
var response = JsonConvert.DeserializeObject<WxPictureResp>(HttpProcess.HttpUploadFile(postUrl, filename, "media", "image/jpeg", myCol));
}
ok,再上微信版模擬http傳送檔案:
/// <summary>
/// 模擬http傳送檔案,這裡只發送圖片
/// </summary>
/// <param name="url">傳送的url地址</param>
/// <param name="">檔案絕對路徑</param>
/// <param name="paramName">這裡必須是media</param>
/// <param name="contentType">是圖片,視訊還是啥,自己去看http傳檔案格式</param>
/// <param name="nvc">可不填</param>
/// <returns></returns>
public static string HttpUploadFile(string url, string , string paramName, string contentType, NameValueCollection nvc)
{
string result = string.Empty;
string boundary = "---------------------------" DateTime.Now.Ticks.ToString("x");
byte[] boundarybytes = System.Text.Encoding.ASCII.GetBytes("\r\n--" boundary "\r\n");
HttpWebRequest wr = (HttpWebRequest)WebRequest.Create(url);
wr.ContentType = "multipart/form-data; boundary=" boundary;
wr.Method = "POST";
wr.KeepAlive = true;
wr.Credentials = System.Net.CredentialCache.DefaultCredentials;
Stream rs = wr.GetRequestStream();
string formdataTemplate = "Content-Disposition: form-data; name=\"{0}\"\r\n\r\n{1}";
foreach (string key in nvc.Keys)
{
rs.Write(boundarybytes, 0, boundarybytes.Length);
string formitem = string.Format(formdataTemplate, key, nvc[key]);
byte[] formitembytes = System.Text.Encoding.UTF8.GetBytes(formitem);
rs.Write(formitembytes, 0, formitembytes.Length);
}
rs.Write(boundarybytes, 0, boundarybytes.Length);
string headerTemplate = "Content-Disposition: form-data; name=\"{0}\"; filename=\"{1}\"\r\nContent-Type: {2}\r\n\r\n";
var pos = .LastIndexOf('/');
var filename = .Substring(pos 1);
string header = string.Format(headerTemplate, paramName, filename, contentType);
byte[] headerbytes = System.Text.Encoding.UTF8.GetBytes(header);
rs.Write(headerbytes, 0, headerbytes.Length);
FileStream fileStream = new FileStream(, FileMode., FileAccess.Read);
byte[] buffer = new byte[4096];
int bytesRead = 0;
while ((bytesRead = fileStream.Read(buffer, 0, buffer.Length)) != 0)
{
rs.Write(buffer, 0, bytesRead);
}
fileStream.();
byte[] trailer = System.Text.Encoding.ASCII.GetBytes("\r\n--" boundary "--\r\n");
rs.Write(trailer, 0, trailer.Length);
rs.Flush();
rs.();
WebResponse wresp = null;
try
{
wresp = wr.GetResponse();
Stream stream2 = wresp.GetResponseStream();
StreamReader reader2 = new StreamReader(stream2);
result = reader2.ReadToEnd();
}
catch (Exception ex)
{
if (wresp != null)
{
wresp.();
wresp = null;
}
}
finally
{
wr = null;
}
result;
}
最後上工具類:
/// <summary>
/// 微信伺服器返回的圖片類,只記錄成功,失敗為null
/// </summary>
public class WxPictureResp
{
/// <summary>
/// 這個就是能用來構造圖文訊息的 thumb_media_id
/// </summary>
public string media_id { get; ; }
/// <summary>
/// 圖片路徑,只能在TX系的域名中使用
/// </summary>
public string url { get; ; }
}
可能模擬http傳送檔案的類有點low,至少應該用StringBuilder的,懶得改了,不差這點效能。
最後
var accessToken = new WxHelper().totalAccessToken;
這個應該不用說,這裡採用了Redis快取,沒法用靜態構造,只好new啦.