MyCATApache/Mycat-Server · error · java.lang.RuntimeException

Can't identify the operation of of where

Error message

Can't identify the operation of  of where

What it means

JoinParser parses a join query's WHERE clause and only understands equality (=), AND and OR binary operators (and IN-lists). Any other binary operator in the WHERE expression reaches the final else branch, which throws a RuntimeException. It is a parser capability limit of the catlet join SQL parser, not a syntax error in your SQL.

Solutions

  1. Rewrite the WHERE clause of the join query to use only = combined with AND/OR/IN when going through the join catlet
  2. Push non-equality predicates (range, LIKE) to a subquery or to the single-node query instead of the join parser
  3. Set the table/route so the query does not go through the JoinParser path (e.g. direct route to a single node)
  4. Patch JoinParser.parserWhere to handle the operator you need, or upgrade to a Mycat version with broader operator support

Example fix

// before
... JOIN b ON a.id=b.id WHERE a.created > '2024-01-01'
// after (filter applied outside join parser, e.g. subquery)
SELECT * FROM a JOIN b ON a.id=b.id WHERE a.id IN (SELECT id FROM a WHERE created > '2024-01-01')
Defensive patterns

Strategy: validation

Validate before calling

// pre-validate WHERE clause before invoking the join catlet path
java.util.regex.Pattern allowed = java.util.regex.Pattern.compile(
    "(\\s*(AND|OR)\\s+)?\\s*\\w+\\.\\w+\\s*(=|IN)\\s*", java.util.regex.Pattern.CASE_INSENSITIVE);
// reject if where contains >, <, LIKE, != etc. and reroute to single-node execution

Type guard

boolean isJoinParserSafe(SQLBinaryOperator op) {
    return op == SQLBinaryOperator.Equality
        || op == SQLBinaryOperator.BooleanAnd
        || op == SQLBinaryOperator.BooleanOr;
}

Try / catch

try {
    joinExec.execute(query);
} catch (RuntimeException e) {
    if (e.getMessage() != null && e.getMessage().startsWith("Can't identify the operation")) {
        LOG.warn("unsupported where operator for join catlet, falling back to direct route");
        return directNodeExecute(query);
    }
    throw e;
}

Prevention

When it happens

Trigger: Running a JOIN query through a catlet (e.g. ShareJoin / JoinParser path) whose WHERE clause contains an operator other than =, AND, OR, or IN — such as >, <, >=, LIKE, <>, or BETWEEN in the where section handled by parserWhere.

Common situations: Users writing range filters or LIKE predicates in a join query routed via a catlet; queries generated by ORMs that emit != or LIKE; upgrading SQL and adding non-equality predicates to an existing working join.

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


AI-assisted analysis of MyCATApache/Mycat-Server@65f8d8beb7 (2026-09-11). Data as JSON: /api/errors/5603e28bb8aad41e. Report an issue: GitHub.

Appendix: source

Thrown at src/main/java/io/mycat/catlets/JoinParser.java:246

	     if (aexpr instanceof SQLBinaryOpExpr){
		   SQLBinaryOpExpr expr=(SQLBinaryOpExpr)aexpr;  
		   SQLExpr exprL=expr.getLeft();
		   if (!(exprL instanceof SQLBinaryOpExpr))
		   {
			  opSQLExpr((SQLBinaryOpExpr)aexpr,Operator);			  
		   }
		   else {
			// if (expr.getOperator().getName().equals("AND")) { 
			 if (expr.getOperator()==SQLBinaryOperator.BooleanAnd) { 	 
			   //parserWhere(exprL); 
			   //parserWhere(expr.getRight());
			   andorWhere(exprL,expr.getOperator().getName(),expr.getRight());
			 }
			 else if (expr.getOperator()==SQLBinaryOperator.BooleanOr){//.getName().equals("OR")) {  
				andorWhere(exprL,expr.getOperator().getName(),expr.getRight()); 				
			 }
			 else {
				 throw new RuntimeException("Can't identify the operation of  of where"); 
			 }
		   }
	   }else if(aexpr instanceof SQLInListExpr){
		   SQLInListExpr expr = (SQLInListExpr)aexpr;
		   SQLExpr exprL =  expr.getExpr();
		   String field=exprL.toString();
		   tableFilter.addWhere(field, SQLUtils.toMySqlString(expr), Operator);
	   }
	     
	}
	
	private void andorWhere(SQLExpr exprL,String Operator,SQLExpr exprR ){ 
		   parserWhere(exprL,"");
		   parserWhere(exprR,Operator);
	}	
	   
    private void opSQLExpr(SQLBinaryOpExpr expr,String Operator) {
		   if (expr==null) {

View on GitHub (pinned to 65f8d8beb7)