Эта инструкция рассказывает как создать приложение на Rails API в качестве бекенда с Ember на фронтенде c нуля. Cтатья объединяет два поста на эту тему первый и второй.
Обзор
От переводчика: Оригинал статьи aviav
Создаем бекенд
На момент написания статьи Rails 5 требует Ruby версии 2.2.2 и выше, если вы используете rvm, выполните rvm install 2.2.3, чтобы установить требуемую версию. Чтобы использовать в качестве дефолтной версии rvm use 2.2.3 --default.
От переводчика: Для каждого проекта, я рекомендую создавать отдельный гемсет, дабы не испытывать проблем с зависимостями, это можно сделать по моей статье.
Так как Rails 5 на данный момент не зарелизен, нам нужно клонировать репозиторий на Github и генерировать приложение из исходников. Для этого выполняем команды:
git clone git://github.com/rails/rails.git
cd rails
bundle
bundle exec railties/exe/rails new ../my_api_app --api --edgeОт переводчика: Лично у меня, на третьей команде возникли трудности с установкой гема nokogiri, помогла команда
gem install nokogiri -v 1.6.7rc3 --pre.
Генерируем ресурс пользователи
Мы сгенерируем очень простое приложение с помощью генератора rails (rails generate scaffold) и выполним миграции:
cd ../my_api_app
bin/rails g scaffold user name
bin/rake db:migrateУстановим JSON формат сериализации данных
REST адаптер Ember требует чтобы root объекты были представлены в JSON. Это можно достигнуть установкой json адаптера вместо flatten_json сериалайзера Active Model.
Создаем новый файл инициализации config/initializers/ams_json_adapter.rb включающий следующий текст:
ActiveModel::Serializer.config.adapter = :jsonЧтобы протестировать что данные представляются в нужном формате, запустим сервер с помощью команды bin/rails server и создадим нового пользователя с помощью curl:
curl -H "Content-Type:application/json; charset=utf-8" \
-d '{"user": {"name":"Hans"}}' http://localhost:3000/usersОткрыв в браузере localhost:3000/users, мы можем увидеть только что созданного пользователя и то что данные отображаются в формате, который мы указали.
Установка CORS
Так как наши бекенд и фронтенд будут запускаться отдельно, нам нужно сконфигурировать Cross Origin Resource Sharing (CORS). Мы будем пробовать бекенд на localhost:3000 и фронтенд на localhost:4200. В начале, нам нужно раскомментировать rack-cors в Gemfile, запустить bundle и добавить следующий код в config/initializers/cors.rb:
# Avoid CORS issues when API is called from the frontend app
# Handle Cross-Origin Resource Sharing (CORS) in order to accept cross-origin AJAX requests
# Read more: https://github.com/cyu/rack-cors
Rails.application.config.middleware.insert_before 0, "Rack::Cors" do
allow do
origins 'localhost:4200'
resource '*',
headers: :any,
methods: [:get, :post, :put, :patch, :delete, :options, :head]
end
endОт переводчика: здесь и далее, я советую использовать адрес 0.0.0.0 для запуска серверов вместо localhost.
Создаем фронтенд
Данная инструкция включает Ember приложение, которое использует простой ресурс Users чтобы получать данные от Rails API и показывать их на главной странице.
Установка Ember CLI и созадние фронтенд
Для установки Ember CLI, мы используем –no-optional, так как он менее подвержен ошибкам. Используя nvm, нам не нужно запускать npm от пользователя root, это исключает проблемы прав:
npm install -g ember-cli --no-optionalCreate the Ember.js app:
cd ..
ember new my_ember_frontend
cd my_ember_frontendНа момент написания статьи, даже с использованием текущей версии node.js, появляется предупреждение:
Future versions of Ember CLI will not support v4.1.0. Please update to Node 0.12 or io.js.Не волнуйтесь: фикс этого ошибочного сообщения анонсирован и будет добавлен в следущих версиях Ember CLI.
Генерируем адаптер приложения
Чтобы заставить наше приложение на Ember общаться с Rails приложением, мы сгенерируем адаптер:
ember generate adapter applicationТеперь отредактируем файл app/adapters/application.js:
import DS from 'ember-data';
export default DS.ActiveModelAdapter.extend({
host: 'http://localhost:3000'
});Добавляем ресурс Users в router.js
Редактируем app/router.js:
import Ember from 'ember';
import config from './config/environment';
var Router = Ember.Router.extend({
location: config.locationType
});
Router.map(function() {
this.resource('users');
});
export default Router;Генерируем модель User
Вначале,
ember generate model userЗатем редактируем app/models/user.js:
import DS from 'ember-data';
export default DS.Model.extend({
name: DS.attr('string')
});Генерируем маршрут Users/index
Теперь,
ember generate route users/indexРедактируем app/routes/users/index.js:
import Ember from 'ember';
export default Ember.Route.extend({
model: function() {
return this.store.findAll('user');
}
});Пишем шаблон для Users/index
Редактируем app/templates/users/index.hbs:
<ul>
{ {#each model as |user|}}
<li> { {user.name}} </li>
{ {/each}}
</ul>
{ {outlet}}Тестируем приложение
Чтобы протестировать наше приложение, запустим в директории Rails приложения:
bin/rails sи в каталоге Ember приложения:
ember serveТеперь откроем в браузере страницу localhost:4200/users чтобы проверить работу приложения!
Большое спасибо уходит Moritz за корректировку данного поста!