Express является фреймворком для приложений Node.js.
Express — это минималистичный и гибкий Node-фреймворк для веб-приложений, который предоставляет широкий набор функций для создания одной или множества страниц и гибридных веб-приложений.
Для Express имеется богатый API и он ЧЕРТОВСКИ БЫСТРЫЙ!!!
Express, как хорошо известно, развивается своим путём, в отличие от других фреймворков, во многом опирающихся на Rails, но также много позаимствовал из другого Ruby-фреймворка под названием Sinatra. Концепция простая: фреймворк предоставляет достаточно возможностей для запуска и работы «на лету», не требуя много времени на подготовку.
В этом руководстве мы будем использовать Express в качестве основного инструмента для получения веб-приложения и запуска его с сервером, поддержки маршрутов, страницы ошибок, ведение логов и т. д.
Установка Express
Установка Express с npm действительно простая. Имейте в виду, что в Express есть две части — это библиотека для его запуска и замечательный генератор приложения.
Установка Express:
$ npm install express -g
Установка генератора:
$ npm install express-generator -g
Версия генератора
Express 4.0 был выпущен недавно и есть те, кто с ним не дружат. В npm содержится способ указать определённую версию генератора для установки.
$ npm install -g express-generator@3
Создание нового Express-приложения
На данный момент вы должны быть готовы двинуться вперёд и создать приложение. В этом примере мы создадим приложение Node.js с фреймворком Express.
$ express <ваше приложение>
Выполнив эту команду (используя demo-app в качестве примера) вы должны увидеть следующее:
create : demo-app
create : demo-app/package.json
create : demo-app/app.js
create : demo-app/public
create : demo-app/public/javascripts
create : demo-app/public/images
create : demo-app/public/stylesheets
create : demo-app/public/stylesheets/style.css
create : demo-app/routes
create : demo-app/routes/index.js
create : demo-app/routes/users.js
create : demo-app/views
create : demo-app/views/index.jade
create : demo-app/views/layout.jade
create : demo-app/views/error.jade
create : demo-app/bin
create : demo-app/bin/www
install dependencies:
$ cd demo-app && npm install
run the app:
$ DEBUG=my-application ./bin/www
БУМ! Express берёт на себя часть работы. Теперь мы делаем то, что сказали компьютеру — изменить текущую папку на папку приложения и запустить npm install.
Что в этом приложении?
В этот момент вы можете увидеть новую структуру приложения, которая была создана для вас.
app.js
node_modules/
public/
views/
bin/
package.json
routes/
app.js
Это логичная отправная точка для вашего приложения. В ней есть несколько вещей, о которых стоит поговорить:
Следующие строки для этого типа приложения нам не понадобятся:
var user = require('./routes/user');
app.get('/users', user.list);
Устанавите путь к папке, где хранятся файлы представления:
app.set('views', path.join(__dirname, 'views'));
Установите путь к папке со статичными ресурсами:
app.use(express.static(path.join(__dirname, 'public')));
Установите корневой маршрут для приложения:
app.use('/', routes);
node_modules/
Это папка, где будут находиться все ваши пакеты npm.
public/
Папка для всех статичных ресурсов, например, изображений, JavaScript, CSS, шрифтов и др.
views/
Здесь будут жить все ваши макеты и файлы представления Jade.
bin/
Здесь хранится единственный файл www и он активирует Node.
package.json
Описание проекта, менеджер скриптов и манифест приложения. Обратите внимание на следующий объект:
"scripts": {
"start": "node ./bin/www"
},
Это код, который позволяет вам запускать npm start для приложения.
routes/
Это папка, в которой вы будете строить маршруты REST для вашего приложения. После базовой установки здесь должны находиться два файла: index.js и users.js.
Веселье с маршрутами
Методы app.VERB() обеспечивают функциональность маршрутизации в Express, где VERB является одним из методов HTTP, вроде app.post(). Можно установить несколько функций обратного вызова, все они рассматриваются одинаково и ведут себя как промежуточное программное обеспечение, с одним исключением, что все эти функции могут вызывать next('route') в обход оставшегося маршрута. Этот механизм может быть использован для выполнения предварительных условий для маршрута, затем передать управление в последующие маршруты, когда нет никаких причин для обработки совпадений маршрута.
Следующий фрагмент иллюстрирует возможно самое простое определение маршрута. Express переводит строку пути в регулярные выражения, используемые внутри для сравнения с входящими запросами. Строки запроса не учитываются при выполнении этих совпадений, например GET/ будет соответствовать следующему маршруту GET/?name=tobi.
app.VERB(path, [callback...], callback)
Давайте получим в настройках несколько маршрутов. В файле app.js следующая строка показывает, как они работают вместе:
var routes = require('./routes/index');
Что здесь происходит? В принципе, Express устанавливает переменную routes чтобы она затребовала путь и файл ./routes.index.
Эта переменная затем используется для установки корневого пути приложения:
app.use('/', routes);
Ещё одну вещь, которую мы можем сделать — это res.send() и что мы сюда положим, то и будет передаваться непосредственно в браузер. Например:
router.get('/foo', function(req, res){
res.send('hello world');
});
Используя res.send() мы можем сделать забавные вещи, вроде отправки в объекты JSON.
router.get('/foo', function(req, res){
res.send({'name':'Bob Goldcat', 'age': '41'})
});
Этот метод позволяет сохранить все наши маршруты в файл index.js, если это необходимо. Есть более эффективные способы для решения более сложных задач маршрутизации, но в рамках этой работы и так хорошо.
Что в файле index.js?
Взглянув на наш файл index.js вы должны увидеть следующее:
var express = require('express');
var router = express.Router();
/* Получить главную страницу. */
router.get('/', function(req, res) {
res.render('index', { title: 'Express' });
});
module.exports = router;
router.get
Это функция, которая получит адрес пути /. Затем нам нужно создать функцию, которая будет делать req (запрос) и res (ответ). Другая концепция next для цепочки событий также хорошо подошла бы сюда, но не показана в данном примере.
Что такое module.exports?
Это объект, который возвращается как результат запрашиваемого вызова. Эта особенность Node, больше о ней написано здесь.
Построение нового маршрута
Глядя на шаблон синтаксиса, если мы хотим добавить новый маршрут в приложение, то можем просто сделать что-то вроде следующего:
router.get('/app', function(req, res) {
res.render('app', { title: 'Express' });
});
Это маршрут? Это контроллер?
Самое интересное что маршрут это функция, содержащая логику. Внутри маршрута находится функция res.render:
res.render('foo', { title: 'Express' });
В шаблоне представления мы видим это:
h1= title
p Добро пожаловать в #{title}
Это два примера того, как мы можем вытащить данные из controller/route и вывести их в представлении. В этом примере мы выводим HTML:
<h1>Express</h1>
<p>Добро пожаловать в Express</p>
Всё это, кажется, вытекает из проблемы — может ли маршрут также содержать информацию контроллера? Это верно, поэтому есть движение в обществе за то, чтобы изменить имя папки с routes на controllers.
Отличный пример этого можно увидеть в примере Express MVC.
Но ради логичности в этом руководстве мы будем держаться текущих соглашений.
Ошибки 404
Ошибки уже направляют вас в Express. В файле app.js есть следующее:
/// поймать 404 и перенаправить в обработчик ошибки
app.use(function(req, res, next) {
var err = new Error('Не найдено');
err.status = 404;
next(err);
});
В папке views/ есть errors.jade.
extends layout
block content
h1= message
h2= error.status
pre #{error.stack}
Всё просто. Если вы хотите настроить свою страницу 404, то всего-лишь редактируйте это представление.