Auto timestamps on bulk inserts, HTML safe translations in controllers and more

Hey, Wojtek here with last week updates from the Ruby on Rails world.

Set timestamps on insert_all/upsert_all record creation

The timestamps will be automatically set when using bulk insert/upsert. This behaviour can be disabled by the record_timestamps config on the model class.

Treat html suffix in controller translation

When translation key ending with _html is used it will be marked as HTML safe in the same way as in the views.

Add support for FILTER clause to Arel

Can be used with PostgreSQL and SQlite databases to use FILTER clause.

Better Action Text plain text output for nested lists

Fixed an issue with how nested lists were displayed when converting to plain text.

Add support for custom CSRF strategies.

Can be used via protect_from_forgery with: CustomStrategy among built in options: exception, reset_session, null_session.

Clear secure password cache if password is set to nil

user.password = 'something'
user.password = nil
# before:
user.password # => 'something'    
# now:
user.password # => nil  

29 people contributed to Rails since the last time. All the changes can be checked here. Until next week!

Automatic inverse_of, performance improvements and more!

Hi, this is Greg, bringing you the latest news about Ruby on Rails!

This week we switched our newsletter delivery platform to HEY, if you are reading this email, you already confirmed your subscription and there is no other action needed on your end.

Avoid instance_exec for controller callbacks

This change brings some performance improvements, by avoiding to create the extra controller singleton classes, created by instance_exec, when :only or :except are passed to a callback.

Automatically infer inverse_of with scopes

This PR changes can_find_inverse_of_automatically to allow us to automatically detect inverse_of when there is a scope on the association, but not when there is a scope on the potential inverse association. Since this is a breaking change, it is placed behind the automatic_scope_inversing configuration flag, which is set to true for new applications via framework defaults.

Add ability to lazily load the schema cache on connection

A new a configuration option enables lazy loading of the schema cache on the connection. If config.active_record.lazily_load_schema_cache is set to true then the schema cache will be loaded when the connection is established rather than on boot.

31 people contributed to Rails since last time. All the changes can be checked here. Until next week!

Autumn is here, and so is Rails 7 Alpha 2! 🍂

Hey! Zzak here with a JAM-PACKED edition of This Week In Rails. 🍇

Server Timing Middleware for Development

This PR started nearly 2 and a half years ago, finally made its way into Rails!

A really neat feature, uses the Server-Timing header to emit durations for all ActiveSupport::Notifications. You can then view these metrics in your browser’s Network Inspector. 

If your model defines #to_s, you can now take advantage of this feature without having to supply a second argument to link_to.

Adds support for deferrable foreign key constraints in PostgreSQL

By default, foreign key constraints in PostgreSQL are checked after each statement. This works for most use cases, but becomes a major limitation when creating related records before the parent record is inserted into the database. Check out the PR for some examples and more detail.

GitHub Codespaces configuration

This PR adds support for GitHub Codespaces, which allows contributors to easily boot a fully functional environment to create patches and test changes to Rails.

Close Rails Guides menu dropdown by pressing Escape

A welcome UX patch that lets you close the menu dropdown by pressing the Escape key.

Improve margin styles for Rails Guides

We always appreciate when folks help improve our documentation, especially the visual aspect to make reading on multiple devices a pleasure.

Fix the diff highlight background for Rails Guides dark mode

Another great UX patch for Rails Guides that is always appreciated.

Suggest a CSP that’s compatible with Turbo + import map

In order for CSP to work with Turbo and an import map, we need nonces to be generated. This PR changes the generated CSP initializer to use per-session nonces instead of per-request nonces which would have negative impact on caching.

Add Bootstrap and Bulma to the CSS processors’ list

As support for more CSS processors are added to cssbundling-rails, we’ve updated the rails new --help text to include currently available options.

Don’t overwrite default opts in rich_text_area_tag

This PR enables passing in a custom direct_upload_url or blob_url_template to rich_text_area_tag. In the case you want to use your own controller to authenticate requests or perform server-side validations.

Avoid comment statements in pg:dump

This PR adds the –no-comment flag to pg_dump to ensure COMMENT statements are omitted from the output when using PostgreSQL >= 11.

Require latest release candidate for selenium-webdriver in Rails new

Since the “rexml” gem was removed from Ruby version >= 3 the selenium-webdriver gem has been waiting for a release that includes their updated dependency on the standard library gem.

Support clearing acronyms from inflector

Previously attempting to clear acronyms in the Inflector breaks would result in a TypeError.

Allow permitting numeric params

ActionController::Parameters now lets you specify multiple parameters index by a number. This may be necessary if the parameters belong to a numeric key.

Check basic auth credentials before authenticate

This PR fixes a bug when sending invalid basic authorization header data when using http_basic_authentication_with.

Render host_authorization debug view only for local requests

This PR fixes a bug where debugging information was visible in production by restricting access to local requests only.

Add missing migrate command to Getting Started Rails Guide

This might seem like a minor patch, but contributions from folks learning Ruby on Rails for the first time is a healthy sign. Changes like these help ease the difficulty of learning and welcomes new contributors to the community.

Active Storage: deprecate invalid default content types

Blobs created with content_type image/jpg, image/pjpeg, image/bmp, text/javascript will now produce a deprecation warning, since these are not valid content types.

Allow configuring PostgreSQL connection password through socket URL

This PR allows you to specify your password using a socket URL, such as “postgres:///?user=user&password=secret&dbname=app”.

Add autocomplete=”off” to all generated hidden fields

Due to a longstanding Firefox bug, this PR ensures hidden fields such as CSRF token and HTTP method fields are not modified without the user’s knowledge.

Add beginning_of_week option to weekday_options_for_select

Now you can specify the beginning of the week to this select field without depending on Date.beginning_of_week.

Action Mailer email_address_with_name now returns the email if name is blank

When sending an email using Action Mailer the object referencing the person you want to send it to may not have a name associated with it. For example, in the case this field is optional for your User record. In this case Action Mailer will now use the target email address.

Add missing DOM ids to rails/mailers/email.html template

This PR will help folks testing their Mailer Preview actions by using unique identifiers to select the mail data from the DOM instantly.

35 people contributed (over 120 commits!) to Rails since last time. All the changes can be checked here. Until next week!

Rails 7 alpha released

Hi, Wojtek here with more new Rails 7 changes.

Rails 7.0 alpha released

The new Rails frontend approach and all the other new goodies can already be checked in this release.

Introduce ActiveModel::API

Make ActiveModel::API the minimum API to talk with Action Pack and Action View. This will allow adding more functionality to ActiveModel::Model.

Add support for generated columns in PostgreSQL

Generated columns are supported since version 12.0 of PostgreSQL. This adds
 support of those to the Active Record PostgreSQL adapter.

Generate less initializers in new/upgraded Rails apps

Removed configurations are set by the default Rails configuration and can be still changed when needed.

Use correct precision when touching updated_at column in upsert

CURRENT_TIMESTAMP provides differing precision depending on the database,
and not all databases support explicitly specifying additional precision. Instead, delegate to the new connection.high_precision_current_timestamp
for the SQL to produce a high precision timestamp on the current database.

13 people contributed to Rails since last time. All the changes can be checked here. Until next week!

Rails 7.0 Alpha 1: New JavaScript Answers, At-Work Encryption, Query Origin Logging, Zeitwerk Exclusively

Welcome to the first alpha release of Rails 7. It brings some very exciting new answers to how we do JavaScript, an awesome approach to at-work encryption with Active Record, SQL query origin logging, asynchronous query loading, exclusive autoloading through Zeitwerk, and much more.

We usually don’t do alpha releases for Rails, but given the fact that the new front-end approach is such a substantial change, we thought it best to validate that a little further before jumping straight on the beta -> release candidate -> final train.

Please help us test all this new stuff so we can ensure a solid final release of Rails 7 this year!

All New Answers On The Front-End

After almost five years with Webpacker as our default answer to writing modern JavaScript in Rails, it’s time to move on. Advancements in browser support for ES6/ESM, widespread adoption of HTTP/2, and the exciting new standard for import maps has paved the way for a no-Node approach to JavaScript in Rails 7without giving up on npm packages.

Together with the replacement of Turbolinks and Rails UJS by the Hotwire combination of Stimulus and Turbo, we now have the most complete in-the-box front-end setup for writing great Rails applications ever. Without needing thousands of node dependencies in node_modules, fighting with bundler configurations, or any of the other challenges common with JavaScript development.

At the same time, we’ve also dramatically improved the integration between Rails and JavaScript + CSS bundlers for those who need that. Through two new companion gems that can be triggered via rails new –javascript [bundler] and –css [bundler], you get easy access to starting a new application or changing one that starts with import maps to use esbuild, rollup.js, Webpack, Tailwind CSS, PostCSS, Dart Sass, and Bootstrap.

At-Work Encryption With Active Record

Extracted from HEY, we’ve added encrypted attributes to Active Record, so your application can offer at-work encryption in addition to the traditional at-rest and in-transit coverage.

As an immediate practical benefit, encrypting sensitive attributes adds an additional security layer. For example, if an attacker gained access to your database, a snapshot of it, or your application logs, they wouldn’t be able to make sense of the encrypted information. And even without thinking about malicious actors, checking application logs for legit reasons shouldn’t expose personal information from customers either.

But more importantly, by using Active Record Encryption, you define what constitutes sensitive information in your application at the code level. This enables controlling how this information is accessed and building services around it. As examples, think about auditable Rails consoles that protect encrypted data or check the built-in system to filter controller params automatically.

Checkout the full guide on how to use encrypted attributes.

Trace Query Origins With Marginalia-Style Tagging

Almost a decade ago, Marginalia was extracted from Basecamp to trace query origins with SQL comment tagging. Now this external gem has been upstreamed into Active Record as QueryLogs.

Asynchronous Query Loading

When you have a controller action that needs to load two unrelated queries, you can now do it concurrently through Relation#load_async. If you have three complex queries that each take 100ms, you’d have to spend 300ms executing them one by one before. Now you can run them in parallel, spending only a total of 100ms on the set.

Zeitwerk Exclusively

Autoloading in Rails is one of those magical quality of life realities that it’s easy to just take for granted. The trusty old const_missing approach which came with a range of quirks and missing features has finally been replaced exclusively with the Zeitwerk code loader. There are a few upgrade gotchas to be aware of, especially for older applications, but with this upgrade guide you should be on your way in no time

A Few Other Highlights

From All Of Us To All Of You

There are over three thousand commits that have gone into Rails 7 since we released version 6.1 last year. This is the work of hundreds of contributors. Including over 200 first-time contributors this year alone. They join the nearly six thousand contributors that have made changes to the Rails code base over the years!

Bye-bye Byebug, Hello jsbundling and cssbundling!

Hi! zzak here! We’re back after a 2 week break with some of the latest changes that will land in Rails 7.

DHH previews JavaScript options in Rails 7 [YouTube]

If you haven’t been following along, Rails 7 will get a major facelift on the front-end. We recommend reading this blog post to learn more.

Replace Byebug with ruby/debug

Ruby 3.1 will launch with a new first-class debugger that works great with Rails.

Let’s all appreciate the many years Byebug has helped us ship software.

Add SSL support for postgresql in “bin/rails dbconsole”

This PR fixes the dbconsole command when used with PostgreSQL to support encrypted connections.

Instrument ActiveStorage analyzers

Help identify bottle necks when using ActiveStorage analyzers by emitting ActiveSupport instrumentation metrics.

Add –css app generator option

The rails new command just got a brand new --css flag that let’s you specify which CSS processor to use in your app. You can choose from tailwind, postcss, or sass.

21 people contributed to Rails since last time. All the changes can be checked here. Until next week!

Autoloading in Rails 7, get ready!

The forthcoming Rails 7 represents a milestone for autoloading.

There are two important changes coming:

  1. Zeitwerk has been the default autoloader for more than two years. Rails 6.0 and Rails 6.1 supported both zeitwerk and classic modes to help projects transition. This period ends with Rails 7: classic mode won’t be available anymore.

  2. Initializers can autoload reloadable constants if wrapped in to_prepare blocks, but they no longer can otherwise.

Maybe your 6.x application is already ready for these changes. Otherwise, you can prepare in advance to ease the upgrade. Let’s briefly explore their implications.

Applications need to run in zeitwerk mode

Applications still running in classic mode have to switch to zeitwerk mode.

Don’t be scared, many non-trivial Rails applications reported really smooth switches. It is very likely that you only need to flip the switch, maybe configure some inflector, and done. Please check the upgrading guide for Rails 6.0 for details.

I am personally more than willing to help if you find anything unexpected, just open an issue and tag @fxn.

The setter config.autoloader= has been deleted

In Rails 7 there is no configuration point to set the autoloading mode, config.autoloader= has been deleted.

ActiveSupport::Dependencies private API has been deleted

You don’t announce changes to internal APIs, but since classic has been there since the first release of Rails, this is worth being included in this post.

ActiveSupport::Dependencies implemented the classic autoloader, and with its removal a lot of internal methods have been dropped in cascade like hook!, unhook!, depend_on, require_or_load, mechanism, qualified_name_for, warnings_on_first_load, logger, verbose, and many others.

Auxiliary internal classes or modules are also gone, like Reference, ClassCache, ModuleConstMissing, Blamable, and more.

About 90% of active_support/dependencies.rb has been deleted. You can compare the version in edge with the one in 6.1.

Autoloading during initialization

Applications that autoloaded reloadable constants during initialization outside of to_prepare blocks got those constants unloaded and had this warning issued since Rails 6.0:

DEPRECATION WARNING: Initialization autoloaded the constant User.

Being able to do this is deprecated. Autoloading during initialization is going
to be an error condition in future versions of Rails.

Reloading does not reboot the application, and therefore code executed during
initialization does not run again. So, if you reload User, for example,
the expected changes won't be reflected in that stale Class object.

This autoloaded constant has been unloaded.

In order to autoload safely at boot time, please wrap your code in a reloader
callback this way:

    Rails.application.reloader.to_prepare do
      # Autoload classes and modules needed at boot time here.
    end

That block runs when the application boots, and every time there is a reload.
For historical reasons, it may run twice, so it has to be idempotent.

Check the "Autoloading and Reloading Constants" guide to learn more about how
Rails autoloads and reloads.
 (called from ...)

If you still get this warning, please check the section about autoloading when the application boots in the autoloading guide. You’d get a NameError in Rails 7 otherwise.

Rails.autoloaders.zeitwerk_enabled?

Engines that want to support Rails 6.x can check

Rails.autoloaders.zeitwerk_enabled?

to know if the parent application runs in zeitwerk mode. This predicate still exists in Rails 7 for this use case.

Remove default reliance on Sass and more!

Hi, this is Greg, bringing you the latest changes in Rails.

Remove default reliance on Sass and CSS generators

Due to Saas has chosen to focus exclusively on dart-saas, Rails is decreasing its reliance on it. Besides that, this PR also removes the per model css file generation.

Avoid use of exceptions to detect invalid floats

This PR Improves the performance of ActiveSupport::NumberHelper and ActionView::Helpers::NumberHelper formatters by avoiding the use of exceptions as flow control.

Prior to this change, preload_link_tag with an image would generate a tag without an as attribute. If the as attribute doesn’t get set, browsers tend to ignore the link tag, making the tag useless. This change fixes the issue.

Add ability to ignore tables in the schema cache

In cases where an application uses pt-osc or lhm they may have temporary tables being used for migrations. Those tables shouldn’t be included by the schema cache because it makes the cache bigger and after this change, on_e can set config.active_record.schema_cache_ignored_tables_ to an array of tables or regex’s.

22 people contributed to Rails since last time. All the changes can be checked here. Until next week!

Good-bye classic mode, --skip-puma, --skip-gemfile.. hello weekday_options_for_select!

Hello, zzak again with the latest changes in Rails this week!

DHH previews modern web apps without JavaScript bundling or transpiling

In this YouTube, DHH goes through the latest changes planned for Rails 7 and how the face of front-end development has evolved.

Rails 6.0.4.1 and 6.1.4.1 have been released

A reminder to upgrade to the latest stable versions of Rails which includes a critical security fix for Action Pack.

Dropping support for classic mode

There’s an ongoing epic to delete the classic autoloader that started months ago. Let’s do a checkpoint in this newsletter.

You can no longer opt-in to classic mode using config.autoloader=, this setter has been deleted, Rails 7 has only one autoloading backend: Zeitwerk.

During application initialization, you can autoload classes and modules from config.autoload_once_paths, but autoloading reloadable constants doesn’t work anymore. That has been deprecated and issuing warnings since Rails 6.0. Check the documentation for valid ways to do that.

Additionally, a lot of private APIs and orphan code fall in cascade. Check for example #43048 and #43058, and there’s more to come.

Add new form builder “weekday_options_for_select”

This PR adds a helper for weekday select which even includes i18n!

Support for byte ranges in Active Storage

This PR allows serving uploads in chunks in order to stream buffered files as is required e.g. audio podcasts from S3 to an iphone.

Add database config option to turn off tasks like db:migrate

In a multidb configuration you may have a database that you want to connect to, such as a replica, but don’t want to accidentally run any db tasks on it.

The “database_task: false” config flag ensures you don’t accidentally “rails db:drop” your backup database.

Remove legacy –skip-gemfile option

“Don’t have to keep all the monuments to old skirmishes around forever.”

Remove –skip-puma option

Since puma is the only option available for the web server, it doesn’t make sense to allow removing it as a configuration option.

15 people contributed to Rails since last time. All the changes can be checked here. Until next week!

Rails 6.0.4.1 and 6.1.4.1 have been released

Hi everyone! Rails versions 6.0.4.1 and 6.1.4.1 have been released!

These releases contain important security fixes, so please update when you can! This release just contains one security fix which you can read about here:

Here are the checksums for the gems:

$ shasum -a 256 *-6.0.4.1.gem 
390edd2a66448c4ba8686c11514be45264e995304cd05095d5bc5e55126e68ef  actioncable-6.0.4.1.gem
7ea740274387f1b955a6f23288baac88c3e6eb8543a98d825efec9105b850b61  actionmailbox-6.0.4.1.gem
357e32b4a17ce9e85f068d90f9ca841cab7f8c37d667cd3ddcc5330e01aeb1db  actionmailer-6.0.4.1.gem
6fa124867dabefa977f64f30005ed918a71fe6d745b1bb6f0fbd05bef2767a03  actionpack-6.0.4.1.gem
9466887c902c791b7b716b6d5169d9f02487cb0ac8bea54fe6e37b7d2e19df03  actiontext-6.0.4.1.gem
ffdde2003358f64a14d8687b3d7bc30c0566f1b74cfe82848c9b99609f5800a8  actionview-6.0.4.1.gem
71744dc6d49a89c64124ce660b48528a1783f508384112f532c1ced009998d64  activejob-6.0.4.1.gem
3753fb5dfd6d7152ceaec361fea4aee2da7f43cc0004718c16b282d139aae5c8  activemodel-6.0.4.1.gem
a0e4e861767c5b38252dbfd040b0f786a80d8794e021fb0f32e75065f71a066c  activerecord-6.0.4.1.gem
a5d08d6ce17cadae0977ab9b3629334076343575d0f20438093b3574c82cd0bc  activestorage-6.0.4.1.gem
33093c89f35db3200d3cb161252e95322e6fd8f46419e98ac712a5d01445913f  activesupport-6.0.4.1.gem
62f6b50573e2afc305575f580ed72783512874464726d8e52fe8c10b981d1ee0  rails-6.0.4.1.gem
e4743f2aaa895962f94c1d6777daffff3fb578818a1544d58e5a40a76d27856c  railties-6.0.4.1.gem
$ shasum -a 256 *-6.1.4.1.gem 
5d7cca7aefeee6ea95003f32786196749c9b6c92f8a96937fda066156d2d9846  actioncable-6.1.4.1.gem
06e39f90ad0da00acf860265188c438b74fa96aa69990216652508cda56d5f99  actionmailbox-6.1.4.1.gem
229525238eeba137d9ecdc6c331fac07c76a2305ea66f102642f16a6043d4003  actionmailer-6.1.4.1.gem
2a5e0af9f561e8b7f27b1f4088a3d6d4283ec7eaa283f0db345ecb152dd6fe75  actionpack-6.1.4.1.gem
02953e65adb6805e0279ffaf44f4faceb4e89adc038d0ed7b73b018831f18e54  actiontext-6.1.4.1.gem
7f08294f1f0e39ea9db211bafedbded068223abf54659581ce440c3a0b8bc4f9  actionview-6.1.4.1.gem
169e7cf2d9ecad34db8199c2da577e853c6a65523c9cd9177b3d2b3e4104ece0  activejob-6.1.4.1.gem
032f5bbe1fc88aa2fb4db97807026c01fe1a41571672d01f2d0b454b49553d9a  activemodel-6.1.4.1.gem
4a22709593cf8e164939286bc1635efcd87378244ad17e87becb1f7324dd8fb1  activerecord-6.1.4.1.gem
716fdda141aa3a9c027f59d0effb08cbf5291fad1df82d50e9e4e1edd2ff769e  activestorage-6.1.4.1.gem
44b781877c2189aa15ca5451e2d310dcedfd16c01df1106f68a91b82990cfda5  activesupport-6.1.4.1.gem
7f5dd7a71046aedb6859eb4288b31b738fb8544bd9fb27574085b58cbaa8a9f8  rails-6.1.4.1.gem
7e03a6b27a1ab455e9d9c52b6dfb1cae34065ea04382272e19da63860ca897cf  railties-6.1.4.1.gem

Have a great day! 😬

-Aaron ❤️