{"record":{"id":"48f7b56fe08f7158","repo":"apache/seatunnel","slug":"caller-is-not-a-cluster-member-calleraddress","errorCode":null,"errorMessage":"Caller is not a cluster member: ${callerAddress}","messagePattern":"Caller is not a cluster member: (.+?)","errorType":"exception","errorClass":"SecurityException","httpStatus":null,"severity":"error","filePath":"seatunnel-engine/seatunnel-engine-server/src/main/java/org/apache/seatunnel/engine/server/task/operation/GetMetricsOperation.java","lineNumber":68,"sourceCode":"    public GetMetricsOperation(Set<Long> runningJobIds) {\n        this.runningJobIds = runningJobIds;\n    }\n\n    public GetMetricsOperation(Set<Long> runningJobIds, String[] metricNamePrefixes) {\n        this.runningJobIds = runningJobIds;\n        this.metricNamePrefixes = metricNamePrefixes;\n    }\n\n    @Override\n    public void run() {\n        ILogger logger = getLogger();\n\n        Address callerAddress = getCallerAddress();\n\n        NodeEngineImpl nodeEngine = (NodeEngineImpl) getNodeEngine();\n        if (callerAddress == null\n                || nodeEngine.getClusterService().getMember(callerAddress) == null) {\n            throw new SecurityException(\"Caller is not a cluster member: \" + callerAddress);\n        }\n        Address masterAddress = getNodeEngine().getMasterAddress();\n        if (!callerAddress.equals(masterAddress)) {\n            throw new IllegalStateException(\n                    \"Caller \"\n                            + callerAddress\n                            + \" cannot get metrics\"\n                            + \" because it is not master. Master is: \"\n                            + masterAddress);\n        }\n        Predicate<MetricDescriptor> metricDescriptorPredicate =\n                dis -> {\n                    String jobIdStr = dis.tagValue(JOB_ID);\n                    if (jobIdStr == null) {\n                        return false;\n                    }\n                    long jobId;\n                    try {","sourceCodeStart":50,"sourceCodeEnd":86,"githubUrl":"https://github.com/apache/seatunnel/blob/cf67b549a7a6c35fa0beb12d83c62892427ea919/seatunnel-engine/seatunnel-engine-server/src/main/java/org/apache/seatunnel/engine/server/task/operation/GetMetricsOperation.java#L50-L86","documentation":"GetMetricsOperation.run() is a cluster operation that fetches task metrics. It first authenticates the caller: if the caller address is null or not a registered cluster member, it throws SecurityException to reject requests from non-member nodes (potential rogue/unauthorized node).","triggerScenarios":"run() invoked via Hazelcast operation dispatch where getCallerAddress() is null or nodeEngine.getClusterService().getMember(callerAddress) returns null — i.e. the operation arrives from an address not in the current member list.","commonSituations":"Stale client/server code invoking operations after the caller left the cluster; network misconfiguration with forged/mismatched addresses; test harness calling the operation outside a real cluster; split-brain leftovers.","solutions":["Ensure the caller node is a joined, healthy member of the same SeaTunnel cluster (check member list on both sides).","Verify all nodes use identical cluster discovery config (cluster name, seed addresses, network interfaces).","Restart the caller so it rejoins the cluster and obtains a valid membership.","Do not invoke internal metrics operations from outside the cluster; use the REST/Client APIs instead."],"exampleFix":null,"handlingStrategy":"validation","validationCode":"boolean isMember = nodeEngine.getClusterService().getMember(callerAddress) != null;\nif (!isMember) throw new SecurityException(\"caller not in cluster\");","typeGuard":null,"tryCatchPattern":"try { invokeGetMetrics(); } catch (SecurityException e) { if (e.getMessage().startsWith(\"Caller is not a cluster member\")) { rejoinClusterAndRetry(); } else { throw e; } }","preventionTips":["Use identical cluster discovery config on all nodes","Never call internal operations from outside the cluster","Rejoin the cluster after membership changes before issuing operations"],"tags":["security","cluster","metrics","authorization"],"backgroundTag":"insufficient-permissions","analyzedSha":"cf67b549a7a6c35fa0beb12d83c62892427ea919","analyzedAt":"2026-09-10T21:44:55.265Z","contentChangedAt":"2026-09-10T21:44:55.265Z","schemaVersion":2},"datasetVersion":"2026-09-14T16:17:12.679Z"}