Статьи

Написание RESTful веб-сервиса с Slim

Из серии статей здесь, в SitePoint, вы узнали, что такое REST и как он работает. В этой статье я хотел бы показать вам, как создать веб-сервис RESTful, используя Slim, PHP-микро-фреймворк, вдохновленный Sinatra, Ruby-фреймворком. Он хорошо подходит для создания простых веб-сервисов RESTful и поставляется с некоторыми минимальными компонентами, такими как Router, Request, Response и View. Это очень просто, легко понять и использовать.

Скажи привет стройному миру

Чтобы начать работать с Slim, вам сначала нужно его скачать. Он требует PHP 5.2+ и позволяет писать приложения как в процедурном стиле, так и в стиле 5.3+, например, с использованием анонимных функций. В этой статье я буду использовать стиль 5.3 для всех примеров, предполагая, что вы уже знакомы с ним.

Чтобы создать приложение Hello World, удалите файл index.php по умолчанию в каталоге приложения и создайте новый файл index.php со следующим кодом:

 <?php require "Slim/Slim.php"; // create new Slim instance $app = new Slim(); // add new Route $app->get("/", function () { echo "<h1>Hello Slim World</h1>"; }); // run the Slim app $app->run(); 

Ваше первое приложение Slim уже готово. Если вы заходите на index.php через браузер, вы должны увидеть большой «Hello Slim World».

Чтобы использовать Slim в своих приложениях, вам нужно включить Slim.php и Slim автоматически Slim.php все остальные Slim.php файлы. Затем вы можете создать один или несколько экземпляров объекта Slim и добавить свои маршруты.

Конструктор Slim принимает массив значений конфигурации приложения. MODE , TEMPLATES.PATH и VIEW — это некоторые важные конфигурации, которые мы часто используем. Используйте MODE чтобы установить среду приложения, которая будет использоваться, например, разработка или производство. TEMPLATES.PATH устанавливает местоположение для файлов шаблона. Slim использует Slim_View для визуализации представления по умолчанию, но вы можете написать собственные обработчики представления и прикрепить их к Slim, используя значение VIEW . В следующем примере показано, как создать новый экземпляр Slim с пользовательским TEMPLATES.PATH и установить среду в режим разработки.

 <?php $app = new Slim(array( "MODE" => "development", "TEMPLATES.PATH' => "./templates" )); 

Самая важная часть создания приложения с использованием Slim — это создание маршрутов. Маршрут помогает сопоставить URI с функцией обратного вызова для определенных методов запроса. Slim предоставляет простой и интуитивно понятный способ сопоставления одних и тех же URI с разными методами запросов. Он вызовет первую функцию обратного вызова, которая соответствует текущему URI и методу запроса, или выдаст ошибку 404, если она не может соответствовать. После добавления маршрутов вам нужно вызвать метод run() в экземпляре Slim чтобы запустить приложение.

Написание библиотечной службы

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

В следующей таблице перечислены конечные точки, которые будут поддерживаться веб-службой:

Для взаимодействия с базой данных я буду использовать NotORM , библиотеку PHP, написанную Якубом Враной, в качестве альтернативы ORM, которая предоставляет простой и интуитивно понятный API для работы с данными из вашей базы данных. NotORM использует PHP-расширение PDO для доступа к базе данных, поэтому экземпляр PDO передается в конструктор NotORM .

 <?php require "NotORM.php"; $pdo = new PDO($dsn, $username, $password); $db = new NotORM($pdo); 

Листинг Книги

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

 <?php ... $app = new Slim( "MODE" => "developement", "TEMPLATES.PATH' => "./templates" ); $app->get("/books", function () use ($app, $db) { $books = array(); foreach ($db->books() as $book) { $books[] = array( "id" => $book["id"], "title" => $book["title"], "author" => $book["author"], "summary" => $book["summary"] ); } $app->response()->header("Content-Type", "application/json"); echo json_encode($books); }); 

get() — это метод Slim, который направляет запрос GET по указанному URI. Первый аргумент — это URI, а последний аргумент — функция обратного вызова. Ключевое слово use позволяет нам получить доступ к внешним переменным изнутри области действия анонимной функции.

Внутри функции мы создаем массив книг, просматривая каждую запись, возвращаемую базой данных ( $db->books() возвращает прослеживаемую ссылку на таблицу books ). Заголовок Content-Type ответа отправляется как «application / json», и мы генерируем закодированный массив данных книги.

Теперь давайте напишем конечную точку для получения сведений о книге с заданным идентификатором:

 <?php ... $app->get("/book/:id", function ($id) use ($app, $db) { $app->response()->header("Content-Type", "application/json"); $book = $db->books()->where("id", $id); if ($data = $book->fetch()) { echo json_encode(array( "id" => $data["id"], "title" => $data["title"], "author" => $data["author"], "summary" => $data["summary"] )); } else{ echo json_encode(array( "status" => false, "message" => "Book ID $id does not exist" )); } }); 

Здесь мы добавили параметр Route для передачи идентификатора книги. При выполнении этого маршрута Slim вызовет функцию обратного вызова со значением параметра в качестве аргумента.

Обратите внимание, что параметр является обязательным. Вы можете сделать его необязательным, поместив его в круглые скобки, например: /book(/:id) Если вы сделаете параметр необязательным, вы не сможете указать параметры для функции обратного вызова. В этом случае вы можете использовать func_get_args() чтобы получить любые аргументы, переданные func_get_args() вызову.

Добавление и редактирование книг

Теперь давайте обратимся к конечным точкам, ответственным за добавление и обновление информации о книге. Мы будем использовать метод post() для добавления новых данных и put() для обновления существующих данных.

 <?php ... $app->post("/book", function () use($app, $db) { $app->response()->header("Content-Type", "application/json"); $book = $app->request()->post(); $result = $db->books->insert($book); echo json_encode(array("id" => $result["id"])); }); $app->put("/book/:id", function ($id) use ($app, $db) { $app->response()->header("Content-Type", "application/json"); $book = $db->books()->where("id", $id); if ($book->fetch()) { $post = $app->request()->put(); $result = $book->update($post); echo json_encode(array( "status" => (bool)$result, "message" => "Book updated successfully" )); } else{ echo json_encode(array( "status" => false, "message" => "Book id $id does not exist" )); } }); 

$app->request() возвращает текущий объект запроса ( Slim_Http_Request ) с данными POST или PUT. Вы можете получить значения POST с помощью метода post() этого объекта, а значения PUT — с помощью метода put() . Здесь мы предполагаем, что данные POST и PUT являются парами ключ / значение информации с именами столбцов таблицы в качестве ключей. В реальном приложении вам нужно будет добавить некоторую проверку и обработку ошибок, но я упустил это здесь для простоты.

Если вы планируете получить доступ к своему приложению Slim из браузера, вы не сможете легко отправлять PUT-запросы, так как браузеры обычно не предоставляют метод через HTML. Чтобы преодолеть это, у Slim есть условие, позволяющее переопределять запросы POST к PUT, помещая скрытое поле в форму. Имя поля должно быть «_METHOD», а значение должно быть «PUT».

 <form action="#" method="post"> <input type="hidden" name="_METHOD" value="PUT"> Title: <input type="text" name="title"><br> Author: <input type="text" name="author"><br> Summary: <textarea name="summary"></textarea> <br> <input type="submit" value="Submit"> </form> 

Удаление книг

Теперь, когда у нас есть конечные точки для добавления, редактирования и составления списка книг в нашем веб-сервисе, следующая очевидная вещь, которая нам нужна, это конечная точка для удаления книг. Он должен принять ID книги для удаления и удалить соответствующую запись из базы данных.

 <?php ... $app->delete("/book/:id", function ($id) use($app, $db) { $app->response()->header("Content-Type", "application/json"); $book = $db->books()->where("id", $id); if ($book->fetch()) { $result = $book->delete(); echo json_encode(array( "status" => true, "message" => "Book deleted successfully" )); } else{ echo json_encode(array( "status" => false, "message" => "Book id $id does not exist" )); } }); 

Здесь все довольно просто. Сначала мы выбираем строку, соответствующую данному идентификатору, из базы данных, как мы делали это при получении сведений о книге ранее. Вызов метода delete() для объекта строки удалит эту запись из базы данных.

Мы создали все необходимые конечные точки, связанные с книгами. В некоторых случаях вам может потребоваться отдельный маршрут, который будет отвечать более чем на один метод запроса. Это может быть реализовано с помощью метода Slim map() , который объясняется здесь .

Резюме

В этой статье мы обсудили создание веб-сервиса RESTful с использованием фреймворка Slim. Теперь вы сможете создавать свои собственные веб-сервисы без особых проблем.

Конечно, есть гораздо больше вещей, которые вы можете сделать, чем простые вещи, обсуждаемые здесь. Вы можете иметь маршруты с множеством параметров, проверкой данных и так далее. Так что копайтесь в этом и используйте инструменты, такие как Slim и NoORM, чтобы помочь вам в достижении ваших целей.

Вы можете скачать исходный код этой статьи с GitHub.

Изображение через Fotolia