MyCATApache/Mycat-Server · error · RuntimeException
Unknown charsetIndex:
Error message
Unknown charsetIndex:
What it means
During the MySQL handshake, MySQLConnectionAuthenticator.processHandShakePacket reads the server's charset index from the handshake packet and maps it to a charset name via CharsetUtil.getCharset(). If the returned charset is null — the index is not present in MyCat's charset table — it throws this RuntimeException, aborting backend connection authentication.
Solutions
- Map the unknown charset index explicitly: add an entry to CharsetUtil's charset index table (or MyCat's charset config) for the reported index before connecting
- Configure the MySQL server (or the user account) to use a charset MyCat knows, e.g. SET GLOBAL character_set_server=utf8 or init_connect on the account
- Upgrade MyCat to a version whose CharsetUtil includes the server's collation ids
- Patch the code to fall back to a default charset (e.g. utf8) instead of throwing when the index is unmapped
Example fix
// before
if (charset != null) { source.setCharset(charset); } else { throw new RuntimeException("Unknown charsetIndex:" + charsetIndex); }
// after
if (charset != null) { source.setCharset(charset); } else { LOGGER.warn("Unknown charsetIndex:" + charsetIndex + ", fallback to utf8"); source.setCharset("utf8"); } Defensive patterns
Strategy: validation
Validate before calling
int idx = serverCharsetIndex & 0xff;
if (CharsetUtil.getCharset(idx) == null) {
throw new IllegalStateException("Server charset index " + idx + " unsupported; use a server charset MyCat knows (e.g. utf8)");
} Try / catch
try { connect(...); } catch (RuntimeException e) { if (e.getMessage().startsWith("Unknown charsetIndex:")) { /* reconfigure server charset or fallback */ } else { throw e; } } Prevention
- Pin the MySQL server's default charset to one MyCat's CharsetUtil maps (utf8/latin1/gbk)
- Check charset index support before upgrading the DB server version
- Add all expected collation ids to CharsetUtil in tests
When it happens
Trigger: The MySQL server sends a handshake packet whose serverCharsetIndex (serverCharsetIndex & 0xff) is not in MyCat's CharsetUtil mapping — typically a newer or unusual collation id, or a charset index for a charset MyCat does not know.
Common situations: Connecting to a newer MySQL (5.7/8.0) or MariaDB whose default collation id is absent from the old MyCat charset table; servers configured with uncommon default charsets like utf8mb4_0900_ai_ci (id 255) or gb18030; connecting through a proxy that alters the handshake.
Understand the failure class
Background: Invalid enum value errors: "Unknown type", "Invalid scope", "must be one of" — when a string is not on the library's allowed list — this error's family across 23 libraries.
Related errors
AI-assisted analysis of MyCATApache/Mycat-Server@65f8d8beb7 (2026-09-11).
Data as JSON: /api/errors/30300be63fd2392f.
Report an issue: GitHub.
Appendix: source
Thrown at src/main/java/io/mycat/backend/mysql/nio/MySQLConnectionAuthenticator.java:133
}
throw e;
}
}
private void processHandShakePacket(byte[] data) {
// 设置握手数据包
HandshakePacket packet= new HandshakePacket();
packet.read(data);
source.setHandshake(packet);
source.setThreadId(packet.threadId);
// 设置字符集编码
int charsetIndex = (packet.serverCharsetIndex & 0xff);
String charset = CharsetUtil.getCharset(charsetIndex);
if (charset != null) {
source.setCharset(charset);
} else {
throw new RuntimeException("Unknown charsetIndex:" + charsetIndex);
}
}
private void auth323(byte packetId) {
// 发送323响应认证数据包
Reply323Packet r323 = new Reply323Packet();
r323.packetId = ++packetId;
String pass = source.getPassword();
if (pass != null && pass.length() > 0) {
byte[] seed = source.getHandshake().seed;
r323.seed = SecurityUtil.scramble323(pass, new String(seed))
.getBytes();
}
r323.write(source);
}
}View on GitHub (pinned to 65f8d8beb7)