Ключевые новинки в Rails 5.1:
Эти заметки о релизе покрывают только основные изменения. Чтобы узнать о других обновлениях, различных исправлениях программных ошибок и изменениях, обратитесь к логам изменений или к списку коммитов в главном репозитории Rails на GitHub.
Прежде чем апгрейднуть существующее приложение, было бы хорошо иметь перед этим покрытие тестами. Также, до попытки обновиться до Rails 5.1, необходимо сначала произвести апгрейд до Rails 5.0 и убедиться, что приложение все еще выполняется так, как нужно. Список вещей, которые нужно выполнить для апгрейда доступен в руководстве Апгрейд Ruby on Rails.
Rails 5.1 позволяет управлять зависимостями JavaScript из npm с помощью Yarn. Это облегчает использование библиотек, таких как React, VueJS и любых других из мира npm. Поддержка Yarn интегрирована с конвейером ресурсов, поэтому все зависимости будут без проблем работать с приложением Rails 5.1.
Приложения Rails можно интегрировать с Webpack, пакетированием ассетов JavaScript, используя новый стандартный гем Webpacker. Укажите флажок --webpack
при генерации новых приложений, чтобы включить интеграцию с Webpack.
Она полностью совместима с конвейером ресурсов, который можно продолжать использовать для картинок, шрифтов, звуков и других ассетов. Можно даже оставить некоторый код JavaScript, управляемый конвейером ресурсов, а остальной код обрабатывать через Webpack. Все это управляется с помощью Yarn, который включен по умолчанию.
jQuery требовался по умолчанию в ранних версиях Rails для предоставления особенностей, таких как data-remote
, data-confirm
и других частей, предлагаемых Unobtrusive JavaScript в Rails. Он больше не требуется, так как UJS был переписан с использованием чистого JavaScript. Этот код теперь находится внутри Action View как rails-ujs
.
При необходимости все еще можно использовать jQuery, но он больше не требуется по умолчанию.
Rails 5.1 имеет встроенную поддержку для написания тестов Capybara в форме системных тестов. Больше не нужно беспокоиться о настройке Capybara и стратегиях очистки базы данных для таких тестов. Rails 5.1 предоставляет обертку для запусков тестов в Chrome с дополнительными особенностями, такими как скриншоты при падении.
Сейчас Rails позволяет управлять секретами приложения безопасным образом, наподобие гема sekrets.
Запустите bin/rails secrets:setup
для настройки нового зашифрованного файла с секретами. Это также сгенерирует мастер-ключ, который должен храниться вне репозитория. Тогда сами секреты могут безопасно добавляться в систему контроля версий в зашифрованной форме.
Секреты будут дешифрованы в production с помощью ключа, либо хранящегося в переменной окружения RAILS_MASTER_KEY
, либо в файле с ключом.
Позволяют определить общие параметры, используемые всеми методами в классе рассыльщика, для переменных экземпляра, заголовков и других общих настроек.
class InvitationsMailer < ApplicationMailer
before_action { @inviter, @invitee = params[:inviter], params[:invitee] }
before_action { @account = params[:inviter].account }
def account_invitation
mail subject: "#{@inviter.name} invited you to their Basecamp (#{@account.name})"
end
end
InvitationsMailer.with(inviter: person_a, invitee: person_b)
.account_invitation.deliver_later
Rails 5.1 добавляет в DSL роутинга два новых метода, resolve
и direct
. Метод resolve
позволяет настроить полиморфное сопоставление моделей.
resource :basket
resolve("Basket") { [:basket] }
<%= form_for @basket do |form| %>
<!-- basket form -->
<% end %>
Это сгенерирует одиночный URL /basket
вместо обычного /baskets/:id
.
Метод direct
позволяет создавать хелперы для произвольного URL.
direct(:homepage) { "http://rubyonrails.org" }
homepage_url # => "http://rubyonrails.org"
Возвращаемое из блока значение должно быть валидным аргументом для метода url_for
. Поэтому можно передать валидные строковый URL, Hash, Array, экземпляр Active Model или класс Active Model.
direct :commentable do |model|
[ model, anchor: model.dom_id ]
end
direct :main do
{ controller: 'pages', action: 'index', subdomain: 'www' }
end
До Rails 5.1 было два интерфейса для обработки форм HTML: form_for
для экземпляров моделей и form_tag
для произвольных URL.
Rails 5.1 объединяет оба этих интерфейса с помощью form_with
и может генерировать теги формы, основанные на URL, скоупах или моделях.
Используя просто URL:
<%= form_with url: posts_path do |form| %>
<%= form.text_field :title %>
<% end %>
<%# Сгенерирует %>
<form action="/posts" method="post" data-remote="true">
<input type="text" name="title">
</form>
Добавление скоупа добавляет префикс для имен полей ввода:
<%= form_with scope: :post, url: posts_path do |form| %>
<%= form.text_field :title %>
<% end %>
<%# Сгенерирует %>
<form action="/posts" method="post" data-remote="true">
<input type="text" name="post[title]">
</form>
URL и скоуп на основе используемой модели:
<%= form_with model: Post.new do |form| %>
<%= form.text_field :title %>
<% end %>
<%# Сгенерирует %>
<form action="/posts" method="post" data-remote="true">
<input type="text" name="post[title]">
</form>
Существующая модель создает форму для обновления и заполняет значения для полей:
<%= form_with model: Post.first do |form| %>
<%= form.text_field :title %>
<% end %>
<%# Сгенерирует %>
<form action="/posts/1" method="post" data-remote="true">
<input type="hidden" name="_method" value="patch">
<input type="text" name="post[title]" value="<the title of the post>">
</form>
Следующие изменения могут потребовать немедленных действий после апгрейде.
Сейчас транзакционные тесты оборачивают все соединения Active Record в транзакции базы данных.
Когда тест порождает дополнительные треды, и эти треды получают соединения с базой данных, то эти соединения теперь обрабатываются по-особенному:
Тредам достается единственное соединение, которое находится посреди управляемой транзакции. Это позволяет убедиться, что все треды видят базу данных в одном и том же состоянии, игнорируя внешнюю транзакцию. Раньше такие дополнительные соединения были неспособны видеть, к примеру, строки фикстур.
Когда тред входит во вложенную транзакцию, он временно получает эксклюзивное использование этого соединения для поддержки изоляции.
Если ваши тесты сейчас полагаются на получение отдельного, внетранзакционного соединения для порождаемого треда, вам необходимо переключиться на более явное управление соединением.
Если ваши тесты порождают треды, и эти треды взаимодействуют, в то же время используя явные соединения с базой данных, то это может вызвать дедлок (deadlock).
Самым простым способом отказаться от подобного нового поведения является отключение транзакционных тестов для всех тестовых случаев, которые оно затрагивает.
За подробностями обратитесь к Changelog.
Удалена устаревшая config.static_cache_control
.
(commit)
Удалена устаревшая config.serve_static_files
.
(commit)
Удален устаревший файл rails/rack/debugger
.
(commit)
Удалены устаревшие задачи: rails:update
, rails:template
, rails:template:copy
, rails:update:configs
и rails:update:bin
.
(commit)
Удалена устаревшая переменная среды CONTROLLER
для задачи routes
.
(commit)
Удалена опция -j (--javascript) для команды rails new
.
(Pull Request)
Добавлена общий раздел в config/secrets.yml
, которая будет загружена для всех сред.
(commit)
Конфигурационный файл config/secrets.yml
теперь загружается со всеми ключами в качестве символов.
(Pull Request)
Убран jquery-rails из стека по умолчанию. rails-ujs, который теперь встроен в Action View, включен в качестве адаптера UJS по умолчанию. (Pull Request)
Добавлена поддержка Yarn для новых приложений с помощью бинстаба yarn и package.json. (Pull Request)
В новых приложениях добавлена поддержка Webpack с помощью опции --webpack
, которая делегируется в гем rails/webpacker.
(Pull Request)
При генерации нового приложения инициализируется репозиторий Git, если не предоставлена опция --skip-git
.
(Pull Request)
Добавлены зашифрованные секреты в config/secrets.yml.enc
.
(Pull Request)
Отображается имя класса railtie в rails initializers
.
(Pull Request)
За подробностями обратитесь к Changelog.
Добавлена поддержка channel_prefix
к Redis и событийным адаптерам Redis в cable.yml
, чтобы избежать коллизии имен при использовании одного и того же сервера Redis с несколькими приложениями.
(Pull Request)
Для данных трансляции добавлен хук ActiveSupport::Notifications
.
(Pull Request)
За подробностями обратитесь к Changelog.
Удалена поддержка аргументов, не являющихся ключами, в #process
, #get
, #post
, #patch
, #put
, #delete
и #head
для классов ActionDispatch::IntegrationTest
и ActionController::TestCase
.
(Commit,
Commit)
Удалены устаревшие ActionDispatch::Callbacks.to_prepare
и ActionDispatch::Callbacks.to_cleanup
.
(Commit)
Удалены устаревшие методы, относящиеся к фильтрам контроллера. (Commit)
Удалена устаревшая поддержка :text
и :nothing
в render
.
(Commit,
Commit)
Удалена устаревшая поддержка для вызова метода HashWithIndifferentAccess
на ActionController::Parameters
.
(Commit)
config.action_controller.raise_on_unfiltered_parameters
. Он ничего не делает в Rails 5.1.
(Commit)
Добавлены методы direct
и resolve
в DSL роутинга.
(Pull Request)
Добавлен новый класс ActionDispatch::SystemTestCase
для написания системных тестов вашего приложения.
(Pull Request)
За подробностями обратитесь к Changelog.
Удален устаревший #original_exception
в ActionView::Template::Error
.
(commit)
Удалена неправильно названная опция encode_special_chars
из strip_tags
.
(Pull Request)
Обработчик raw шаблонов (обработчик шаблонов по умолчанию в Rails 5) теперь выводит HTML-безопасные строки. (commit)
Изменены datetime_field
и datetime_field_tag
, чтобы они генерировали поле datetime-local
.
(Pull Request)
Новый синтаксис в стиле Builder для тегов HTML (tag.div
, tag.br
и т.д.)
(Pull Request)
Добавлен form_with
, объединяющий использование form_tag
и form_for
.
(Pull Request)
Добавлена опция check_parameters
в current_page?
.
(Pull Request)
За подробностями обратитесь к Changelog.
Разрешена установка произвольного типа содержимого, когда включены прикрепленные файлы и тело установлено как встроенное. (Pull Request)
Разрешена передача lambda в качестве значений в метод default
.
(Commit)
Добавлена поддержка параметризованного вызова рассыльщиков для совместного использования предварительных (before) фильтров и значений по умолчанию различными экшнами рассыльщика. (Commit)
Входящие аргументы передаются в экшн рассыльщика в событии process.action_mailer
в ключе args
.
(Pull Request)
За подробностями обратитесь к Changelog.
Удалена поддержка одновременной передачи аргументов и блока в ActiveRecord::QueryMethods#select
.
(Commit)
Удалены устаревшие скоупы i18n activerecord.errors.messages.restrict_dependent_destroy.one
и activerecord.errors.messages.restrict_dependent_destroy.many
.
(Commit)
Удален устаревший аргумент принудительной перезагрузки для методов чтения одиночной и множественной связи. (Commit)
Удалена устаревшая поддержка передачи столбца в #quote
.
(Commit)
Удалены устаревшие аргументы name
из #tables
.
(Commit)
Удалено устаревшее поведение #tables
, и #table_exists?
, которое возвращало таблицы и представления, чтобы теперь возвращало только таблицы, но не представления.
(Commit)
Удален устаревший аргумент original_exception
в ActiveRecord::StatementInvalid#initialize
и ActiveRecord::StatementInvalid#original_exception
.
(Commit)
Удалена устаревшая поддержка передачи класса в качестве значения в запрос. (Commit)
Удалена устаревшая поддержка запросов с использованием запятых в LIMIT. (Commit)
Удален устаревший параметр conditions
из #destroy_all
.
(Commit)
Удален устаревший параметр conditions
из #delete_all
.
(Commit)
Удален устаревший метод #load_schema_for
в пользу #load_schema
.
(Commit)
Удалена устаревшая конфигурация #raise_in_transactional_callbacks
.
(Commit)
Удалена устаревшая конфигурация #use_transactional_fixtures
.
(Commit)
Устаревший флажок error_on_ignored_order_or_limit
заменен в пользу error_on_ignored_order
.
(Commit)
Устаревший sanitize_conditions
заменен в пользу sanitize_sql
.
(Pull Request)
Устарел supports_migrations?
в адаптерах соединения.
(Pull Request)
Устарел Migrator.schema_migrations_table_name
, вместо него используйте SchemaMigration.table_name
.
(Pull Request)
Устарело использование #quoted_id
в квотировании и приведении типов.
(Pull Request)
Устарела передача аргумента default
в #index_name_exists?
.
(Pull Request)
Изменены первичные ключи по умолчанию на BIGINT. (Pull Request)
Поддержка виртуальных/генерированных столбцов для MySQL 5.7.5+ и MariaDB 5.2.0+. (Commit)
Добавлена поддержка лимитов в обработке пакетами. (Commit)
Транзакционные тесты теперь оборачивают все соединения Active Record в транзакцию базы данных. (Pull Request)
По умолчанию опускаются комментарии в выводе команды mysqldump
.
(Pull Request)
Починен ActiveRecord::Relation#count
, чтобы использовался Enumerable#count
из Ruby для подсчета записей, когда передан блок, вместо игнорирования переданного блока.
(Pull Request)
Передача флажка "-v ON_ERROR_STOP=1"
команде psql
не подавляет ошибки SQL.
(Pull Request)
Добавлен ActiveRecord::Base.connection_pool.stat
.
(Pull Request)
Наследование непосредственно от ActiveRecord::Migration
вызывает ошибку. Необходимо указывать версию Rails, для которой была написана миграция.
(Commit)
Вызывается ошибка, когда у связи through
имеется избыточное имя противоположной связи.
(Commit)
За подробностями обратитесь к Changelog.
Удалены устаревшие методы в ActiveModel::Errors
.
(commit)
Удалена устаревшая опция :tokenizer
в валидаторе длины.
(commit)
Удалено устаревшее поведение, прерывающее колбэки, когда возвращаемое значение равно false. (commit)
За подробностями обратитесь к Changelog.
Удалена устаревшая поддержка передачи класса адаптера в .queue_adapter
.
(commit)
Удален устаревший #original_exception
в ActiveJob::DeserializationError
.
(commit)
Добавлена декларативная обработка исключений с помощью ActiveJob::Base.retry_on
и ActiveJob::Base.discard_on
.
(Pull Request)
После того, как все попытки провалятся, передается экземпляр задания, поэтому у вас будет доступ к таким вещам, как job.arguments
, для реализации собственной логики.
(commit)
За подробностями обратитесь к Changelog.
Удален класс ActiveSupport::Concurrency::Latch
.
(Commit)
Удалена halt_callback_chains_on_return_false
.
(Commit)
Удалено устаревшее поведение, прерывающее колбэки, когда возвращаемое значение равно false. (Commit)
Верхнеуровневый класс HashWithIndifferentAccess
устарел в пользу ActiveSupport::HashWithIndifferentAccess
.
(Pull Request)
Устарела передача строк в опции условий :if
и :unless
для методов set_callback
и skip_callback
.
(Commit)
Починен парсинг продолжительности и перемещения во времени, теперь он более последователен при смене DST. (Commit, Pull Request)
Unicode обновлен до версии 9.0.0. (Pull Request)
Добавлены Duration#before и #after в качестве псевдонимов для #ago и #since. (Pull Request)
Добавлен Module#delegate_missing_to
для делегирования вызовов метода, не определенного для текущего объекта, на прокси-объект.
(Pull Request)
Добавлен Date#all_day
, возвращающий интервал, представляющий целый день для текущих даты и времени.
(Pull Request)
Представлены методы assert_changes
и assert_no_changes
для тестов.
(Pull Request)
Методы travel
и travel_to
теперь вызывают ошибку на вложенных вызовах.
(Pull Request)
Обновлен DateTime#change
для поддержки usec и nsec.
(Pull Request)
Взгляните на полный список контрибьюторов Rails, на людей, которые потратили много часов, сделав Rails стабильнее и надёжнее. Спасибо им всем.