天天看點

微信公共服務平台開發(.Net 的實作)8-------處理圖檔(上傳下載下傳發送)

舉個例子,有人對着我們的公共微信号拍個照片發送過來,然後我們處理這個照片,比如進行ocr識别字(随後就會降到這個例子),或者人臉識别,或者拍照驗證等,這些功能都是相當有用的。那麼我們現在就要分析一下這個過程。微信平台肯定不能幫助我們OCR或者人臉識别等功能,要做這些功能首先到得到圖檔!使用者拍攝的照片首先被上傳到了wenxin的伺服器,然後就有了一個mediaID,我們用這個mediaID可以下載下傳到我們自己的伺服器上然後處理,把結果給微信平台,由微信平台最終回報給使用者(關注者)。微信的開發文檔已經給出了下載下傳資源的辦法,我改造為.net的,如下:

/// <summary>
    /// 下載下傳儲存多媒體檔案,傳回多媒體儲存路徑
    /// </summary>
    /// <param name="ACCESS_TOKEN"></param>
    /// <param name="MEDIA_ID"></param>
    /// <returns></returns>
    public string GetMultimedia(string ACCESS_TOKEN, string MEDIA_ID)
    {
        string file = string.Empty;
        string content = string.Empty;
        string strpath = string.Empty;
        string savepath = string.Empty;
        string stUrl = "http://file.api.weixin.qq.com/cgi-bin/media/get?access_token=" + ACCESS_TOKEN + "&media_id=" + MEDIA_ID;

        HttpWebRequest req = (HttpWebRequest)HttpWebRequest.Create(stUrl);

        req.Method = "GET";
        using (WebResponse wr = req.GetResponse())
        {
            HttpWebResponse myResponse = (HttpWebResponse)req.GetResponse();

            strpath = myResponse.ResponseUri.ToString();
            WriteLog("接收類别://" + myResponse.ContentType);
            WebClient mywebclient = new WebClient();
            savepath = Server.MapPath("image") + "\\" + DateTime.Now.ToString("yyyyMMddHHmmssfff") + (new Random()).Next().ToString().Substring(0, 4) + ".jpg";
            WriteLog("路徑://" + savepath);
            try
            {
                mywebclient.DownloadFile(strpath, savepath);
                file = savepath;
            }
            catch (Exception ex)
            {
                savepath = ex.ToString();
            }

        }
        return file;
    }
           

上面的兩個參數很好了解,第一就是ACCESS_TOKEN,之前說過很多了,第二就是在微信伺服器上的資源id,即mediaID。如果我們要下載下傳微信伺服器上的資源總要知道id吧。但是MEDIA_ID又是怎麼産生的呢?我首先改造一下之前的消息實體類,加入MediaId 屬性

class wxmessage  
   {  
       public string FromUserName { get; set; }  
       public string ToUserName { get; set; }  
        public string MsgType { get; set; }  
        public string EventName { get; set; }  
        public string Content { get; set; }
        public string Recognition { get; set; }
        public string MediaId { get; set; }
        public string EventKey { get; set; } 
    }
           

然後改造一下GetWxMessage(),給MediaId指派。

private wxmessage GetWxMessage()
     {
         wxmessage wx = new wxmessage();
         StreamReader str = new StreamReader(Request.InputStream, System.Text.Encoding.UTF8);
         XmlDocument xml = new XmlDocument();
         xml.Load(str);
         wx.ToUserName = xml.SelectSingleNode("xml").SelectSingleNode("ToUserName").InnerText;
         wx.FromUserName = xml.SelectSingleNode("xml").SelectSingleNode("FromUserName").InnerText;
         wx.MsgType = xml.SelectSingleNode("xml").SelectSingleNode("MsgType").InnerText;
         if (wx.MsgType.Trim() == "text")
         {
             wx.Content = xml.SelectSingleNode("xml").SelectSingleNode("Content").InnerText;
         }
         if (wx.MsgType.Trim() == "event")
         {
             wx.EventName = xml.SelectSingleNode("xml").SelectSingleNode("Event").InnerText;
             wx.EventKey = xml.SelectSingleNode("xml").SelectSingleNode("EventKey").InnerText;
         }
         if (wx.MsgType.Trim() == "voice")
         {
             wx.Recognition = xml.SelectSingleNode("xml").SelectSingleNode("Recognition").InnerText;
         }
        if (wx.MsgType.Trim() == "image")
        {
            wx.MediaId = xml.SelectSingleNode("xml").SelectSingleNode("MediaId").InnerText;
        }
         
         return wx;
     }
           

如果我們在修改一下消息接受的代碼,就可以做到,客戶發一個照片給微信平台,程式檢測到時圖檔,然後根據MediaId,調用GetMultimedia方法把圖檔下載下傳到自己的伺服器上。後面的工作嘛,你就想幹什麼幹什麼了。

剛才的例子好像是使用者(關注者),發圖檔,然後通過微信平台到我們的伺服器中,還有一種情況,使用者發一個使用者名:例如“hemeng”,然後我需要調用已經存在伺服器中的hemeng頭像的圖檔回報給使用者,這怎麼辦呢?如何把我們的圖檔傳給微信平台,然後傳給使用者呢?我們就用到了上傳得方法:

/// <summary>
    /// 上傳多媒體檔案,傳回 MediaId
    /// </summary>
    /// <param name="ACCESS_TOKEN"></param>
    /// <param name="Type"></param>
    /// <returns></returns>
    public string UploadMultimedia(string ACCESS_TOKEN, string Type)
    {
        string result = "";
        string wxurl = "http://file.api.weixin.qq.com/cgi-bin/media/upload?access_token=" + ACCESS_TOKEN + "&type=" + Type;
        string filepath = Server.MapPath("image") + "\\hemeng80.jpg";(本地伺服器的位址)
        WriteLog("上傳路徑:" + filepath);
        WebClient myWebClient = new WebClient();
        myWebClient.Credentials = CredentialCache.DefaultCredentials;
        try
        {
            byte[] responseArray = myWebClient.UploadFile(wxurl, "POST", filepath);
            result = System.Text.Encoding.Default.GetString(responseArray, 0, responseArray.Length);
            WriteLog("上傳result:" + result);
            UploadMM _mode = JsonHelper.ParseFromJson<UploadMM>(result);
            result = _mode.media_id;
        }
        catch (Exception ex)
        {
            result = "Error:" + ex.Message;
        }
        WriteLog("上傳MediaId:" + result);
        return result;
    }
           

第二個參數如果是圖檔"image",可以參照微信的文檔。函數的傳回值就是一個MediaId,這樣你就可以利用發送圖檔的函數,發給客戶了,發送圖檔的函數如下:

protected string sendPicTextMessage(Msg _mode, string MediaId)
    {
        string res = string.Format(@"<xml>
                                            <ToUserName><![CDATA[{0}]]></ToUserName>
                                            <FromUserName><![CDATA[{1}]]></FromUserName>
                                            <CreateTime>{2}</CreateTime>
                                            <MsgType><![CDATA[image]]></MsgType>
                                            <Image>
                                            <MediaId><![CDATA[{3}]]></MediaId>
                                            </Image>
                                   </xml> ",
           _mode.FromUserName, _mode.ToUserName, DateTime.Now, MediaId);

        return res;
    }
           

其他視訊,語音的操作也類似,就不再備援介紹了。有了這些知識我們是不是能做不少應用了?當然是肯定的,但是我們的代碼還不夠優化,結構也不合理,不着急,我們會逐漸介紹到的,因為我們還沒有完全了解完微信的強大功能。

繼續閱讀