2009-07-15 3 views
3

Я изменил тип возврата одного метода в интерфейсе в библиотеке. Раньше это было пусто, и я изменил его, чтобы вернуть объект. Я не изменял код в своем модуле, так как я не хотел ничего делать с возвращенным объектом (он был для другого модуля). Я скомпилировал мой модуль с новым банком библиотеки и провел единичные тесты, которые работали нормально, но когда я нажал банку вместе с библиотекой jar для производства и запускает модуль, я получаю java.lang.NoSuchMethodError для метода, который я изменил на интерфейсе. Я изменил интерфейс, а также реализацию, оба находятся в библиотечном банке, и я использую весенние аннотации, чтобы внедрить объект реализации в мой модуль. Какова возможная причина этой проблемы?изменение типа возвращаемого метода дает java.lang.NoSuchMethodError

ответ

6

Похоже, вы не перекомпилировали все или не перетащили все перекомпилированные файлы jar в prod.

Кроме того, вы не указали, перезагрузили ли вы сервер. Если у вас есть какой-то «горячий перезапуск», вам нужно тщательно настроить все загрузчики классов, чтобы все было правильно. Если вы можете полностью перезагрузить контейнер, это может помочь.

0

Удалили ли вы среду своего развертывания производства, поскольку кажется, что старая сигнатура метода все еще висит где-то?

0

Мы всегда настраиваем процесс сборки (и QA), чтобы очистить все классы и перекомпилировать именно из-за таких проблем. Иногда эвристика зависимости компилятора ошибочна (особенно если у вас есть статическое конечное поле, определенное как константа, где компилятор просто оптимизирует всю зависимость).

В этом случае, хотя код с использованием метода не изменился (фактически, потому что он не изменился), скомпилированный байт-код не разрешает правильную подпись метода и не может найти то, что он искал. На уровне байткода есть ссылка на тип возврата, который JVM просматривает и не находит.

0

void не является подтипом другого типа. Поэтому, если вы измените интерфейс, чтобы вернуть тип не void, тогда классы реализации, которые все еще возвращают void, больше не будут совместимы с этим методом.

5

В байт-коде Java возвращаемый тип метода является частью сигнатуры метода и он различает два метода с тем же именем и с теми же параметрами (это то, что вы не можете сделать на языке Java). Таким образом, ваш код, который вызывает этот метод, каким-то образом не перекомпилировался и по-прежнему пытается вызвать метод, который возвращает void.

Смежные вопросы