apache/dolphinscheduler · error · RuntimeException

itemsList is null

Error message

itemsList is null

What it means

WeChatSender.markdownText parses the alert content string as a JSON array of LinkedHashMap objects to build the WeChat markdown message. If the content is non-empty but does not deserialize into a non-empty list (wrong shape or unparseable JSON), it logs 'itemsList is null' and throws this RuntimeException, refusing to send a malformed WeChat alert.

Source

Thrown at dolphinscheduler-alert/dolphinscheduler-alert-plugins/dolphinscheduler-alert-wechat/src/main/java/org/apache/dolphinscheduler/plugin/alert/wechat/WeChatSender.java:117

            log.info("Enterprise WeChat send [{}], param:{}, resp:{}",
                    url, data, resp);
            return resp;
        }
    }

    /**
     * convert text to markdown style
     *
     * @param title   the title
     * @param content the content
     * @return markdown text
     */
    private static String markdownText(String title, String content) {
        if (StringUtils.isNotEmpty(content)) {
            List<LinkedHashMap> mapItemsList = JSONUtils.toList(content, LinkedHashMap.class);
            if (null == mapItemsList || mapItemsList.isEmpty()) {
                log.error("itemsList is null");
                throw new RuntimeException("itemsList is null");
            }

            StringBuilder contents = new StringBuilder(100);
            contents.append(String.format("`%s`%n", title));
            for (LinkedHashMap mapItems : mapItemsList) {

                Set<Map.Entry<String, Object>> entries = mapItems.entrySet();
                for (Entry<String, Object> entry : entries) {
                    contents.append(WeChatAlertConstants.MARKDOWN_QUOTE);
                    contents.append(entry.getKey()).append(":").append(entry.getValue());
                    contents.append(WeChatAlertConstants.MARKDOWN_ENTER);
                }

            }
            return contents.toString();
        }
        return null;
    }

View on GitHub (pinned to 02eac45a1b)

Solutions

  1. Ensure the alert content is a JSON array of objects, e.g. '[{"title":"x","content":"y"}]', matching what markdownText expects.
  2. Check which alert template/format generated the content and switch the alert instance or template so it emits the list-of-maps JSON.
  3. Validate the alert data JSON with a JSON parser before the alert fires to catch malformed payloads early.

Example fix

// before: alert data passed to WeChat plugin
"task failed with exit code 1"
// after: JSON list of maps
"[{\"title\":\"task failed\",\"content\":\"exit code 1\"}]"
Defensive patterns

Strategy: validation

Validate before calling

List<LinkedHashMap> items = JSONUtils.toList(content, LinkedHashMap.class);
if (StringUtils.isEmpty(content) || items == null || items.isEmpty()) {
    throw new IllegalArgumentException("WeChat alert content must be a non-empty JSON array of objects: " + content);
}

Type guard

boolean isWeChatMarkdownPayload(String s) {
    if (s == null || !s.trim().startsWith("[")) return false;
    List<LinkedHashMap> l = JSONUtils.toList(s, LinkedHashMap.class);
    return l != null && !l.isEmpty();
}

Try / catch

try {
    weChatSender.send(alert);
} catch (RuntimeException e) {
    if ("itemsList is null".equals(e.getMessage())) {
        log.error("Alert content is not a JSON list of maps; check the alert template: {}", alert.getContent());
    }
}

Prevention

When it happens

Trigger: An alert reaches the WeChat plugin whose content is not a JSON array of objects — e.g. plain text alert data, an empty array '[]', or JSON that JSONUtils.toList cannot parse, while the content string itself is non-empty.

Common situations: Wiring a WeChat (markdown) alert to alert data produced for a different plugin (e.g. email/plain text formats); upstream alert payload format changed; alert content column contains text instead of the expected JSON list of maps.

Understand the failure class

Background: "failed to unmarshal" / json.Unmarshal errors: why parsing a response into a Go struct fails and how to fix it — this error's family across 23 libraries.

Related errors


AI-assisted analysis of apache/dolphinscheduler@02eac45a1b (2026-09-06). Data as JSON: /api/errors/9ebb73dc919ded96. Report an issue: GitHub.