Смекни!
smekni.com

Василий Гринюк

Бесспорно, java является одним из лидеров на рынке сложных корпоративных продуктов. Прекрасная масштабируемость и надежность - основные факторы этого успеха. Но стоит ли прибегать к такому мощному инструменту, когда масштабируемость не очень и важна? Ведь для небольших компаний более важным является стоимость разработки и ее сроки, а также возможность быстро отреагировать на перемены в деятельности компании и при необходимости изменить программный продукт. А для интернет-стартапов и вовсе нужно как можно быстрее реализовать первичный набросок бизнес-идеи и при этом с максимально привлекательным интерфейсом. И практически перед каждой компанией стоит выбор - заказать программное решение «под ключ» или попытаться найти уже готовое и адаптировать под свой бизнес. Microsoft тоже не отстает и с выходом net framework 2.0 и ms ajax пытается захватить рынок. Чтобы ответить на вопрос, подходит ли java для разработки программных решений, нужных среднему и малому бизнесу, посмотрим, для какого рода задач ее можно эффективно применять, где проявляются ее преимущества.

Любое приложение состоит из нескольких слоев. Обычно это модель и графический интерфейс. В случае, если логика приложения достаточно сложна, появляется еще один слой между моделью и интерфейсом — это сервисы. Модель содержит в себе всю основную логику приложения — бизнес-логику, включая бизнес-объекты и бизнес-процессы, которые необходимы для поставленной задачи. Сервисы — это слой, который предоставляет более удобные методы для решения задач отображения, редактирования и добавления данных в пользовательском интерфейсе. Остановимся более детально именно на модели, так как она фактически является ядром системы, работоспособность и эффективность приложения в большей мере зависят именно от нее. От способов ее реализации также зависит, насколько сложно будет в дальнейшем вносить изменения в приложение.

Hibernate

Первый вопрос при проектировании модели — как и где хранить данные? Очевидно, что лучше всего в базе данных, но в какой именно и как организовать коммуникацию между приложением и конкретной СУБД? Здесь нам на помощь приходит практически революционный фреймворк— Hibernate. При работе с ним практически полностью отпадает необходимость заботиться о том, что данные где-то должны храниться.

Разберемся в нем более детально. Во-первых, Hibernate является отчасти абстракцией над СУБД, а это означает, что приложение больше не привязано к конкретному серверу базы данных. Например, для того чтобы перейти с легкой и удобной СУБД MySQL на очень производительный Oracle, нужно всего лишь в конфигурационном файле поменять название диалекта. Во-вторых, Hibernate —это средство для объектного маппинга данных, т.е. фактически., мы манипулируем связками объектов, а не просто структурированными данными. Мы не заботимся о том, как эти объекты будут храниться в конкретной СУБД, и о том, как эти объекты (а точнее, их связки) сохранять или получать из базы данных.

В связи с тем что при работе через Hibernate мы никогда не сталкиваемся с какими-либо специфическими для разных СУБД функциями, то привязки к конкретному серверу не существует. На самом деле нам даже не приходится писать SQL-запросы или самим создавать структуру базы данных. Структуру Hibernate создает сам при загрузке приложения. А вот с запросами еще интересней. Запросы пишутся на его собственном языке — HQL (Hibernate Query Language). Этот язык имеет некоторые логические сходства с SQL, но не более. Во-первых, этот язык оперирует не с таблицами и их полями, а с объектами и их связками. Во-вторых, на этом языке пишутся только запросы на получение связок объектов, а точнее, сложные поиски. Для выборки данных без сложной логики он не нужен, так как есть такое понятие, как критерий, этого вполне хватает, если не нужно вести поиск с учетом значений в дочерних объектах.

Есть два способа «научить» Hibernate работать с нашими объектами — маппинг и аннотации. Оба способа указывают Hibernate, какие именно поля нашего объекта нужно хранить и как этот объект расположен в нашей иерархии: какие связи у этого объекта с другими объектам (один со многими, многие со многими, многие с одним). Благодаря этому, получая объект из базы данных, мы получаем и все его дочерние объекты. При этом используется такое понятие, как lazy loading. Благодаря ему Hibernate не сразу передает нам всю связку объектов (это могло бы привести к тому, что получая один объект, который так или иначе связан с другими, пришлось бы извлечь все, что хранится в базе данных), а некие персистентные ссылки. И только при первом реальном обращении к этому объекту достает его. Еще один приятный момент — это простота реализации ОАО (DataBase Access Object). Можно просто сделать единственный ОАО-класс для всех объектов. Все стандартные методы (save, delete, update) предоставляет сам Hibernate, о них нам заботиться не нужно вовсе. А для сложных методов, использующих HQL-запросы, достаточно сделать метод обвертку, который будет читать по какому-либо ключу сам запрос из xml-файла и возвращать нам список наших объектов. Следующим важным моментом является то, что Hibernate работает в транзакционном режиме, что немаловажно для безопасности сохранения данных. Это очень критично, к примеру, в любых бухгалтерских приложениях. Однако это нужно учитывать еще во время планировки, так как необходим постоянный контроль состояния транзакций. Например, после закрытия транзакции все lazy-данные будут недоступны.

Spring

Еще один мощный фреймворк — Spring. Он позволяет хранить любые объекты как бины. То есть мы указываем интерфейс и его реализацию, a Spring уже создает экземпляр этого класса и помещает его в контекст. Этот бин доступен всему приложению и будет существовать все время, пока приложение запущено. Это очень удобно, так как мы можем поместить в контекст наши ОАО-объекты и быть уверенными, что во всех частях приложения используется один и тот же экземпляр. Но только, если нам это нужно.

То есть мы беспроблемно можем создать и сессионные бины, и тогда для каждой сессии будет создаваться свой личный бин. Это достаточно «легковесный» фреймворк и благодаря ему можно полностью отказаться от такого громоздкого контейнера, как JBoss, обойдясь «маленьким» Tomcat'oM. А это существенно снижает аппаратные требования.

Web 2.0

Теперь посмотрим, как можно быстро и эффективно реализовать front-end. Учитывая, что Web 2.0 уже фактически полностью стал стандартом, остановимся именно на нем. Если коротко, Web 2.0 — это сайты, страницы которых не являются статическими, а изменение содержимого происходит не посредством перезагрузки страницы, а при помощи JavaScript через асинхронные запросы, проще говоря, AJAX (Asynchronous JavaScript and XML). Яркие примеры такого интерфейса —Gmail и Google Maps. Есть два способа реализовать AJAX-интерфейс — самому писать JavaScript'ы и использовать какой-либо RPC (например, JSON-RPC), либо использовать готовый фреймворк. Одни из лучших фреймворков для создания интерфейса Web 2.0— это GWT (Google Web Toolkit), dojo или Tapestry 4.1 + Tecas. У всех способов есть свои плюсы и минусы. Пойдем по порядку.

Главным минусом первого варианта является то, что у команды должен быть довольно большой опыт в разработке такого интерфейса и желательно наличие собственных заготовок. Главный плюс—то, что программисты имеют полный контроль над всем, что они делают, и нет никаких ограничений, накладываемых тем или иным фреймворком. Хорошее вспомогательное средство — JSON-RPC. Он передает данные не в формате xml, а в специальном формате JSON, предоставляя очень удобный способ напрямую вызывать методы на сервере и получать ответ уже в готовом объектном представлении. Это очень удобно, потому что можно полностью использовать объектную модель на клиенте. Он поддерживает передачу сложных объектов, списков и т. д. Но есть несколько моментов, про которые не стоит забывать при работе с JSON-RPC. Например, регистрировать все сервисы нужно в каждой сессии отдельно, в зависимости оттого, кем авторизовывался пользователь. Тогда вам не придется реализовывать систему безопасности в бизнес-логике. И если команда имеет большой опыт работы с объектно-ориентированным программированием на JavaScript и хотя бы небольшую коллекцию наработок, то этот подход весьма привлекателен и эффективен.

Второй подход—использование готового фреймворка. Он не проще или быстрее, это просто альтернатива. Во-первых, каждый фреймворк имеет свои особенности, во-вторых, у каждого из них есть свои «подводные камни». Это означает, что команда должна иметь опыт работы с этим фреймворком. И чем данный опыт больше, тем больше толку от его использования. Еще стоит добавить, что большинство фреймворков рассчитаны на решение конкретных задач — шаг влево сделать очень сложно. А в Ul (User Interface) это очень и очень проблематично. Ведь реально практически у любого проекта есть свои уникальные требования к представлению данных. Поэтому выбирать фреймворк нужно либо такой, в котором точно предусмотрено все, что нужно, либо такой, который легко расширяется. Давайте посмотрим на некоторые фреймворки поближе.

GWT

В очередной раз нас порадовала компания Google. Это и неудивительно, ведь в создании интерфейсов Web 2.0 она набралась немало опыта —фактически она занимает лидирующие места в этой области: Gmail, Google Map, Google Docs&Spreadsheets. Решение у Google весьма интересное и необычное — мы пишем весь код на Java. Специальный компилятор компилирует Java-код в JavaScript-код. Причем этот код поддерживается во всех браузерах. Код, который пишется, оперирует со стандартными Java-классами, такими как ArrayList, HashMap, HashSet и т.д. Дополнительно реализованы все классы, нужные для интерфейса (Button, Window и т. д.). То есть этот код компилируется стандартным Java компилятором и можно беспроблемно писать unit-тесты и запускать их. К сожалению, пока что поддерживается только компилятор версии 1.3, который, к примеру, не содержит итеративных циклов. Но мы получаем реальный контроль типов (по крайней мере, во время компиляции), возможность удобно записывать классы, да и вообще отсутствие большинства проблем, которые возникают при написании кода на скриптовых языках. Дополнительно предлагается система связи клиента с сервером. То есть фактически полноценный RPC. Хотя модель этой системы не такая простая и наглядная, как у JSON-RPC, она все же эффективна. И не смотря на то что писать несложные приложения и интерфейсы, используя GWT, относительно просто, для серьезного использования требуется хороший опыт работы с ним, особенно у архитекторов системы.