更改企业微信发送方式

This commit is contained in:
2025-12-04 16:37:03 +08:00
parent f8b635f060
commit 27551af823
2 changed files with 75 additions and 2 deletions

View File

@@ -175,4 +175,33 @@ public class WeChatUtil {
throw new RuntimeException("请求发送消息出错", e); throw new RuntimeException("请求发送消息出错", e);
} }
} }
/**
* 发送企业微信 Markdown 消息
* @param toUser 接收用户,'|' 分隔
* @param markdown Markdown 内容
*/
public void sendMarkdownMessage(String toUser, String markdown) {
String accessToken = getAccessToken();
String url = "https://qyapi.weixin.qq.com/cgi-bin/message/send?access_token=" + accessToken;
JSONObject msg = new JSONObject();
msg.put("touser", toUser);
msg.put("msgtype", "markdown");
msg.put("agentid", weChatConfig.getAgentId());
JSONObject md = new JSONObject();
md.put("content", markdown);
msg.put("markdown", md);
try {
String response = restTemplate.postForObject(url, msg, String.class);
JSONObject jsonResponse = JSONObject.parseObject(response);
if (jsonResponse.getIntValue("errcode") != 0) {
throw new RuntimeException("发送Markdown消息失败: " + jsonResponse.getString("errmsg"));
}
} catch (Exception e) {
throw new RuntimeException("请求发送Markdown消息出错", e);
}
}
} }

View File

@@ -243,12 +243,56 @@ public class NotificationManagementServiceImpl extends ServiceImpl<NotificationM
List<String> batch = studentNos.subList(i, Math.min(i + batchSize, studentNos.size())); List<String> batch = studentNos.subList(i, Math.min(i + batchSize, studentNos.size()));
// 拼接成"2023001|2023002|2023003"格式 // 拼接成"2023001|2023002|2023003"格式
String toUser = String.join("|", batch); String toUser = String.join("|", batch);
// 调用企业微信发送消息方法 // 如果内容包含超链接标签,转换为 Markdown
weChatUtil.sendTextMessage(toUser, content); String md = convertHtmlLinkToMarkdown(content);
if (md != null) {
weChatUtil.sendMarkdownMessage(toUser, md);
} else {
// 如果没有标签但包含 http 链接,直接发送文本也可点击
weChatUtil.sendTextMessage(toUser, content);
}
} }
} }
/**
* 将单个 a 标签的 HTML 转为 Markdown 格式;不匹配返回 null
*/
private String convertHtmlLinkToMarkdown(String html) {
if (html == null) return null;
String lower = html.toLowerCase();
if (!lower.contains("<a")) return null;
try {
// 简单提取 href 与锚文本
int aStart = lower.indexOf("<a");
int hrefStart = lower.indexOf("href", aStart);
if (hrefStart < 0) return null;
int quoteStart = lower.indexOf("\"", hrefStart);
int quoteStartSingle = lower.indexOf("'", hrefStart);
int qs = -1, qe = -1;
if (quoteStart >= 0 && (quoteStartSingle < 0 || quoteStart < quoteStartSingle)) {
qs = quoteStart;
qe = lower.indexOf("\"", qs + 1);
} else if (quoteStartSingle >= 0) {
qs = quoteStartSingle;
qe = lower.indexOf("'", qs + 1);
}
if (qs < 0 || qe < 0) return null;
String url = html.substring(qs + 1, qe).trim();
int textStart = lower.indexOf(">", qe) + 1;
int textEnd = lower.indexOf("</a>", textStart);
if (textStart <= 0 || textEnd <= textStart) return null;
String text = html.substring(textStart, textEnd).trim();
// 其余文本去掉标签
String before = html.substring(0, aStart).replaceAll("<[^>]+>", "");
String after = html.substring(textEnd + 4).replaceAll("<[^>]+>", "");
String mdLink = "[" + (text.isEmpty() ? url : text) + "](" + url + ")";
return before + mdLink + after;
} catch (Exception e) {
return null;
}
}
/** /**
* 根据年级获取学生学号列表 * 根据年级获取学生学号列表
* *