binarywang/WxJava · error · IllegalArgumentException

uri参数中不允许有access_token: {}

Error message

uri参数中不允许有access_token: {}

What it means

Thrown by BaseCpServiceImpl.executeInternal() when the supplied uri already contains the substring 'access_token='. The service appends access_token itself after fetching it from config storage, so a caller-provided token is treated as a misuse/leak risk and rejected with IllegalArgumentException before the request is sent.

Source

Thrown at weixin-java-cp/src/main/java/me/chanjar/weixin/cp/api/impl/BaseWxCpServiceImpl.java:394

  }

  /**
   * Execute internal t.
   *
   * @param <T>              the type parameter
   * @param <E>              the type parameter
   * @param executor         the executor
   * @param uri              the uri
   * @param data             the data
   * @param doNotAutoRefresh the do not auto refresh
   * @return the t
   * @throws WxErrorException the wx error exception
   */
  protected <T, E> T executeInternal(RequestExecutor<T, E> executor, String uri, E data, boolean doNotAutoRefresh) throws WxErrorException {
    E dataForLog = DataUtils.handleDataWithSecret(data);

    if (uri.contains("access_token=")) {
      throw new IllegalArgumentException("uri参数中不允许有access_token: " + uri);
    }
    String accessToken = getAccessToken(false);

    String uriWithAccessToken = uri + (uri.contains("?") ? "&" : "?") + "access_token=" + accessToken;

    try {
      T result = executor.execute(uriWithAccessToken, data, WxType.CP);
      log.debug("\n【请求地址】: {}\n【请求参数】:{}\n【响应数据】:{}", uriWithAccessToken, dataForLog, result);
      return result;
    } catch (WxErrorException e) {
      WxError error = e.getError();

      if (WxConsts.ACCESS_TOKEN_ERROR_CODES.contains(error.getErrorCode())) {
        // 强制设置wxCpConfigStorage它的access token过期了,这样在下一次请求里就会刷新access token
        this.configStorage.expireAccessToken();
        if (this.getWxCpConfigStorage().autoRefreshToken() && !doNotAutoRefresh) {
          log.warn("即将重新获取新的access_token,错误代码:{},错误信息:{}", error.getErrorCode(), error.getErrorMsg());
          //下一次不再自动重试

View on GitHub (pinned to 1c43293a3c)

Solutions

  1. Pass the bare endpoint URL without access_token; the service injects it from config storage.
  2. If using executeNormal with a pre-built URL, strip the access_token query param first.
  3. Avoid logging or caching full URLs that include tokens.

Example fix

// before
String url = "https://qyapi.weixin.qq.com/cgi-bin/...?access_token=" + token;
service.get(url, null);
// after
String url = "https://qyapi.weixin.qq.com/cgi-bin/...";
service.get(url, null); // token added by the service
Defensive patterns

Strategy: validation

Validate before calling

if (uri != null && uri.contains("access_token=")) {
  throw new IllegalArgumentException("uri must not include access_token; service injects it");
}
service.get(uri, null);

Type guard

static boolean uriHasToken(String uri) { return uri != null && uri.contains("access_token="); }

Try / catch

null

Prevention

When it happens

Trigger: A caller manually appends access_token to the URL (e.g. from a cached token), or passes a full WeChat URL that already includes the query parameter, or builds the URI from a template that pre-fills access_token.

Common situations: Copy-pasting a full WeChat API URL with token into the uri argument; migrating from a hand-rolled client that put the token in the URL; debugging code that hardcoded a token.

Related errors


AI-assisted analysis of binarywang/WxJava@1c43293a3c (2026-08-14). Data as JSON: /api/errors/05551c07e8cca41f. Report an issue: GitHub.