{"record":{"id":"21e7e9afa2ce49c3","repo":"JakeWharton/butterknife","slug":"must-have-return-type-of","errorCode":null,"errorMessage":" must have return type of ","messagePattern":" must have return type of ","errorType":"exception","errorClass":"IllegalStateException","httpStatus":null,"severity":"error","filePath":"butterknife-reflect/src/main/java/butterknife/ButterKnife.java","lineNumber":1003,"sourceCode":"          + \" must not be private or static\");\n    }\n    if ((modifiers & PUBLIC) == 0) {\n      object.setAccessible(true);\n    }\n  }\n\n  /** Returns true when the return value should be propagated. Use a default otherwise. */\n  private static boolean validateReturnType(Method method, Class<?> expected) {\n    Class<?> returnType = method.getReturnType();\n    if (returnType == void.class) {\n      return false;\n    }\n    if (returnType != expected) {\n      String expectedType = \"'\" + expected.getName() + \"'\";\n      if (expected != void.class) {\n        expectedType = \"'void' or \" + expectedType;\n      }\n      throw new IllegalStateException(method.getDeclaringClass().getName()\n          + \".\"\n          + method.getName()\n          + \" must have return type of \"\n          + expectedType);\n    }\n    return true;\n  }\n\n  private static boolean isRequired(Method method) {\n    return method.getAnnotation(Optional.class) == null;\n  }\n\n  private static ArgumentTransformer createArgumentTransformer(Method method,\n      Class<?>[] callbackParameterTypes) {\n    Class<?>[] targetParameterTypes = method.getParameterTypes();\n\n    int targetParameterLength = targetParameterTypes.length;\n    if (targetParameterLength == 0) {","sourceCodeStart":985,"sourceCodeEnd":1021,"githubUrl":"https://github.com/JakeWharton/butterknife/blob/fcdebedf3276096db2f51bf6372b849b5a9c75ed/butterknife-reflect/src/main/java/butterknife/ButterKnife.java#L985-L1021","documentation":"Thrown by ButterKnife's reflection binder when an @On* listener method declares a non-void return type that does not exactly match the expected type of the listener callback (e.g. boolean for OnTouchListener/OnLongClickListener/OnEditorActionListener). ButterKnife supports either void or the listener's own return type so return values propagate correctly; anything else is rejected.","triggerScenarios":"ButterKnife.bind(...) via butterknife-reflect where a method annotated @OnClick/@OnTouch/etc. returns a type that is neither void nor the callback's return type — e.g. `@OnTouch(R.id.area) boolean onTouch() {...}` on a listener whose callback returns void, or an @OnLongClick method returning String.","commonSituations":"Copying a listener implementation with the wrong signature, changing a handler to return a status object, or an @OnEditorActionListener method returning void while the framework expects boolean (silent behavior change) or vice versa. Compiler binder checks the same rule at build time; reflect defers it to bind time.","solutions":["Make the listener method return `void` when the return value is unused (ButterKnife supplies the default).","Or return exactly the listener callback's type: boolean for @OnLongClick/@OnTouch/@OnEditorActionListener, void for clicks/checked/text changes.","Match the parameter list too, then switch to butterknife-compiler for compile-time validation."],"exampleFix":"// before\n@OnLongClick(R.id.item) String onLongClick() { return \"ok\"; }\n\n// after\n@OnLongClick(R.id.item) boolean onLongClick() { return true; }","handlingStrategy":"validation","validationCode":"// Mirror of validateReturnType for an @OnLongClick method\nMethod m = ...;\nClass<?> rt = m.getReturnType();\nif (rt != void.class && rt != boolean.class) {\n  throw new IllegalStateException(m + \" must return void or boolean\");\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Return void for listeners whose return value you ignore.","Copy the exact callback signature from the wrapped listener interface (e.g. OnLongClickListener returns boolean).","Use butterknife-compiler so return types are checked at build time."],"tags":["butterknife","reflection","listener","return-type","annotation"],"backgroundTag":null,"analyzedSha":"fcdebedf3276096db2f51bf6372b849b5a9c75ed","analyzedAt":"2026-08-14T10:13:55.083Z","schemaVersion":2},"datasetVersion":"2026-08-14T10:17:34.591Z"}