1. Обзор
Цель этого вводного руководства — изучить Play Framework и выяснить, как мы можем создать с его помощью веб-приложение.
Play — это высокопроизводительная среда веб-приложений для языков программирования, код которых компилируется и запускается на JVM, в основном на Java и Scala. Он объединяет компоненты и API, необходимые для разработки современных веб-приложений.
2. Настройка игровой платформы
Давайте перейдем на официальную страницу фреймворка Play и загрузим последнюю версию дистрибутива. На момент написания этого руководства последней была версия 2.7.
Мы загрузим ZIP-папку учебника Play Java Hello World и разархивируем файл в удобное место. В корне этой папки мы найдем исполняемый файл sbt
, который мы можем использовать для запуска приложения. Кроме того, мы можем установить sbt
с их официальной страницы .
Чтобы использовать sbt
из скачанной папки, сделаем следующее:
cd /path/to/folder/
./sbt run
Обратите внимание, что мы запускаем скрипт в текущем каталоге, поэтому используется синтаксис ./ .
Если мы установим sbt,
то сможем использовать его вместо него:
cd /path/to/folder/
sbt run
После запуска этой команды мы увидим заявление, которое гласит: «(Сервер запущен, нажмите Enter, чтобы остановить и вернуться к консоли…)». Это означает, что наше приложение готово, поэтому теперь мы можем перейти по адресу http://localhost:9000
, где нам будет представлена страница приветствия Play:
3. Анатомия игровых приложений
В этом разделе мы лучше поймем, как устроено приложение Play и для чего используется каждый файл и каталог в этой структуре.
Если вы хотите сразу же бросить себе вызов на простом примере, перейдите к следующему разделу.
Вот файлы и папки, которые мы находим в типичном приложении Play Framework:
├── app → Application sources
│ ├── assets → Compiled Asset sources
│ │ ├── javascripts → Typically Coffee Script sources
│ │ └── stylesheets → Typically LESS CSS sources
│ ├── controllers → Application controllers
│ ├── models → Application business layer
│ └── views → Templates
├── build.sbt → Application build script
├── conf → Configurations files and other non-compiled resources (on classpath)
│ ├── application.conf → Main configuration file
│ └── routes → Routes definition
├── dist → Arbitrary files to be included in your projects distribution
├── lib → Unmanaged libraries dependencies
├── logs → Logs folder
│ └── application.log → Default log file
├── project → sbt configuration files
│ ├── build.properties → Marker for sbt project
│ └── plugins.sbt → sbt plugins including the declaration for Play itself
├── public → Public assets
│ ├── images → Image files
│ ├── javascripts → Javascript files
│ └── stylesheets → CSS files
├── target → Generated files
│ ├── resolution-cache → Information about dependencies
│ ├── scala-2.11
│ │ ├── api → Generated API docs
│ │ ├── classes → Compiled class files
│ │ ├── routes → Sources generated from routes
│ │ └── twirl → Sources generated from templates
│ ├── universal → Application packaging
│ └── web → Compiled web assets
└── test → source folder for unit or functional tests
3.1. Каталог приложений
_
Этот каталог содержит исходный код Java, веб-шаблоны и исходники скомпилированных ресурсов — в основном, все исходники и все исполняемые ресурсы.
Каталог app
содержит несколько важных подкаталогов, каждый из которых содержит одну часть архитектурного шаблона MVC:
модели
— это бизнес-уровень приложения, файлы в этом пакете, вероятно, будут моделировать наши таблицы базы данных и позволят нам получить доступ к уровню сохраняемости.представления
— все шаблоны HTML, которые могут быть отображены в браузере, содержатся в этой папке.controllers
— подкаталог, в котором у нас есть наши контроллеры.Контроллеры
— это исходные файлы Java, содержащие действия, которые должны выполняться для каждого вызова API.Действия
— это общедоступные методы, которые обрабатывают HTTP-запросы и возвращают такие же результаты, как и ответы HTTP.assets
— подкаталог, содержащий скомпилированные ресурсы, такие как CSS и javascript. Приведенные выше соглашения об именах являются гибкими, мы можем создавать наши пакеты, например , пакетapp/utils
. Мы также можем настроить имя пакетаapp/com/foreach/controllers.
Он также содержит необязательные файлы и каталоги, необходимые конкретному приложению.
3.2. Публичный
каталог _
Ресурсы, хранящиеся в общедоступном
каталоге, являются статическими активами, которые обслуживаются непосредственно веб-сервером.
Этот каталог обычно имеет три подкаталога для файлов изображений, CSS и JavaScript. Мы рекомендуем организовывать файлы ресурсов таким образом, чтобы обеспечить единообразие во всех приложениях Play.
3.3. Каталог conf
_
Каталог conf
содержит файлы конфигурации приложения. В application.conf
мы поместим большинство свойств конфигурации для приложения Play. Мы определим конечные точки для приложения в route
.
Если приложению нужны дополнительные файлы конфигурации, их следует поместить в этот каталог.
3.4. Каталог библиотек
_
Каталог lib
является необязательным и содержит зависимости от неуправляемых библиотек. Если у нас есть jar-файлы, не указанные в системе сборки, мы помещаем их в этот каталог. Они будут автоматически добавлены в путь к классам приложения.
3.5. Файл build.sbt
_
Файл build.sbt
— это скрипт сборки приложения. Здесь мы перечисляем зависимости, необходимые для запуска приложения, такие как тестовые и сохраняемые библиотеки.
3.6. Каталог проекта
_
Все файлы, которые настраивают процесс сборки на основе SBT, находятся в каталоге проекта .
3.7. Целевой
каталог _
Этот каталог содержит все файлы, сгенерированные системой сборки, например, все файлы .class
.
Увидев и изучив структуру каталогов для примера Play Framework Hello World, который мы только что скачали, мы теперь можем пройтись по основам фреймворка на примере.
4. Простой пример
В этом разделе мы создадим очень простой пример веб-приложения. Мы будем использовать это приложение, чтобы ознакомиться с основами платформы Play.
Вместо того, чтобы загружать пример проекта и строить из него, давайте посмотрим, как мы можем создать приложение Play Framework, используя команду sbt new
.
Давайте откроем командную строку, перейдем к выбранному нами местоположению и выполним следующую команду:
sbt new playframework/play-java-seed.g8
Для этого нам нужно уже установить sbt
, как описано в Разделе 2 .
Приведенная выше команда сначала предложит нам имя для проекта. Затем он запросит домен (наоборот, как в соглашении об именах пакетов в Java), который будет использоваться для пакетов. Мы нажимаем Enter
, не вводя имя, если хотим сохранить значения по умолчанию, указанные в квадратных скобках.
Приложение, созданное с помощью этой команды, имеет ту же структуру, что и созданное ранее. Поэтому мы можем приступить к запуску приложения, как мы это делали ранее:
cd /path/to/folder/
sbt run
Приведенная выше команда после завершения выполнения создаст сервер на порту 9000
для предоставления нашего API , доступ к которому мы можем получить через http://localhost:9000
. Мы должны увидеть сообщение «Добро пожаловать в игру» в браузере.
Наш новый API имеет две конечные точки, которые теперь мы можем опробовать по очереди из браузера. Первая, которую мы только что загрузили, — это корневая конечная точка, которая загружает индексную страницу с сообщением «Добро пожаловать в игру!». сообщение.
Второй, по адресу http://localhost:9000/assets,
предназначен для загрузки файлов с сервера путем добавления имени файла к пути. Мы можем протестировать эту конечную точку, получив файл favicon.png
, который был загружен вместе с приложением, по адресу http://localhost:9000/assets/images/favicon.png
.
5. Действия и контроллеры
Метод Java внутри класса контроллера, который обрабатывает параметры запроса и создает результат для отправки клиенту, называется действием.
Контроллер — это класс Java, расширяющий play.mvc.Controller
, который логически группирует действия, которые могут быть связаны с результатами, которые они производят для клиента.
Теперь давайте перейдем к app-parent-dir/app/controllers
и обратим внимание на HomeController.java
.
Действие index HomeController
возвращает веб-страницу с простым приветственным сообщением:
public Result index() {
return ok(views.html.index.render());
}
Эта веб-страница является шаблоном индекса
по умолчанию в пакете представлений:
@main("Welcome to Play") {
<h1>Welcome to Play!</h1>
}
Как показано выше, страница индекса вызывает
основной
шаблон. Затем основной шаблон обрабатывает отображение заголовка страницы и тегов тела. Он принимает два аргумента: строку
для заголовка страницы и объект Html
для вставки в тело страницы.
@(title: String)(content: Html)
<!DOCTYPE html>
<html lang="en">
<head>
@* Here's where we render the page title `String`. *@
<title>@title</title>
<link rel="stylesheet" media="screen" href="@routes.Assets.versioned("stylesheets/main.css")">
<link rel="shortcut icon" type="image/png" href="@routes.Assets.versioned("images/favicon.png")">
</head>
<body>
@* And here's where we render the `Html` object containing
* the page content. *@
@content
<script src="@routes.Assets.versioned("javascripts/main.js")" type="text/javascript"></script>
</body>
</html>
Немного изменим текст в индексном
файле:
@main("Welcome to ForEach") {
<h1>Welcome to Play Framework Tutorial on ForEach!</h1>
}
Перезагрузка браузера даст нам жирный заголовок:
Welcome to Play Framework Tutorial on ForEach!
Мы можем полностью отказаться от шаблона, удалив директиву рендеринга
в методе index()
HomeController
, чтобы мы могли напрямую возвращать обычный текст или текст HTML:
public Result index() {
return ok("REST API with Play by ForEach");
}
После редактирования кода, как показано выше, в браузере останется только текст. Это будет просто текст без HTML и стилей:
REST API with Play by ForEach
С таким же успехом мы могли бы вывести HTML, заключив текст в теги заголовка <h1></h1>
и затем передав текст HTML методу Html.apply
. Не стесняйтесь играть с ним.
Давайте добавим конечную точку /foreach/html
в маршруты
:
GET /foreach/html controllers.HomeController.applyHtml
Теперь давайте создадим контроллер, который обрабатывает запросы на этой конечной точке:
public Result applyHtml() {
return ok(Html.apply("<h1>This text will appear as a heading 1</h1>"));
}
Когда мы посетим http://localhost:9000/foreach/html
, мы увидим приведенный выше текст в формате HTML.
Мы манипулировали нашим ответом, настроив тип ответа. Мы рассмотрим эту функцию более подробно в следующем разделе.
Мы также увидели две другие важные функции Play Framework.
Во-первых, перезагрузка браузера отражает самую последнюю версию нашего кода; это потому, что наши изменения кода компилируются на лету.
Во-вторых, Play предоставляет нам вспомогательные методы для стандартных ответов HTTP в классе play.mvc.Results
. Примером может служить метод ok()
, который возвращает ответ OK HTTP 200 вместе с телом ответа, которое мы передаем ему в качестве параметра. Мы уже использовали метод отображения текста в браузере.
В классе Results
есть дополнительные вспомогательные методы, такие как notFound()
и badRequest()
. ``
6. Манипулирование результатами
Мы получили выгоду от функции согласования контента в Play, даже не осознавая этого. Play автоматически определяет тип содержимого ответа из тела ответа. Вот почему мы смогли вернуть текст в методе ok :
return ok("text to display");
А затем Play автоматически установит для заголовка Content-Type значение
text/plain
. Хотя в большинстве случаев это работает, мы можем взять на себя управление и настроить заголовок типа контента.
Давайте настроим ответ для действия HomeController.customContentType
на text/html
:
public Result customContentType() {
return ok("This is some text content").as("text/html");
}
Этот шаблон подходит для всех типов контента. В зависимости от формата данных, которые мы передаем вспомогательному методу ok
, мы можем заменить text/html
на text/plain
или application/json
.
Мы можем сделать что-то похожее на набор заголовков:
public Result setHeaders() {
return ok("This is some text content")
.as("text/html")
.withHeader("Header-Key", "Some value");
}
7. Заключение
В этой статье мы изучили основы Play Framework. Мы также смогли создать базовое веб-приложение Java с помощью Play.
Как обычно, исходный код этого руководства доступен на GitHub .