Rails Strict Locals, undefined local_assigns
, and reserved keywords
local_assigns
, and reserved keywordsUpdate: This has been mostly fixed upstream in Rails (Rails 8.0, I think) and documented in the Rails Guides.
Huge thank you to Vojta Drbohlav in the Rails Performance Slack for helping me figure this out! 🙇
Things I learned today about a new-to-me Ruby on Rails feature:
- Rail 7.1 added a feature called “Strict Locals” that uses a magic comment in ERB templates to declare required and optional local variables. It looks like this:
<%# locals: (shirts:, class: nil) %>
which in this example means when rendering the partial, it must be provided ashirts
parameter and optionalclass
parameter. Having ERB templates act more like callable functions with explicit signatures is a nice feature. - When using Rails Strict Locals, the
local_assigns
variable is not defined. You can’t uselocal_assigns
. You’ll see an error that looks likeActionView::Template::Error (undefined local variable or method 'local_assigns' for an instance of #<Class:0x0000000130536cc8>)
. This has been fixed 🎉 thoughlocal_assigns
doesn’t expose default values. - This is a problem if your template has locals that are also Ruby reserved keywords like
class
orif
, which can be accessed withlocal_assigns[:class]
unless you start using Strict Locals. To access local variables named with reserved keywords in your ERB template when using Strict Locals, you can usebinding.local_variable_get(:the_variable_name)
, e.g.,binding.local_variable_get(:class)
orbinding.local_variable_get(:if)
. This is still necessary if you want to access reserved keywords with defaults because the defaults don’t show up inlocal_assigns
.