一、接入机器人
1.进入智能群助手
2.添加机器人
3.选择自定义:通过webhook接入自定义服务
4.设置关键字或加签:
设置关键字后:发送内容中包含设置的关键字之一才会发送成功
加签:请求时链接地址上加sign,如 $url = "{$url}×tamp={$time}&sign={$sign}";
群主/群成员可以在电脑端通过如下的路径添加自定义机器人:
步骤一:【电脑端钉钉 】-【群聊】-【群设置】-【智能群助手】-【添加更多】-【添加机器人】-【自定义】-【添加】,编辑机器人名称和选择添加的群组。
完成必要的安全设置(至少选择一种),勾选 我已阅读并同意《自定义机器人服务及免责条款》,点击“完成”即可。
二、代码实现
如果设置的敏感词,那么发送的消息中必须含有敏感词,才可以成功发送
如果设置了验签,那么必须要计算签名才可以发送
下面是验签方式的代码
方法一:
$url = 'webhook地址';
// 第一步,把timestamp+"\n"+密钥当做签名字符串,使用HmacSHA256算法计算签名,然后进行Base64 encode,最后再把签名参数再进行urlEncode,得到最终的签名(需要使用UTF-8字符集)。
$time = time() *1000;//毫秒级时间戳,我这里为了方便,直接把时间*1000了
$secret = '这是密钥';
$sign = hash_hmac('sha256', $time . "\n" . $secret,$secret,true);
$sign = base64_encode($sign);
$sign = urlencode($sign);
$msg = [
'msgtype' => 'text',//这是文件发送类型,可以根据需求调整
'text' => [
'content' => '这是需要发送的内容',
],
];
$url = "{$url}×tamp={$time}&sign={$sign}";
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false);
curl_setopt($curl, CURLOPT_POST, 1);
curl_setopt($curl, CURLOPT_POSTFIELDS, json_encode($msg));
curl_setopt($curl, CURLOPT_HEADER, 0);
curl_setopt($curl, CURLOPT_HTTPHEADER, ['Content-Type: application/json']);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
$res = curl_exec($curl);
curl_close($curl);
var_dump($res);
方法二:
function sendMessage2DingTalk($msg, $secret, $accessToken)
{
// 当前时间(毫秒)
$timestamp = time() * 1000;
// HmacSHA256加密,设置为 true 输出原始二进制数据
$hmacsha256 = hash_hmac('sha256', $timestamp . "
" . $secret, $secret, true);
// 请求参数
$param = [
'access_token' => $accessToken,
'timestamp' => $timestamp,
// 签名值
'sign' => urlencode(base64_encode($hmacsha256))
];
// Webhook地址
$webhook = "https://oapi.dingtalk.com/robot/send?" . http_build_query($param);
// 发送消息
$options = [
'http' => [
// 请求方法
'method' => "POST",
// 请求格式为json
'header' => "Content-type:application/json;charset=utf-8
",
// 请求内容
'content' => $msg
],
// 不验证ssl证书
"ssl" => [
"verify_peer" => false,
"verify_peer_name" => false
]
];
return file_get_contents($webhook, false, stream_context_create($options));
}
sendMessage2DingTalk('{"msgtype":"text","text":{"content":"我就是我, 是不一样的烟火啊"}}', "SECxxx", "xxx");
我的代码
//加签机器人
// 当前时间(毫秒)
$timestamp = time() * 1000;
$secret = 'SEC5384c3***ea1719c1be2e3fff3';//秘钥
$signStr = getSign($timestamp, $secret);
$webhookUrl = "https://oapi.dingtalk.com/robot/send?access_token=d9e39e***134d71" . $signStr;
define('DING_TALK', $webhookUrl);
$robot = new Plugin_Robot;
//获取签名参数
function getSign($timestamp = 0, $secret = '')
{
$signStr = hash_hmac('sha256', $timestamp . "\n" . $secret, $secret, true);
$signStr = urlencode(base64_encode($signStr));
$params = '&' . http_build_query(['timestamp' => $timestamp, 'sign' => $signStr]);
return $params;
}
$date = date('Y-m-d H:i:s');
$res=$robot->text('test');
//*****robot.php****//
//发送text文本信息
public function text($content = '', $mobiles = [], $userIds = [], $isAtAll = false)
{
$sendContent = [
"msgtype" => "text",
"text" => [
"content" => $content
],
"at" => [
"atMobiles" => $mobiles,
"atUserIds" => $userIds, //不是钉钉管理员无法获取userIds
"isAtAll" => $isAtAll
]
];
$res = $this->_curl_post_json($this->webhookurl, $sendContent);
return $res;
}
//发送json数据
public function _curl_post_json($url, $data = array())
{
$curl = curl_init($url);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false);
curl_setopt($curl, CURLOPT_CONNECTTIMEOUT, 5);
curl_setopt($curl, CURLOPT_POST, 1);
curl_setopt($curl, CURLOPT_POSTFIELDS, json_encode($data, 320));
curl_setopt($curl, CURLOPT_HEADER, 0);
curl_setopt($curl, CURLOPT_HTTPHEADER, ['Content-Type: application/json']);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
$res = curl_exec($curl);
curl_close($curl);
return $res;
}
设置关键字
//webhook 地址
define('DING_TALK', 'https://oapi.dingtalk.com/robot/send?access_token=XXX');//钉钉机器人
//curl发送json数据
function curl_post_json($url, $data = array(), $header = array(), $timeout = 80, $port = 80){
$curl = curl_init($url);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false);
curl_setopt($curl, CURLOPT_POST, 1);
curl_setopt($curl, CURLOPT_POSTFIELDS, json_encode($data,320));
curl_setopt($curl, CURLOPT_HEADER, 0);
curl_setopt($curl, CURLOPT_HTTPHEADER, ['Content-Type: application/json']);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
$res = curl_exec($curl);
curl_close($curl);
return $res;
}
//发送逻辑
$resStr = $search_result;
if (strlen($search_result) > 4000){ //markdown格式的消息,最大不超过5000字符。
$resStr = substr($search_result, 0, 1000) . '...' . substr($search_result, -1000);
}
$voiceContent = "### **监控:**" . $type .
" \n #### **查询条件:** \n " . $noticeData['search_cond'] .
" \n #### **查询结果:** \n " . $resStr .
" \n #### **错误原因:** " . $noticeData['content'] . ':查询超时';
$talkContent = [
"msgtype" => "markdown",//这是文件发送类型,可以根据需求调整
"markdown" => [
"title" => "访问异常通知",
"text" => $voiceContent
]];
$res = curl_post_json(DING_TALK, $talkContent);
$errcode = json_decode($res, true)['errcode'];
三、最后看效果图
四、注意事项
最近在做告警系统的过程中,需要用到钉钉机器人进行告警,创建自定义机器人后,发送相关消息。我们需要@群内的相关人员,使用过程中发现只有text类型的消息支持@相关人,其余类型不支持。百思不得其解,下面是钉钉的开发文档
如需要@人,只需要在at这个json对象中加入对应手机号就ok,text['content']中不用写@手机号,而其他类型的消息,比如MarkDown类型则不能@相关人,但可以设置 at['isAtAll'] 为true ,来进行 @所有人
起初我以为是我哪里配置的问题,找了很久始终没有找到原因。最后提了工单,他们告诉我在text中也要把手机号当作文本拼接在后面
文档中没有任何说明,而且这是什么反人类的设计……坑啊!
$markdown="#### 杭州天气 \n > 9度,西北风1级,空气良89,相对温度73% @18**01 \n > ![screenshot](https://t7.baidu.com/it/u=3691080281,11347921&fm=193&f=GIF)\n > ###### 10点20分发布 相关负责关注是否需要处理异常数据 [天气](https://image.so.com/) \n ";
$res2 = $robot->markdown('我是预警标题', $markdown, ["18**01",'1851**33']);
var_dump($res2, $date);
记录一下,避免大家遇到类似的问题
参考:
钉钉-消息类型与数据格式_lxw1844912514的博客-CSDN博客