1. 程式人生 > >c# 呼叫阿里巴巴釘釘自定義機器人介面發訊息。

c# 呼叫阿里巴巴釘釘自定義機器人介面發訊息。

using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
/*****************************
 * 介面開發文件地址:https://open-doc.dingtalk.com/docs/doc.htm?spm=a219a.7629140.0.0.ABt1ET&treeId=257&articleId=105735&docType=1
 * 概要:阿里巴巴釘釘自定義機器人
 * 設計者:DuanXuWen
 * 設計時間:20180523
 * 版本:0.1
 * 修改者:
 * 修改時間:
 * ***************************/

namespace Common
{
    public class DinDinHelper
    {
        /// <summary>
        ///  呼叫自定義機器人發Txt訊息
        /// </summary>
        /// <param name="webhook">機器人管理-自定義-webhook</param>
        /// <param name="content">訊息內容</param>
        /// <param name="atMobiles">被@人的手機號</param>
        /// <param name="isAtAll">@所有人時:true,否則為:false</param>
        /// <param name="exception">返回內部異常</param>
        /// <returns>釘釘返回JObject</returns>
        public static JObject SendTxtMessage(string webhook, string content, string[] atMobiles, bool isAtAll, ref Exception exception)
        {
            try
            {
                string mobiles = GetAtMobiles(atMobiles);
                object message = new
                {
                    msgtype = "text",
                    text = new
                    {
                        content = (mobiles + content).Trim(),
                    },
                    at = new
                    {
                        atMobiles = atMobiles,
                        isAtAll = isAtAll
                    }
                };
                return SendMessage(webhook, message, ref exception);
            }
            catch (Exception ex)
            {
                exception = ex;
                throw;
            }
        }

        /// <summary>
        /// 呼叫自定義機器人發Link[分享]訊息
        /// </summary>
        /// <param name="webhook">機器人管理-自定義-webhook</param>
        /// <param name="text">訊息內容(注:如果太長只會部分展示)</param>
        /// <param name="title">訊息標題</param>
        /// <param name="picUrl">圖片URL</param>
        /// <param name="messageUrl">點選訊息跳轉的URL</param>
        /// <param name="exception">返回內部異常</param>
        /// <returns>釘釘返回JObject</returns>
        public static JObject SendLinkMessage(string webhook, string text, string title, string picUrl, string messageUrl, ref Exception exception)
        {
            try
            {
                object message = new
                {
                    msgtype = "link",
                    link = new
                    {
                        text = text,
                        title = title,
                        picUrl = picUrl,
                        messageUrl = messageUrl
                    },
                };
                return SendMessage(webhook, message, ref exception);
            }
            catch (Exception ex)
            {
                exception = ex;
                throw;
            }
        }

        /// <summary>
        /// 呼叫自定義機器人發Markdown訊息
        /// </summary>
        /// <param name="webhook">機器人管理-自定義-webhook</param>
        /// <param name="title">訊息標題</param>
        /// <param name="titleType">標題型別等級</param>
        /// <param name="markdownMessageList">訊息內容</param>
        /// <param name="atMobiles">被@手機號</param>
        /// <param name="isAtAll">@所有人時:true,否則為:false</param>
        /// <param name="exception">返回內部異常</param>
        /// <returns>釘釘返回JObject</returns>
        public static JObject SendMarkdownMessage(string webhook, string title, TitleType titleType, List<MarkdownMessage> markdownMessageList, string[] atMobiles, bool isAtAll, ref Exception exception)
        {
            try
            {
                //@手機號
                string mobiles = GetAtMobiles(atMobiles);
                //訊息內容頭部(標題+被@的人;注:自動換行)
                string textTop = GetContentGrade(titleType, title) + "\n >" + mobiles + "\n >";
                //訊息內容
                string text = textTop + GetNewMessage(markdownMessageList);
                object message = new
                {
                    msgtype = "markdown",
                    markdown = new
                    {
                        title = title,
                        text = text,
                    },
                    at = new
                    {
                        atMobiles = atMobiles,
                        isAtAll = isAtAll,
                    }
                };
                return SendMessage(webhook, message, ref exception);
            }
            catch (Exception ex)
            {
                exception = ex;
                throw;
            }
        }

        /// <summary>
        /// 呼叫自定義機器人發ActionCards訊息
        /// </summary>
        /// <param name="webhook">機器人管理-自定義-webhook</param>
        /// <param name="markdownMessageList">訊息內容</param>
        /// <param name="hideAvatar">0-正常發訊息者頭像,1-隱藏發訊息者頭像</param>
        /// <param name="btnOrientation">0-按鈕豎直排列,1-按鈕橫向排列</param>
        /// <param name="singleTitle">單個按鈕的方案。(設定此項和singleURL後btns無效。)</param>
        /// <param name="singleURL">點選singleTitle按鈕觸發的URL</param>
        /// <param name="exception">返回內部異常</param>
        /// <returns>釘釘返回JObject</returns>
        public static JObject SendActionCardsMessage(string webhook, List<MarkdownMessage> markdownMessageList, int hideAvatar, int btnOrientation, string singleTitle, string singleURL, ref Exception exception)
        {
            try
            {
                object message = new
                {
                    msgtype = "actionCard",
                    actionCard = new
                    {
                        text = GetNewMessage(markdownMessageList),
                        hideAvatar = hideAvatar,
                        btnOrientation = btnOrientation,
                        singleTitle = singleTitle,
                        singleURL = singleURL
                    },
                };
                return SendMessage(webhook, message, ref exception);
            }
            catch (Exception ex)
            {
                exception = ex;
                throw;
            }
        }

        /// <summary>
        /// 呼叫自定義機器人發ActionCard訊息
        /// </summary>
        /// <param name="webhook">機器人管理-自定義-webhook</param>
        /// <param name="markdownMessageList">訊息內容</param>
        /// <param name="hideAvatar">0-正常發訊息者頭像,1-隱藏發訊息者頭像</param>
        /// <param name="btnOrientation">0-按鈕豎直排列,1-按鈕橫向排列</param>
        /// <param name="btns">按鈕集合</param>
        /// <param name="exception">返回內部異常</param>
        /// <returns>釘釘返回JObject</returns>
        public static JObject SendActionCardMessage(string webhook, List<MarkdownMessage> markdownMessageList, int hideAvatar, int btnOrientation, Btns[] btns, ref Exception exception)
        {
            try
            {
                object message = new
                {
                    actionCard = new
                    {
                        text = GetNewMessage(markdownMessageList),
                        hideAvatar = hideAvatar,
                        btnOrientation = btnOrientation,
                        btns = btns
                    },
                    msgtype = "actionCard",
                };
                return SendMessage(webhook, message, ref exception);
            }
            catch (Exception ex)
            {
                exception = ex;
                throw;
            }
        }

        /// <summary>
        /// 呼叫自定義機器人發ActionCard訊息
        /// </summary>
        /// <param name="webhook">機器人管理-自定義-webhook</param>
        /// <param name="links">圖片按鈕集合</param>
        /// <param name="exception">返回內部異常</param>
        /// <returns>釘釘返回JObject</returns>
        public static JObject SendFeedCardMessage(string webhook, Links[] links, ref Exception exception)
        {
            try
            {
                object message = new
                {
                    feedCard = new
                    {
                        links = links,
                    },
                    msgtype = "feedCard"
                };
                return SendMessage(webhook, message, ref exception);
            }
            catch (Exception ex)
            {
                exception = ex;
                throw;
            }
        }

        /// <summary>
        /// 呼叫自定義機器人發訊息
        /// </summary>
        /// <param name="webhook">機器人管理-自定義-webhook</param>
        /// <param name="message">訊息資訊</param>
        /// <param name="exception">返回內部異常</param>
        /// <returns>釘釘返回JObject</returns>
        public static JObject SendMessage(string webhook, object message, ref Exception exception)
        {
            try
            {
                JObject jsons = null;
                System.Net.WebClient webclient = new System.Net.WebClient();
                string s = JsonConvert.SerializeObject(message);
                webclient.Headers.Add("Content-Type", "application/json; charset=utf-8");
                byte[] bytes = Encoding.UTF8.GetBytes(s);
                var arr = webclient.UploadData(webhook, "POST", bytes);
                string str = Encoding.UTF8.GetString(arr).ToString();
                webclient.Dispose();
                return jsons = (JObject)JsonConvert.DeserializeObject(str);
            }
            catch (Exception ex)
            {
                exception = ex;
                throw;
            }
        }

        /// <summary>
        /// 獲取訊息內容
        /// </summary>
        /// <param name="markdownMessageList">訊息內容</param>
        /// <returns>string</returns>
        private static string GetNewMessage(List<MarkdownMessage> markdownMessageList)
        {
            string text = "";
            foreach (var item in markdownMessageList.OrderBy(x => x.index))
            {
                if (item.markdownType == MarkdownType.文字)
                {
                    if (item.Text.contentType == ContentType.加粗)
                    {
                        item.Text.content = "**" + item.Text.content + "**";
                    }
                    if (item.Text.contentType == ContentType.斜體)
                    {
                        item.Text.content = "*" + item.Text.content + "*";
                    }
                    //文字等級賦值
                    item.Text.content = GetContentGrade(item.Text.contentGrade, item.Text.content);
                    //判斷是否換行
                    text += (item.isLineFeed) ? item.Text.content + "\n >" : item.Text.content;
                }
                if (item.markdownType == MarkdownType.圖片)
                {
                    text += (item.isLineFeed) ? "![screenshot](" + item.Text.imgurl + ")\n >" : "![screenshot](" + item.Text.imgurl + ")";
                }
                if (item.markdownType == MarkdownType.連結)
                {
                    text += (item.isLineFeed) ? "[" + item.Text.content + "](" + item.Text.url + ")\n >" : "[" + item.Text.content + "](" + item.Text.url + ")";
                }
            }
            return text;
        }

        /// <summary>
        /// 獲取被@人的手機號
        /// </summary>
        /// <param name="atMobiles">被@人的手機號</param>
        /// <returns>string</returns>
        private static string GetAtMobiles(string[] atMobiles)
        {
            string mobiles = "";
            if (atMobiles != null && atMobiles.ToList().Count() != 0)
            {
                foreach (var item in atMobiles)
                {
                    mobiles += "@" + item;
                }
            }
            return mobiles;
        }

        /// <summary>
        /// 獲取等級文字
        /// </summary>
        /// <param name="titleType">文字型別</param>
        /// <param name="title">文字</param>
        /// <returns>string</returns>
        private static string GetContentGrade(TitleType titleType, string title)
        {
            switch (titleType)
            {
                case TitleType.一級:
                    title = "# " + title;
                    break;
                case TitleType.二級:
                    title = "## " + title;
                    break;
                case TitleType.三級:
                    title = "### " + title;
                    break;
                case TitleType.四級:
                    title = "#### " + title;
                    break;
                case TitleType.五級:
                    title = "##### " + title;
                    break;
                case TitleType.六級:
                    title = "###### " + title;
                    break;
                default:
                    break;
            }
            return title;
        }
    }

    #region Class

    /// <summary>
    /// Markdown訊息內容類
    /// </summary>
    public class MarkdownMessage
    {
        /// <summary>
        /// 內容座標
        /// </summary>
        public int index { get; set; }

        /// <summary>
        /// 內容型別(文字、圖片、連結)
        /// </summary>
        public MarkdownType markdownType { get; set; }

        /// <summary>
        /// 內容(注:文字型別的內容中禁止字元["#"、"*"、"["、"]"、"!"];
        /// 圖片型別和連結型別的內容傳可訪問的http地址即可)
        /// </summary>
        public Text Text { get; set; }

        /// <summary>
        /// 是否換行
        /// </summary>
        public bool isLineFeed { get; set; }
    }

    /// <summary>
    /// 內容
    /// </summary>
    public class Text
    {
        /// <summary>
        /// 文字或連結顯示文字
        /// </summary>
        public string content { get; set; }

        /// <summary>
        /// 圖片連結
        /// </summary>
        public string imgurl { get; set; }

        /// <summary>
        /// 超連結地址
        /// </summary>
        public string url { get; set; }

        /// <summary>
        /// 文字型別
        /// </summary>
        public ContentType contentType { get; set; }

        /// <summary>
        /// 文字等級
        /// </summary>
        public TitleType contentGrade { get; set; }
    }

    /// <summary>
    /// 超連結按鈕
    /// </summary>
    public class Btns
    {
        /// <summary>
        /// 標題
        /// </summary>
        public string title { get; set; }

        /// <summary>
        /// 標題對應的超連結
        /// </summary>
        public string actionURL { get; set; }
    }

    /// <summary>
    /// 超連結按鈕帶圖片
    /// </summary>
    public class Links
    {
        /// <summary>
        /// 標題
        /// </summary>
        public string title { get; set; }

        /// <summary>
        /// 超連結
        /// </summary>
        public string messageURL { get; set; }

        /// <summary>
        /// 圖片超連結
        /// </summary>
        public string picURL { get; set; }
    }

    #endregion

    #region Enum

    /// <summary>
    /// 文字型別
    /// </summary>
    public enum ContentType
    {
        加粗 = 1,
        斜體 = 2,
    }

    /// <summary>
    /// Markdown訊息內容型別
    /// </summary>
    public enum MarkdownType
    {
        文字 = 1,
        圖片 = 2,
        連結 = 3,
    }

    /// <summary>
    /// 標題(文字)型別等級
    /// </summary>
    public enum TitleType
    {
        一級 = 1,
        二級 = 2,
        三級 = 3,
        四級 = 4,
        五級 = 5,
        六級 = 6,
    }

    #endregion
}