Функция скаффолдинга Grails является отличным ресурсом для быстрой генерации экранов создания / чтения / обновления / удаления (CRUD) для классов вашего домена. Создайте сущность, создайте контроллер и поместите статический каркас на вершину. Для различных типов свойств в вашем доменном классе используется подходящий (HTML) вход для ввода пользовательского ввода: логические значения становятся флажками, ассоциации с другими классами домена становятся (в зависимости от владения и ограничений), например, раскрывающимися списками или множественным выбором и т. Д.
Даже перечисление работает из коробки, как можно себе представить ? Этот пост служит небольшой подсказкой — в первую очередь для меня и других разработчиков, ищущих такого рода вещи — интернационализации экранов скаффолдинга в целом и перечислений в частности с использованием toString () и SpringSourceResolvable .
Возьмите следующий продукт со статусом :
class Product { enum Status { AVAILABLE, SOLD_OUT } String name Status status static constraints = { name blank: false, unique: true } } class ProductController { def scaffold = true }
Открытие нашего / product / create url покажет, что вы ожидаете.
Отличительной особенностью лесов является то, что интернационализация элементов на экране очень проста! Переводы по умолчанию для Home и Create уже предоставлены для дюжины или около того языков в папке i18n . Имя самого объекта («Продукт») и его свойства могут быть определены следующим соглашением: [имя объекта] .label и [имя объекта]. [Имя свойства] .label — см. Установку Grails / src / grails / Папка шаблонов / строительных лесов .
Посмотрите, как мы могли бы перевести несколько вещей на голландский, добавив несколько ключей к messages_nl.properties :
product.label=Product product.name.label=Naam product.status.label=Status
Если мы хотим протестировать определенный язык (без изменения среды вашего браузера) или вы просто хотите исправить приложение в определенной локали, мы можем переопределить локаль по умолчанию с помощью Spring глобально. Давайте сделаем это для голландского для следующих примеров.
beans = { localeResolver(org.springframework.web.servlet.i18n.FixedLocaleResolver) { defaultLocale = new Locale("nl", "NL") } }
Повторное рассмотрение нашего экрана показывает нам правильные голландские переводы для элементов пользовательского интерфейса по умолчанию и для наших собственных свойств.
Пока все хорошо, но разве мы не хотели бы переводить значения для наших значений перечисления AVAILABLE и SOLD_OUT? Есть несколько подходов, которые мы можем предпринять, из которых я опишу toString () и использую SpringSourceResolvable .
# 1. нанизывать()
Как вы знаете, экраны scaffolded просто выводят значения в выборках и выпадающих списках с помощью метода toString () показанного объекта. Мы можем создать каждое перечисление с жестко закодированным переводом, и функция toString () вернет это значение.
class Product { enum Status { AVAILABLE("Beschikbaar"), SOLD_OUT("Uitverkocht") final String value Status(String value) { this.value = value } String toString() { value } } String name Status status static constraints = { name blank: false, unique: true } }
И престо!
Фактические имена перечислений теперь появляются только в сгенерированном HTML:
<select name="status" required="" id="status" > <option value="AVAILABLE" >Beschikbaar</option> <option value="SOLD_OUT" >Uitverkocht</option> </select>
# 2. MessageSourceResolvable
Теперь вы, вероятно, поймете, что вышеупомянутое жестко закодированное решение работает только для одного языка, одного жестко закодированного в самом enum — что вызовет проблемы, когда через месяц ваше приложение фактически должно будет поддерживать второй язык ? Итак, как мы используем тот факт, что у нас уже есть message_XX.properties, куда мы поместили другие наши ключи сообщений?
Используйте базовую среду Spring. Пусть наш enum реализует org.springframework.context.MessageSourceResolvable, например так:
enum Status implements org.springframework.context.MessageSourceResolvable { AVAILABLE, SOLD_OUT public Object[] getArguments() { [] as Object[] } public String[] getCodes() { [ name() ] } public String getDefaultMessage() { "?-" + name() } }
Точно так же, как ошибки валидации — SpringError и ObjectError Spring, которые реализуют упомянутый интерфейс — мы можем предоставить наши собственные коды для поиска определенного ключа сообщения.
Просмотрев наш экран, вы заметите, что, поскольку мы еще не предоставили перевод, берется значение из getDefaultMessage () . Я просто добавил «? -» перед ним, чтобы сделать это более заметным, но вы можете делать все что угодно, например, просто возвращать name () .
Теперь мы можем предоставить значение в наших messages_nl.properties для каждого перечисления:
product.label=Product product.name.label=Naam product.status.label=Status <b>AVAILABLE=Beschikbaar SOLD_OUT=Uitverkocht</b>
И у нас тот же эффект, что и у нашей предыдущей жестко закодированной версии, но теперь мы сделали все правильно!
Оригинальная статья: http://tedvinke.wordpress.com/2012/08/22/grails-scaffolding-enums-and-i18n