apache/dubbo · error · IllegalArgumentException

Invoke method [{}] argument number error.

Error message

Invoke method [{}] argument number error.

What it means

Thrown by OBJECT_WRAPPER.invokeMethod when the method name is "equals" but the args array does not have exactly one element. The equals contract requires a single argument; any other arity is treated as a programming error.

Source

Thrown at dubbo-common/src/main/java/org/apache/dubbo/common/bytecode/Wrapper.java:101

        }

        @Override
        public Object invokeMethod(Object instance, String mn, Class<?>[] types, Object[] args)
                throws NoSuchMethodException {
            if ("getClass".equals(mn)) {
                return instance.getClass();
            }
            if ("hashCode".equals(mn)) {
                return instance.hashCode();
            }
            if ("toString".equals(mn)) {
                return instance.toString();
            }
            if ("equals".equals(mn)) {
                if (args.length == 1) {
                    return instance.equals(args[0]);
                }
                throw new IllegalArgumentException("Invoke method [" + mn + "] argument number error.");
            }
            throw new NoSuchMethodException("Method [" + mn + "] not found.");
        }
    };
    private static AtomicLong WRAPPER_CLASS_COUNTER = new AtomicLong(0);

    /**
     * get wrapper.
     *
     * @param c Class instance.
     * @return Wrapper instance(not null).
     */
    public static Wrapper getWrapper(Class<?> c) {
        return ConcurrentHashMapUtils.computeIfAbsent(WRAPPER_MAP, c, (clazz) -> {
            while (ClassGenerator.isDynamicClass(clazz)) // can not wrapper on dynamic class.
            {
                clazz = clazz.getSuperclass();
            }

View on GitHub (pinned to 3a3043227f)

Solutions

  1. Ensure "equals" is always invoked with exactly one argument.
  2. Validate args.length against the method's expected parameter count before dispatch.
  3. If you did not intend to call equals, check for a method-name collision in your invocation metadata.

Example fix

// before
wrapper.invokeMethod(obj, "equals", new Class[]{}, new Object[]{});
// after
wrapper.invokeMethod(obj, "equals", new Class[]{Object.class}, new Object[]{other});
Defensive patterns

Strategy: validation

Validate before calling

if ("equals".equals(methodName) && args != null && args.length == 1) {
    wrapper.invokeMethod(instance, methodName, types, args);
} else {
    // wrong arity for equals; reject before dispatch
}

Type guard

static boolean isValidEqualsCall(String mn, Object[] args) {
    return !"equals".equals(mn) || (args != null && args.length == 1);
}

Try / catch

try {
    wrapper.invokeMethod(instance, mn, types, args);
} catch (IllegalArgumentException e) {
    // method arity mismatch; correct the args array
}

Prevention

When it happens

Trigger: Calling wrapper.invokeMethod(instance, "equals", types, args) where args.length != 1 (typically 0 or 2+). Happens in generic-invocation argument wiring where equals is dispatched with the wrong argument count.

Common situations: A custom InvocationHandler or test harness invokes equals with zero or multiple arguments. Mismatched method metadata between provider and consumer can also produce a zero-length args array for an equals call.

Related errors


AI-assisted analysis of apache/dubbo@3a3043227f (2026-08-14). Data as JSON: /api/errors/f1ab5726c2465d80. Report an issue: GitHub.