{"record":{"id":"e953ea4067e4fd34","repo":"didi/DoKit","slug":"no-similar-method-name-with-params-types-cou","errorCode":null,"errorMessage":"No similar method ${name} with params ${types} could be found on type ${type}.","messagePattern":"No similar method (.+?) with params (.+?) could be found on type (.+?)\\.","errorType":"exception","errorClass":"NoSuchMethodException","httpStatus":null,"severity":"error","filePath":"Android/dokit-util/src/main/java/com/didichuxing/doraemonkit/util/ReflectUtils.java","lineNumber":361,"sourceCode":"        }\n        if (!methods.isEmpty()) {\n            sortMethods(methods);\n            return methods.get(0);\n        }\n        do {\n            for (Method method : type.getDeclaredMethods()) {\n                if (isSimilarSignature(method, name, types)) {\n                    methods.add(method);\n                }\n            }\n            if (!methods.isEmpty()) {\n                sortMethods(methods);\n                return methods.get(0);\n            }\n            type = type.getSuperclass();\n        } while (type != null);\n\n        throw new NoSuchMethodException(\"No similar method \" + name + \" with params \"\n                + Arrays.toString(types) + \" could be found on type \" + type() + \".\");\n    }\n\n    private void sortMethods(final List<Method> methods) {\n        Collections.sort(methods, new Comparator<Method>() {\n            @Override\n            public int compare(Method o1, Method o2) {\n                Class<?>[] types1 = o1.getParameterTypes();\n                Class<?>[] types2 = o2.getParameterTypes();\n                int len = types1.length;\n                for (int i = 0; i < len; i++) {\n                    if (!types1[i].equals(types2[i])) {\n                        if (wrapper(types1[i]).isAssignableFrom(wrapper(types2[i]))) {\n                            return 1;\n                        } else {\n                            return -1;\n                        }\n                    }","sourceCodeStart":343,"sourceCodeEnd":379,"githubUrl":"https://github.com/didi/DoKit/blob/626827cddb2feb2f3aee87a52a064b4e5ca2bed4/Android/dokit-util/src/main/java/com/didichuxing/doraemonkit/util/ReflectUtils.java#L343-L379","documentation":"ReflectUtils.similarMethod(name, types) walks the class hierarchy comparing declared methods with isSimilarSignature (name match plus boxed-type-compatible parameters). If no class in the chain declares a matching method, it throws NoSuchMethodException with the method name, parameter types and originating type. 'Similar' means parameter types are compared leniently (primitives vs wrappers), but the method name must match exactly and accessibility is not considered at this stage.","triggerScenarios":"Calling reflect().method(\"toString\", ...) misspelled (e.g. \"tostring\"); passing wrong arity or incompatible parameter types; target method living in an interface rather than a class (getDeclaredMethods on the implementing class still shows it, but a proxy-only type may not); calling before the right class loader loaded the class.","commonSituations":"Version changes of a third-party library renaming or removing a reflected method (classic proguard/R8 issue — reflection breaking after minification); wrong parameter boxing (passing Integer where double is expected); invoking on the wrong type variable after refactoring.","solutions":["Verify the method name spelled exactly and parameter types/arity against the target class (javap or the source).","Add proguard/R8 keep rules for classes accessed via ReflectUtils.","Pass wrapper types matching the declared signature, or use the no-arg method(...) variant when applicable.","Catch NoSuchMethodException and degrade gracefully if the reflected API is optional."],"exampleFix":"// before\nMethod m = ReflectUtils.on(view).reflect().method(\"setTex\", CharSequence.class).get();\n\n// after\nMethod m = ReflectUtils.on(view).reflect().method(\"setText\", CharSequence.class).get();","handlingStrategy":"try-catch","validationCode":"boolean exists = false;\nfor (Method m : targetClass.getMethods()) {\n    if (m.getName().equals(name) && m.getParameterCount() == expectedArity) { exists = true; break; }\n}","typeGuard":null,"tryCatchPattern":"try {\n    Method m = ReflectUtils.on(obj).reflect().method(\"setText\", CharSequence.class).get();\n} catch (NoSuchMethodException e) {\n    // optional API absent: degrade gracefully, log once\n}","preventionTips":["Add R8/ProGuard keep rules for every class touched by ReflectUtils.","Write a startup smoke test that reflects each required method.","Double-check method spelling and boxed parameter types against the real signature."],"tags":["reflection","nosuchmethod","obfuscation"],"backgroundTag":null,"analyzedSha":"626827cddb2feb2f3aee87a52a064b4e5ca2bed4","analyzedAt":"2026-08-14T12:45:58.758Z","schemaVersion":2},"datasetVersion":"2026-08-15T17:31:12.345Z"}