apache/shenyu · error · NullPointerException
Key or data is null.
Error message
Key or data is null.
What it means
SignUtils.sign computes HMAC-style signatures via a map of supported algorithms. It explicitly throws NullPointerException when either the secret key or the data is null, and UnsupportedOperationException for unknown algorithm names. This fails fast instead of letting the signing function NPE deep inside.
Solutions
- Ensure the signing key is configured and non-null before calling sign.
- Null-check/guard the data (e.g. default empty string) prior to signing.
- Verify the sign plugin's selector/rule configuration contains the secret key.
- If null data is legitimate, decide on a canonical representation (empty string) and normalize inputs first.
Example fix
// before
String sign = SignUtils.sign("HmacSHA256", config.getKey(), body); // body may be null
// after
String sign = SignUtils.sign("HmacSHA256",
Objects.requireNonNull(config.getKey(), "sign key missing"),
body == null ? "" : body); Defensive patterns
Strategy: validation
Validate before calling
if (key == null || data == null) throw new IllegalArgumentException("key and data must be non-null before signing");
if (!SIGN_FUNCTION_MAP.containsKey(algorithmName)) throw new IllegalArgumentException("unsupported algorithm: " + algorithmName); Type guard
boolean signable = key != null && data != null && algorithmName != null;
Try / catch
try { return SignUtils.sign(alg, key, data); } catch (NullPointerException | UnsupportedOperationException e) { LOG.error("sign failed: {}", e.getMessage()); throw new SignatureException(e); } Prevention
- Fail fast on missing signing key at config load time
- Default null body to empty string before signing
- Keep the algorithm whitelist documented for plugin config
- Validate sign plugin config in admin before publishing rules
When it happens
Trigger: Calling SignUtils.sign(algorithmName, key, data) with a null key or null data string, e.g. when the configured secret is missing or the body to sign was not extracted.
Common situations: Sign plugin configured without a secret key; request body empty/null when building the signature; environment/config property for the key not set; upstream clients sending requests that bypass key extraction.
Related errors
- Access to localhost is not allowed
- Access to private or internal IP addresses is not allowed
- Access to sensitive ports is not allowed
- entry count exceeds maximum of " + maxEntryCount
- entry size exceeds maximum allowed value.
AI-assisted analysis of apache/shenyu@567142e072 (2026-09-12).
Data as JSON: /api/errors/f7c638e3b8277de0.
Report an issue: GitHub.
Appendix: source
Thrown at shenyu-common/src/main/java/org/apache/shenyu/common/utils/SignUtils.java:59
SIGN_MD5, (key, data) -> DigestUtils.md5Hex(data + key),
SIGN_HMD5, HmacHexUtils::hmacMd5Hex,
SIGN_HS256, HmacHexUtils::hmacSha256Hex,
SIGN_HS512, HmacHexUtils::hmacSha512Hex
);
/**
* Returns signature of data as hex string (lowercase).
*
* @param algorithmName the name of sign algorithm
* @param key key
* @param data data to sign
* @return signature
* @throws NullPointerException if key or data is null
* @throws UnsupportedOperationException if algorithmName isn't supported
*/
public static String sign(final String algorithmName, final String key, final String data) {
if (Objects.isNull(key) || Objects.isNull(data)) {
throw new NullPointerException("Key or data is null.");
}
return Optional.ofNullable(SIGN_FUNCTION_MAP.get(algorithmName))
.orElseThrow(() -> new UnsupportedOperationException("unsupported sign algorithm:" + algorithmName))
.sign(key, data);
}
/**
* Generate key string.
*
* @return the string
*/
public static String generateKey() {
return UUID.randomUUID().toString().replaceAll("-", "").toUpperCase();
}
@FunctionalInterface
private interface SignFunction {View on GitHub (pinned to 567142e072)