binarywang/WxJava · error · WxErrorException
请先设置WebhookKey
Error message
请先设置WebhookKey
What it means
Thrown as WxErrorException (checked) by getWebhookUrl() in WxCpGroupRobotServiceImpl when the webhookKey is empty or not set in WxCpConfigStorage. The webhook key is the unique token appended to the group robot webhook URL; without it the robot endpoint cannot be constructed. This fires before any HTTP request on every send method (sendText, sendMarkdown, etc.) that relies on the default webhook URL.
Source
Thrown at weixin-java-cp/src/main/java/me/chanjar/weixin/cp/api/impl/WxCpGroupRobotServiceImpl.java:30
import java.util.List;
import static me.chanjar.weixin.cp.constant.WxCpConsts.GroupRobotMsgType;
/**
* 企业微信群机器人消息发送api 实现
*
* @author yr created on 2020-08-20
*/
@RequiredArgsConstructor
public class WxCpGroupRobotServiceImpl implements WxCpGroupRobotService {
private final WxCpService cpService;
private String getWebhookUrl() throws WxErrorException {
WxCpConfigStorage wxCpConfigStorage = this.cpService.getWxCpConfigStorage();
final String webhookKey = wxCpConfigStorage.getWebhookKey();
if (StringUtils.isEmpty(webhookKey)) {
throw new WxErrorException("请先设置WebhookKey");
}
return wxCpConfigStorage.getApiUrl(WxCpApiPathConsts.WEBHOOK_SEND) + webhookKey;
}
@Override
public void sendText(String content, List<String> mentionedList, List<String> mobileList) throws WxErrorException {
this.sendText(this.getWebhookUrl(), content, mentionedList, mobileList);
}
@Override
public void sendMarkdown(String content) throws WxErrorException {
this.sendMarkdown(this.getWebhookUrl(), content);
}
@Override
public void sendMarkdownV2(String content) throws WxErrorException {
this.sendMarkdownV2(this.getWebhookUrl(), content);
}View on GitHub (pinned to 1c43293a3c)
Solutions
- Extract the webhook key from the full webhook URL (the part after 'key=' in https://qyapi.weixin.qq.com/cgi-bin/webhook/send?key=XXX) and set it: ((WxCpDefaultConfigImpl) configStorage).setWebhookKey("XXX").
- If you already have the full webhook URL, use the overloaded send methods that accept a url parameter directly, bypassing getWebhookUrl().
- Verify the key is set before sending: if (StringUtils.isEmpty(configStorage.getWebhookKey())) set it first.
Example fix
// before
WxCpDefaultConfigImpl config = new WxCpDefaultConfigImpl();
config.setCorpId("corpId");
config.setCorpSecret("secret");
// webhook key never set
cpService.getGroupRobotService().sendText("hello", null, null); // throws
// after
config.setWebhookKey("12345678-abcd-efgh-ijkl-1234567890ab");
cpService.getGroupRobotService().sendText("hello", null, null); Defensive patterns
Strategy: validation
Validate before calling
if (StringUtils.isEmpty(cpService.getWxCpConfigStorage().getWebhookKey())) {
throw new IllegalStateException("WebhookKey is not configured; set it via configStorage.setWebhookKey(key)");
} Try / catch
try {
cpService.getGroupRobotService().sendText(content, mentionedList, mobileList);
} catch (WxErrorException e) {
if (e.getMessage().contains("WebhookKey")) {
// configure webhook key and retry
}
throw e;
} Prevention
- Extract the webhook key from the full webhook URL and set it on config storage at application startup.
- Use the overloaded send methods that accept a full URL if you prefer not to use config storage.
- Add a startup health check that verifies webhookKey is non-empty before the app accepts requests.
When it happens
Trigger: Calling any group robot send method (sendText, sendMarkdown, sendImage, sendNews, sendFile) without having set the webhook key on the config storage. The key is typically extracted from the webhook URL provided in WeCom group chat robot settings.
Common situations: Developer initializes WxCpService with corpId/secret but forgets to call configStorage.setWebhookKey(key) or setWebhookKey on the InMemoryConfigStorage. Or they confuse the app secret with the webhook key.
Related errors
AI-assisted analysis of binarywang/WxJava@1c43293a3c (2026-08-14).
Data as JSON: /api/errors/dd461c35d684e1df.
Report an issue: GitHub.