使用webhook推送消息给群中钉钉机器人或者用户

项目中需要给企业微信群使用钉钉机器人定时提醒功能,特此整理设计开发方案demo如下。这里简单介绍发送功能,后期定时调度再陆续更新。

一、创建钉钉群

创建步骤请参考: 自定义机器人接入,创建好机器人后,复制出机器人的Webhook地址。

二、根据Webhook发送至群消息

import com.alibaba.fastjson.JSON;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClientBuilder;
import org.apache.http.protocol.HTTP;
import org.apache.http.util.EntityUtils;
import java.io.File;
import java.util.HashMap;
import java.util.Map;

public class testSend {
    public static void main(String[] args) throws Exception {
        File[] disks = File.listRoots();
        long totalSpace = 0;
        long freeSpace = 0;
        for (File file : disks) {
            totalSpace += file.getTotalSpace();
            freeSpace += file.getFreeSpace();
        }
        double a = totalSpace / (1024 * 1024) / 1024;
        double b = freeSpace / (1024 * 1024) / 1024;
        double c = (b / a);
        if (c < 1) {
            // 钉钉的webhook
            String dingDingToken = "https://*.dingtalk.com/robot/send?access_token=***************";
            Map<String, Object> json = new HashMap();
            Map<String, Object> text = new HashMap();
            json.put("msgtype", "text");
            text.put("content", "磁盘的空间大小为:" + a + "G\n" + "磁盘的剩余空间大小为:" + b + "G\n剩余空间不足" + String.format("%.2f", c * 100) + "%");
            json.put("text", text);
            System.out.println(JSON.toJSONString(json));
            sendJSON(dingDingToken, JSON.toJSONString(json));
        }
    }
    public static String sendJSON(String url, String json) throws Exception {
        String res = "";
        CloseableHttpClient httpClient = HttpClientBuilder.create().build();

        HttpPost request = new HttpPost(url);
        StringEntity params = new StringEntity(json, HTTP.UTF_8);
        request.addHeader("content-type", "application/json");
        request.setEntity(params);
        CloseableHttpResponse response = httpClient.execute(request);
        res = EntityUtils.toString(response.getEntity(), HTTP.UTF_8);
        httpClient.close();
        return res;
    }
}

POM文件

 <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-jdbc</artifactId>
        </dependency>
        <dependency>
            <groupId>org.apache.httpcomponents</groupId>
            <artifactId>httpclient</artifactId>
            <version>4.5.5</version>
        </dependency>
        <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>fastjson</artifactId>
            <version>1.2.70</version>
        </dependency>
        <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>druid-spring-boot-starter</artifactId>
            <version>1.1.9</version>
        </dependency>
        <dependency>
            <groupId>com.oracle</groupId>
            <artifactId>ojdbc6</artifactId>
            <version>11.2.0</version>
        </dependency>
        <dependency>
            <groupId>commons-collections</groupId>
            <artifactId>commons-collections</artifactId>
            <version>3.2.2</version>
            <scope>compile</scope>
        </dependency>
        <dependency>
            <groupId>org.apache.commons</groupId>
            <artifactId>commons-lang3</artifactId>
        </dependency>
    </dependencies>

三、发送给用户,进行钉钉提醒

package com.common.util;

import com.dingtalk.api.DefaultDingTalkClient;
import com.dingtalk.api.DingTalkClient;
import com.dingtalk.api.request.OapiGettokenRequest;
import com.dingtalk.api.request.OapiMessageCorpconversationAsyncsendV2Request;
import com.dingtalk.api.request.OapiV2UserGetbymobileRequest;
import com.dingtalk.api.response.OapiGettokenResponse;
import com.dingtalk.api.response.OapiMessageCorpconversationAsyncsendV2Response;
import com.dingtalk.api.response.OapiV2UserGetbymobileResponse;
import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.databind.JsonMappingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.taobao.api.ApiException;
import lombok.extern.slf4j.Slf4j;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import java.io.IOException;
import java.text.MessageFormat;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

/**
 * @Description: 钉钉工具类
 */
@Slf4j
@Component
public class DingDingUtil {
    private static String appKey;

    private static String appSecret;

    private static long agentId;

    private static String getTokenUrl;

    private static String userGetByMobile;

    private static String messageCorpConversationAsyncsend;

    private static String getHcmUserByAdAccountUrl;
    @Value("${dingding.appKey}")
    public void setAppKey(String appKey) {
        DingDingUtil.appKey = appKey;
    }
    @Value("${dingding.appSecret}")
    public void setAppSecret(String appSecret) {
        DingDingUtil.appSecret = appSecret;
    }
    @Value("${dingding.agentId}")
    public void setAgentId(long agentId) {
        DingDingUtil.agentId = agentId;
    }
    @Value("${dingding.getToken}")
    public void setGetTokenUrl(String getTokenUrl) {
        DingDingUtil.getTokenUrl = getTokenUrl;
    }
    @Value("${dingding.userGetByMobile}")
    public void setUserGetByMobile(String userGetByMobile) {
        DingDingUtil.userGetByMobile = userGetByMobile;
    }
    @Value("${dingding.messageCorpConversationAsyncsend}")
    public void setMessageCorpConversationAsyncsend(String messageCorpConversationAsyncsend) {
        DingDingUtil.messageCorpConversationAsyncsend = messageCorpConversationAsyncsend;
    }
    @Value("${bkpaas.getHcmUserByAdAccount}")
    public void setGetHcmUserByAdAccountUrl(String getHcmUserByAdAccountUrl) {
        DingDingUtil.getHcmUserByAdAccountUrl = getHcmUserByAdAccountUrl;
    }

    public static String getToken()
    {
        String token="";
        String logText="";
        try {
            DingTalkClient client = new DefaultDingTalkClient(getTokenUrl);
            OapiGettokenRequest req = new OapiGettokenRequest();
            req.setAppkey(appKey);
            req.setAppsecret(appSecret);
            req.setHttpMethod("GET");
            OapiGettokenResponse rsp = client.execute(req);
            System.out.println(rsp.getBody());
            String bodyStr=rsp.getBody();
            ObjectMapper mapper = new ObjectMapper();
            //Json映射为对象
            Map<String,String> bodyMap = mapper.readValue(bodyStr, Map.class);
            token=bodyMap.get("access_token");
        } catch (ApiException e) {
            logText=MessageFormat.format("钉钉获取access token失败,异常:{0}",e.getMessage());
        } catch (JsonParseException e) {
            logText=MessageFormat.format("钉钉获取access token失败,异常:{0}",e.getMessage());
        } catch (JsonMappingException e) {
            logText=MessageFormat.format("钉钉获取access token失败,异常:{0}",e.getMessage());
        } catch (IOException e) {
            logText=MessageFormat.format("钉钉获取access token失败,异常:{0}",e.getMessage());
        }
        if(!logText.equals(""))
            log.error(logText);
        return token;
    }

    public static String getUserId(String accessToken,String mobile)
    {
        String userId="";
        String logText="";
        try {
            DingTalkClient client = new DefaultDingTalkClient(userGetByMobile);
            OapiV2UserGetbymobileRequest req = new OapiV2UserGetbymobileRequest();
            req.setMobile(mobile);
            OapiV2UserGetbymobileResponse rsp = client.execute(req, accessToken);
            String bodyStr=rsp.getBody();
            ObjectMapper mapper = new ObjectMapper();
            //Json映射为对象
            Map<String,Object> bodyMap = mapper.readValue(bodyStr, Map.class);
            Map<String,Object> resultMap=(Map) bodyMap.get("result");
            userId=resultMap.get("userid").toString();
        } catch (ApiException e) {
            logText=MessageFormat.format("钉钉获取手机号{0}的user id失败,异常:{1}",mobile,e.getMessage());
        } catch (JsonParseException e) {
            logText=MessageFormat.format("钉钉获取手机号{0}的user id失败,异常:{1}",mobile,e.getMessage());
        } catch (JsonMappingException e) {
            logText=MessageFormat.format("钉钉获取手机号{0}的user id失败,异常:{1}",mobile,e.getMessage());
        } catch (IOException e) {
            logText=MessageFormat.format("钉钉获取手机号{0}的user id失败,异常:{1}",mobile,e.getMessage());
        }
        if(!logText.equals(""))
            log.error(logText);
        return userId;
    }

    public static String getMobileByUserAccount(String account)
    {
        String mobile="";
        OkHttpClient client = new OkHttpClient().newBuilder()
                .build();
        Request request = new Request.Builder()
                .url(getHcmUserByAdAccountUrl+"/"+account)
                .method("GET", null)
                .addHeader("Cookie", "szcrowd.token_key=\"yKKce-oz7AzCaiAAAAAAF4AGcy1zZmM=\"")
                .build();
        try {
            Response response = client.newCall(request).execute();
            String bodyStr= response.body().string();
            ObjectMapper mapper = new ObjectMapper();
            //Json映射为对象
            Map<String,Object> bodyMap = mapper.readValue(bodyStr, Map.class);
            Boolean result=(Boolean) bodyMap.get("result");
            if(result)
            {
                Map<String,Object> dataMap= (Map)bodyMap.get("data");
                mobile=dataMap.get("ding_mobile").toString();
                String logText= MessageFormat.format("获取域账号{0}的手机号{1}成功",account,mobile);
                log.info(logText);
            }
        } catch (IOException e) {
            String logText=MessageFormat.format("获取域账号{0}的手机号失败,异常:{1}",account,e.getMessage());
            log.error(logText);
        }
        return mobile;
    }

    /*
    * @Description: 通过手机号发送钉钉消息,目前支持文本(text)和Markdown消息(markdown,需提供标题)类型
    * @Param: [mobileList, msgType, msg, title]
    * @return: java.lang.Boolean
    **/
    public static Boolean sendMsgByMobileList(List<String> mobileList,String msgType,String msg,String title)
    {
        Boolean sendResult=false;
        try {
            String accessToken=getToken();
            //获取user id
            List<String> userIdList=new ArrayList<>();
            for (String mobile:mobileList) {
                String userId=getUserId(accessToken,mobile);
                userIdList.add(userId);
            }
            String userIdStr=String.join(",",userIdList);
            DingTalkClient client = new DefaultDingTalkClient(messageCorpConversationAsyncsend);
            OapiMessageCorpconversationAsyncsendV2Request req = new OapiMessageCorpconversationAsyncsendV2Request();
            req.setAgentId(agentId);
            req.setToAllUser(false);
            req.setUseridList(userIdStr);
            OapiMessageCorpconversationAsyncsendV2Request.Msg obj1 = new OapiMessageCorpconversationAsyncsendV2Request.Msg();
            obj1.setMsgtype(msgType);
            OapiMessageCorpconversationAsyncsendV2Request.Text obj2 = new OapiMessageCorpconversationAsyncsendV2Request.Text();
            obj2.setContent(msg);
            obj1.setText(obj2);
            OapiMessageCorpconversationAsyncsendV2Request.Markdown obj3 = new OapiMessageCorpconversationAsyncsendV2Request.Markdown();
            obj3.setText(msg);
            obj3.setTitle(title);
            obj1.setMarkdown(obj3);
            req.setMsg(obj1);
            OapiMessageCorpconversationAsyncsendV2Response rsp = client.execute(req, accessToken);
            System.out.println(rsp.getBody());
            sendResult=true;
        } catch (ApiException e) {
            String logText=MessageFormat.format("通过手机号发送钉钉消息失败,异常:{0}",e.getMessage());
            log.error(logText);
        }
        return sendResult;
    }

    /*
    * @Description: 通过员工域账号发送钉钉消息,目前支持文本(text)和Markdown消息(markdown,需提供标题)类型
    * @Param: [accountList, msgType, msg, title]
    **/
    public static Boolean sendMsgByDomainAccountList(List<String> accountList,String msgType,String msg,String title)
    {
        List<String> mobileList=new ArrayList<>();
        for (String account:accountList) {
            String mobile=getMobileByUserAccount(account);
            mobileList.add(mobile);
        }
        Boolean sendResult=sendMsgByMobileList(mobileList,msgType,msg,title);
        return sendResult;
    }
}

application.yml

server:
  port: 9002
  servlet:
    context-path: /testProject
dingding:
  appKey: dingxbgxp**********
  appSecret: NBpYiuPU3MNxK2fdo9VNshTURKYI2SjZVHzxbx**********
  agentId: 1211016099
  getToken: http://oapi.dingtalk.com.internal/gettoken
  userGetByMobile: http://oapi.dingtalk.com.internal/topapi/v2/*** 
  messageCorpConversationAsyncsend: http://oapi.dingtalk.com.internal/topapi/message/***    

BzAbnormalMsgPushController.java触发方法

package com.modules.bz.controller;

import com.common.api.vo.Result;
import com.common.aspect.annotation.AutoLog;
import com.common.util.DingDingUtil;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;
import java.util.Arrays;
import java.util.List;

/**
 * @Description: 异常情况钉钉推送消息
 * @author: He JianPing
 */
@Slf4j
@RestController
@RequestMapping("/api/dingding")
@Api(value = "钉钉推送消息", tags = {"钉钉推送消息"})
public class BzAbnormalMsgPushController {

    @ApiOperation("推送数据校验异常消息")
    @AutoLog(value = "推送数据校验异常消息")
    @RequestMapping(value = "/push/verify", method = RequestMethod.POST)
    public Result getBgPanelIndex(String users,String msg)
    {
        Result<String> result=new Result<>();
        String [] usersArray=users.split(",");
        List<String> usersList= Arrays.asList(usersArray);
        DingDingUtil.sendMsgByDomainAccountList(usersList,"text",msg,"");
        result.setResult("OK");
        result.success("OK");
        return result;
    }
}

参考文章
https://blog.csdn.net/lonewolves/article/details/118598517
https://blog.csdn.net/weixin_37650458/article/details/105280528
https://blog.csdn.net/lonewolves/article/details/118598517

  • 1
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值