Java има екосистема, която е узряла с години на развитие, утвърждавайки я като една от най-надеждните платформи там. И все пак липсват средствата, необходими за бързото свършване на работата, особено за неща като уеб приложения. В опит да избегнат разочарования от този тип проблеми, разработчиците често избират вместо това езици за внедряване и техните модерни уеб рамки, като Ruby с Ruby on Rails, Python с Django и т.н. За разлика от Java, те предоставят много по-опростен път към изграждането на уеб приложение.
За щастие, за разработчиците на Java, които искат да създават уеб приложения, има е по-добър начин и включва Граал. В тази статия ще видим как Grails with Groovy е жизнеспособна алтернатива в сферата на JVM. Ще разгледаме някои примери, в които Grails е привлекателен за нас като разработчици на Java и може да изкуши някой друг да опита.
При стартиране, за което работех, имахме точно този проблем. Имахме пролетно приложение, което се превръщаше в болка за работа. С нарастването му все повече и повече, скоро установихме, че рефакторингът и добавянето на функционалност ни отнемат повече време, отколкото би трябвало. Комбинирането на това с някои други мотиви ни накара да решим да пренапишем нашето основно приложение. Бяхме отворени и за промяна или замяна на съществуващ технологичен стек. Grails изглеждаше като жизнеспособен избор, тъй като работи в JVM и е изграден върху технологиите, които вече познавахме. Той използва езика за програмиране Groovy, но в същото време ви позволява да го смесвате с Java. Така че ние се впуснахме.
Едно нещо, в което Grails наистина превъзхожда, е да улесни започването на нов проект. Това е толкова просто, колкото стартирането на команда, която създава структурата на проекта с всички папки, необходими за класовете, които ще добавите по-късно. Добавянето на класове модели, контролери, услуги и уеб страници изисква подобно минимално количество усилия. Единственото нещо, за което трябва да се погрижите, е да назовавате и поставяте нещата правилно. За разлика от Java, на практика няма шаблонния код, който да трябва да бъде там, само защото трябва да бъде. Това е частично възможно чрез използването на Spring и Hibernate, които са два от стълбовете на Grails, както и концепцията за кодиране по конвенция. За да стартира проекта, Grails се доставя в комплект с Apache Tomcat като сървър за разработка. Всичко, което трябва да направим, е да стартираме проекта в нашата IDE и сървърът ще се задейства с нашия код. Също така Релационно картографиране на обекти на Grails (GORM) с Hibernate ще се погрижи за създаването на базата данни за нас. За да използваме съществуваща база данни, трябва да конфигурираме свойствата на връзката JDBC или просто да я оставим по подразбиране да използва екземпляр в паметта. След като сървърът с Grails се изпълни (отнема малко повече от Spring MVC приложение), можем да модифицираме кода и функцията за горещо разполагане ще поддържа нашата сесия за отстраняване на грешки оборудвана с най-новата версия. Единствените класове, които не могат да бъдат презаредени по този начин, са обектните класове.
Попълването на базата данни може да се извърши с помощта на SQL скриптове, но това може да стане досадно. Всички проекти на Grails съдържат клас Bootstrap, който ще се изпълнява, когато се изпълни нашето приложение. В този клас можем да съхраняваме или модифицираме данни и по този начин инициализиране състоянието на нашето приложение. Това се оказа много полезно за нас, така че веднага имаме няколко тестови случая във версия за разработка.
В клас Bootstrap можем да използваме и условия „if“, за да проверим типа на средата (разработка, тест, производство и т.н.) и да модифицираме данните съответно.Едно от нещата, които веднага привлече вниманието ни с Grails, беше лекотата на работа с данни. Четенето от базата данни е задача, която трябва да се извършва отново и отново. И много пъти е просто. Като извличането на един или повече обекти, които отговарят на определени критерии, и след това ги обобщава. Защо не използваме динамичен търсач за това? Това е начин за заявки за данни, при които методите се създават динамично по време на изпълнение. Всичко, което трябва да направите, е да следвате конвенцията за именуване.
def users = User.findAllByLastNameLikeOrAgeGreaterThan(‘Doe%’, 30)
Редът над реда ще извлече всички потребителски обекти с фамилно име, започвайки с „Doe“ или възраст по-голяма от 30. Да, не е много сложен случай, но получавате същността.
Ами ако искаме да филтрираме този списък допълнително за тези, които имат свойството “failedLogins” по-голямо от 10? И какво, ако искаме да ги сортираме по създадената им дата? И какво, ако искаме да обединим имената им или да намерим максималната възраст на върнатите потребители?
users = users.findAll() { it.failedLogins > 10 } users = users.sort { it.dateCreated } def firstNamesString = users.firstName.join(‘, ‘) def maximumAge = users.age.max()
Горните примери може да изглеждат прости, но показват колко мощни могат да бъдат Grails за заявки, филтриране и манипулиране на данни. В Java 8 можете да постигнете подобни резултати за някои от тези случаи, но все пак ще е необходим повече код от Граали.
Динамичен конструктор или именован конструктор на аргументи е функция, която много от нас искаха да имат в Java. Хубаво е да дефинирате кои конструктори позволява даден клас, но в много случаи просто искате да зададете някои свойства и да получите проклетия екземпляр. Groovy добавя специален конструктор за всеки обект, който по същество приема елегантността на картата като вход и задава свойствата с записите в картата.
def Person = new Person(name: 'Batman', age: 57)
Този подход води до код, който е много по-изразителен и избягва необходимостта от целия код на конструкторски шаблон.
И BTW, ето няколко примера за страхотността и елегантността на картите на Groovy:
def emptyMap = [:] def map = [bread:3, milk:5, butter:2] map[‘bread’] = 4 map.milk = 6
Това е друг пример за това как кодът може да бъде кратък и опростен, но същевременно мощен. Той показва как може да се използва вградена инициализация и как стойностите на картата могат да бъдат манипулирани по начин, подобен на свойствата на обекта. Няма нужда да извиквате традиционни Java методи за основна манипулация, освен ако наистина не искате.
Разбира се, няма рамка, която да може всичко, но когато попълваме пропуските, трябва да видим какво още може да е налично, преди да се опитаме да приложим нашето собствено решение. За да разширим нашия арсенал от базирана на Grails функционалност, можем да използваме Grails Plugins. Инсталирането на приставка се извършва просто чрез добавяне на друг ред в BuildConfig
клас, който присъства във всеки проект на Grails (конвенцията за кодове отново нанася удар!).
compile ':spring-security-core:2.0-RC4'
Редът по-горе добавя ядрото за защита Spring към нашето приложение и практически не е необходима повече конфигурация за включване на тази функционалност.
Подобно е на използването на зависимости на Maven (на които можете да се позовавате и в същия клас за конфигуриране), но приставките обикновено са по-големи блокове, които съдържат цялата функционалност.Като се има предвид това, нека ви разкажа за един случай, с който трябваше да се справим. Трябваше да приложим търсене, обхващащо няколко обекта на данни. Grails има приставка Elasticsearch, която е лесна за използване. Както споменахме по-горе, трябва само да се позовем на приставката в конфигурационния файл и е добре да започнем. Ако искаме да търсим обекти от определен клас, просто трябва да добавим статично свойство „за търсене“ към този клас. И ако искаме, можем дори да ограничим свойствата, които ще бъдат разрешени за търсене.
class User { static searchable = { only = name } String name Double salary }
Това е толкова малко код, но под капака, Grails и приставката Elasticsearch автоматично ще индексират всички потребители по име и ще ни позволят да търсим по име. Действителното обаждане за търсене също е много кратко:
User.search('${params.query}')
Ако не искаме, никога няма да се наложи да докосваме индекса на Луцен. Всичко ще бъде направено автоматично-магически за нас. Приставката дори има API за показване на резултатите от търсенето - тя може да подчертае съвпадението, намерено в търсения текст. Това е само пример как плъгинът може да осигури огромен пакет функционалности, които могат да ни направят много по-ефективни, като избягват необходимостта сами да го прилагаме.
Приставките са страхотни, но понякога не се нуждаем от цял плъгин, а просто искаме нещо допълнително. Спомняте ли си последния път, когато сте искали да имате допълнителен метод за съществуващ клас на Java, но не сте искали (или не сте могли) да ги разширите / замените? В Groovy можете да добавяте методи и свойства към съществуващи класове или дори само към определени екземпляри от тях. Например можете да добавите formatting
метод към java.util.Date
клас, което е страхотно, когато искате да форматирате последователно дати и просто не искате да пишете статични помощни класове или да дефинирате различни филтри.
Date.metaClass.formatDate = { delegate.format('dd.MM.yyyy') }
Какво ще стане, ако искате да сортирате списък с потребители по изчислена стойност и имате нужда от това само в един случай (т.е. добавянето на нов метод в потребителския клас би замърсило)? Можете да добавите свойство във всеки от тези случаи и след това просто да сортирате или филтрирате колекцията по това свойство:
user.metaClass.computedProp = 312 * 32 * 3
Авторите на Groovy вече са добавили много подобрения към някои от основните Java класове, така че не е нужно. По-долу са някои примери.
Използване на „минус“ за премахване на всички елементи от колекция, които присъстват в друга колекция.
assert [1, 2, 3, 4, 4, 5] - [2, 4] == [1, 3, 5]
Допълнителни методи за манипулиране java.util.Date
обекти, които са полезни толкова много пъти, като добавяне / изваждане на дни от дати или получаване / задаване на определено поле от датата, без да го конвертирате в Calendar
или използване на допълнителни библиотеки.
def yesterdayAllMyTroublesSeemedSoFarAway = new Date() - 1 def myAwesomeAnniversaryYear = myAwesomeDate[Calendar.YEAR] + 1 myAwesomeDate.set(year: myAwesomeAnniversaryYear, second: 0)
Когато искате наистина да получите описателен текст с манипулация на датата, можете просто да използвате добавения Groovy TimeCategory
клас:
use (TimeCategory) { println 1.minute.from.now println 10.hours.ago def someDate = new Date() println someDate - 3.months }
След това има IDE. Базирани на Eclipse GGTS и IntelliJ IDEA са настроени за работа с Grails. Те разбират структурата на проекта (и ще ви помогнат да навигирате през папки и ресурси) и имат преки пътища за командите, които най-често ще използвате (напр. Добавяне на контролер, добавяне на страница, стартиране на проект и т.н.). С Grails ще изпълнявате команди (за стартиране на проект или настройване на нова функционалност на приставката) и ще ви трябват различни конфигурации, което също е обхванато от IDE. Попълването на кода работи добре в уеб страниците с шаблони на Grails, където често ще препращате към контролери и действия. Има и други IDE, които могат да се използват с Grails като Netbeans, TextMate, Emacs и други.
Както при всичко в живота, така и при Граалите има предупреждения. Под капака се правят много магии, които често могат да бъдат нещо добро, но понякога резултатът няма да е такъв, какъвто сте очаквали. Грешки ще се случват само поради това, че не използвате въвеждането (да, типовете не са задължителни в Groovy) и не сте достатъчно внимателни. И може би няма да забележите грешка, докато не стане твърде късно. Освен това е много изкушаващо да пишете еднолинейни текстове, за да впечатлите колегите си. И себе си. Но тези мощни редове код може да не са толкова обясними за вашите колеги. Или дори за себе си след няколко месеца. Ето защо мисля, че Grails изисква повече дисциплина по програмиране, отколкото някои от по-традиционните рамки.
Кодирането не трябва да отнема повече време, само защото настоящата ви рамка го изисква. Особено при все по-големия брой стартиращи компании в наши дни е важно да се съсредоточите върху задачите, които наистина имат значение и да бъдете възможно най-ефективни. Времето наистина е пари, а времето за пускане на пазара е от решаващо значение. Трябва да можете да действате бързо и да внедрите решението, преди да изтече времето и вашата конкуренция ще ви победи.
Моите приятели, работещи с Рубин на релси или Python / Django отдавна ми казват колко страхотни са тези технологии. И наистина се почувствах глупаво да си помисля колко повече време ми отне в Java да напиша код, който съхранява нещо в базата данни и го показва в уеб страница. Граалите наистина могат да бъдат полезен отговор. Не че не бихте могли да направите това с чиста Java, Spring MVC и Hibernate. Можеш. Вашето приложение може дори да работи малко по-бързо. Но ще свършите работата по-бързо с Grails.
Свързани: Защо вече трябва да надстроите до Java 8