apache/shenyu · error · IllegalStateException
Not supported when there are multiple instances of external…
Error message
Not supported when there are multiple instances of external Tomcat.
What it means
PortUtils.getPort() discovers the embedded/external Tomcat HTTP connector port via JMX MBeans. The MBean query '*:type=Connector,*' returned more than one Connector object name, meaning multiple Tomcat instances (or connectors) are running in this JVM, so there is no single unambiguous port to return. The utility deliberately refuses to guess.
Solutions
- Remove or disable extra Tomcat connectors so exactly one HTTP Connector remains
- Configure the port explicitly in the client config (shenyu.client.<type>.props.port) instead of relying on auto-discovery
- Ensure only one Tomcat instance runs in the JVM; start others in separate processes
- Catch IllegalStateException and fall back to an explicitly configured port
Example fix
// before
int port = PortUtils.getPort();
// after
int port = props.containsKey("port")
? Integer.parseInt(props.getProperty("port"))
: PortUtils.getPort(); Defensive patterns
Strategy: try-catch
Validate before calling
int connectorCount = ManagementFactory.getPlatformMBeanServer()
.queryNames(new ObjectName("*:type=Connector,*"), null).size();
if (connectorCount > 1) { /* use explicit port from config */ } Try / catch
int port;
try { port = PortUtils.getPort(); }
catch (IllegalStateException e) { port = Integer.parseInt(props.getProperty("port")); } Prevention
- Keep exactly one Tomcat connector per JVM
- Always provide an explicit port in client config as fallback
- Avoid AJP connectors when using auto port discovery
When it happens
Trigger: Calling PortUtils.getPort() when the MBean server reports multiple 'Connector' MBeans — e.g. several external Tomcat instances in the same JVM, or multiple connectors configured in server.xml (HTTP + AJP, HTTPS + HTTP).
Common situations: Running several embedded Tomcat instances in one application; a server.xml with AJP or additional HTTPS connectors alongside the HTTP connector; deploying the ShenYu client into a shared Tomcat hosting multiple webapps with separate connectors.
Understand the failure class
Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.
Related errors
- failed to get the HTTP port of the current tomcat
- Cannot get the names of MBeans controlled by the MBean…
- shenyu.jwt.secretKey is not configured. In a multi-instance…
- shenyu discovery mode current didn't support
- websocket on client open failed, namespaceId is null
AI-assisted analysis of apache/shenyu@567142e072 (2026-09-12).
Data as JSON: /api/errors/6ce39132ac56d98c.
Report an issue: GitHub.
Appendix: source
Thrown at shenyu-client/shenyu-client-core/src/main/java/org/apache/shenyu/client/core/utils/PortUtils.java:99
return (int) method.invoke(bean);
}
/**
* get the current tomcat port number.
* Note: This method is not supported when there are multiple instances of external Tomcat.
*
* @return tomcat port number
* @throws Exception when failed to get port
*/
public static Integer getPort() throws Exception {
MBeanServer mBeanServer = ManagementFactory.getPlatformMBeanServer();
Set<ObjectName> objectNames = mBeanServer.queryNames(new ObjectName("*:type=Connector,*"), null);
if (CollectionUtils.isEmpty(objectNames)) {
throw new IllegalStateException("Cannot get the names of MBeans controlled by the MBean server.");
}
//This method is not supported when there are multiple instances of external Tomcat
if (objectNames.size() > 1) {
throw new IllegalStateException("Not supported when there are multiple instances of external Tomcat.");
}
ObjectName objectName = objectNames.iterator().next();
String protocol = String.valueOf(mBeanServer.getAttribute(objectName, "protocol"));
String port = String.valueOf(mBeanServer.getAttribute(objectName, "port"));
// The property name is HTTP1.1, org.apache.coyote.http11.Http11NioProtocol under linux
if ("HTTP/1.1".equals(protocol) || "org.apache.coyote.http11.Http11NioProtocol".equals(protocol)) {
return Integer.parseInt(port);
}
throw new IllegalStateException("failed to get the HTTP port of the current tomcat");
}
}
View on GitHub (pinned to 567142e072)