Это правильный способ использования javax.annotation из JSR305? - PullRequest
5 голосов
/ 13 мая 2009

Я недавно добавил RI для JSR305 в свой проект и добавляю аннотации к моим интерфейсам, например:

public interface AccountService
{
    @Nullable AccountResult consolidate( @Nonnull Date from, @Nonnull Date to )
}

В духе JSR (как описано здесь), вы думаете, я неправильно использую аннотации, используя их в интерфейсах? Я хочу указать, что возвращаемое значение может быть нулевым, но я думаю, что @Nullable больше применяется к методу «консолидировать». Я не добавляю их в реализации, потому что когда я пишу код, мой интерфейс - код для интерфейса.

Ответы [ 2 ]

6 голосов
/ 16 августа 2009

Вы можете видеть '@NonNull String' как строгий подкласс String. В конце концов, любая ненулевая строка определенно является 'instanceof' '@Nullable String', но любой экземпляр '@Nullable String' может не быть экземпляром '@NonNull String' (это не было бы, если бы оно был ноль, например).

Глядя на это таким образом, @Nullable и @NonNull - это информация о типах, и поэтому они совершенно разумны в интерфейсах. Вы указываете реализаторам, что они могут возвратить ноль, и что им не нужно беспокоиться о вводимых нулях, и вы указываете вызывающим, что они не должны передавать нулевое значение и что они должны ожидать нулевые значения.

Конечно, хотя все это очень разумно, vanilla javac v1.6 определенно не применяет ни одно из этих правил, как это обеспечивает безопасность типов для реальных типов. Но можно мечтать или использовать что-то вроде pmd или findbugs для проверки этих аннотаций.

Однако аннотаций @NonNull и @Nullable недостаточно для полной системы набора недействительности. Я действительно не знаю, почему JSR305 не решает эту проблему, но есть третий тип: "@MaybeNull". Это будет отображаться внутри общих параметров; в любом другом месте это будет иметь то же значение, что и @ Nullable.

public static void addIfNotNull (список List <@MaybeNull T>, элемент @Nullable T) { if (item! = null) list.add (item); }

Если в первой букве 'T' есть аннотация "@Nullable", то вы не могли бы передавать ненулевые списки, что создавало бы довольно бесполезный API. С другой стороны, если бы это был @NonNull, вы не могли бы передать в него обнуляемый список. На практике не имеет значения, что вы там перемещаете, это (A) никогда не вызовет исключение NullPointerException, и (B) никогда нарушать аннотацию. Итак, вам нужен способ выразить: мне все равно, является ли этот конкретный 'T' Nullable или нет; Я буду проверять нуль, когда читаю, и никогда не буду писать нули, так что это не имеет значения.

Разница между @MaybeNull и @Nullable аналогична разнице между '? расширяет Number 'и' Number 'в генериках. За пределами дженериков они означают одно и то же, но в дженериках есть разница.

Так что не надейтесь в ближайшее время на жесткую проверку типов.

@ Наследование работает только для классов, но можно представить что-то похожее для аннотированных типов возвращаемых данных и аннотированных параметров.

1 голос
/ 07 августа 2009

Я думаю, это зависит от того, почему вы добавляете аннотации.

Если вы просто добавляете их для справки, чтобы разработчики интерфейса знали ваш предполагаемый дизайн, то это нормально.

Я использую аннотации для обработки транзакций и применения ролей безопасности, поэтому мои аннотации находятся на уровне реализации. Что хорошо в этом, так это то, что процессор AOP в моем контейнере Spring может проверять наличие той или иной аннотации и применять соответствующие прокси-классы для таких вещей, как определение границы транзакции или обеспечение авторизации пользователя для вызова определенного метода. *

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...