This commit updates the comments in ActionView::Helpers::FormHelper, replacing instances of `form_for` with `form_with` as the recommended approach. The Rails guide has already documented the usage of `form_with` on the form_helpers page.
Ref: https://guides.rubyonrails.org/form_helpers.html
Co-authored-by: Hartley McGuire <skipkayhil@gmail.com>
This mirrors the documentation on `preload_link_tag` for the following:
- `javascript_include_tag`
- `stylesheet_link_tag`
These methods have a similar API with a different default behavior. The
methods for these methods default to including a `nopush` with the
corresponding link header.
After reviewing the Action View Overview guide, a discussion started
around the builder gem that was detailed in the guide. We decided to
move it to the rails/ umbrella so we can help maintain it as needed,
since the framework uses/documents it, keeping it similar to jbuilder.
https://github.com/rails/rails/pull/51435#discussion_r1556390070
Follow-up to [#49819][]
Since [#49819][] resolves an issue with
`ActionDispatch::IntegrationTest#with_routing` helper support, Action
View's `test/abstract_unit.rb` file can rely on routing being reset
within the block argument.
This means that the `RoutedRackApp` class and `.build_app` method is can
be made unnecessary.
[#49819]: https://github.com/rails/rails/pull/49819
The code sample for the Action View `cache` helper method mixed Ruby
syntax with prose. This commit introduces `#` comment characters to
separate the English from the Ruby.
Ref: https://github.com/rails/rails/pull/8222
`mathn` used to be in the standard library, hence this was a
relatively common issue. But it has been extracted and deprecated
a long time ago, so It's no longer a big concern.
Making `Integer#/` private now emits a warning on Ruby 3.4:
```
/rails/actionview/test/template/date_helper_test.rb:148: warning: Redefining 'Integer#/' disables interpreter and JIT optimizations
```
Ref: https://bugs.ruby-lang.org/issues/15554
Ruby 3.4 now warns when passing a block to a method that
never expects one.
In the case of rendered template, a block is always passed for
some engines that do expect one, but some never expect it.
We can silence that warning by declaring an anonymous block.
Documentation previously uses post which is confusing as the
methods/verb is also post.
Before
<form action="/posts" method="post">
After
<form action="/articles" method="post">
Method
Worked through a new Rails app with scaffold of article
and checking the output of the HTML. Other HTML changes
make it more authentic:
/> => at the end of the input
`ostruct` was being implictly required by the `json` gem. But once it
was upgraded, these tests failed to initialize `OpenStruct`.
While we're trying to remove `ostruct` usage in #51510, CI is currently
failing so I'm pushing these in the mean time.
Currently initialization of every Rails::Engine leads to the creation
of a new View watcher when the engine prepends its paths.
This contributes to the time it takes to perform the first cold request
on a lazy loaded application.
This change delays the initialization of the View watcher until the first
`updated?` check is performed.
Co-Authored-By: Gannon McGibbon <gannon.mcgibbon@gmail.com>
Replaced by `#lease_connection` to better reflect what it does.
`ActiveRecord::Base#connection` is deprecated in the same way
but without a removal timeline nor a deprecation warning.
Inside the Active Record test suite, we do remove `Base.connection`
to ensure it's not used internally.
Some callsites have been converted to use `with_connection`,
some other have been more simply migrated to `lease_connection`
and will serve as a list of callsites to convert for
https://github.com/rails/rails/pull/50793
Follow-up to [49856][]
Follow-up to [49194][]
The introduction of memoization as an optimization posed a backwards
incompatible change to View tests that call `render` multiple times.
This commit changes the `@rendered` instance variable from a `String` to
an instance of the `RenderedViewContent` specialized `String` subclass.
The end result is that there is no memoization to reset, and the
memoization optimization side-effect is preserved after rendering for
test cases where `rendered` (or parser methods like `rendered.html`)
might be invoked more than once.
[49856]: https://github.com/rails/rails/pull/49856#issuecomment-1945039015
[49194]: https://github.com/rails/rails/pull/49194/files#diff-ce84a807f3491121a5230d37bd40454bb1407fcca71179e1a2fa76d4c0ddfa2aR293
Fix: https://github.com/rails/rails/issues/50930
While Action View is predominantly meant to render text,
in sime case it's used to render more complex object.
So we shouldn't assume `#_run` returns a buffer.
Minitest::Test does not support all of the same options as
ActiveSupport::TestCase, such as running bin/test <filename>:<lineno>
and -n /regex/. Trying to use these options on this file would just run
all of the Minitest::Tests no matter what options were passed.
This commit fixes the ability to use those options by using
ActiveSupport::TestCase (like every other test in the repo).
Before:
```
$ bin/test test/template/dependency_tracker_test.rb:217
Running 59 tests in parallel using 8 processes
Run options: --seed 42725
.........................................................
Finished in 0.322759s, 176.6024 runs/s, 176.6024 assertions/s.
57 runs, 57 assertions, 0 failures, 0 errors, 0 skips
```
After:
```
$ bin/test test/template/dependency_tracker_test.rb:217
Running 59 tests in parallel using 8 processes
Run options: --seed 15213
...
Finished in 0.359162s, 8.3528 runs/s, 8.3528 assertions/s.
3 runs, 3 assertions, 0 failures, 0 errors, 0 skips
```
Motivation / Background
---
Strict Locals support was introduced in [#45727][] and announced as part
of the [7.1 Release][]. There are several mentions across the Guides,
but support is rarely mentioned in the API documentation.
Detail
----
Mention the template short identifier (the pathname, in most cases) as
part of the `ArgumentError` message.
This commit adds two test cases to ensure support for splatting
additional arguments, and for forbidding block and positional arguments.
It also makes mention of strict locals in more places, and links to the
guides.
[#45727]: https://github.com/rails/rails/pull/45727
[7.1 Release]: https://edgeguides.rubyonrails.org/7_1_release_notes.html#allow-templates-to-set-strict-locals
Previously, only the PrismRenderParser or RipperRenderParser would be
tested depending on if the Prism gem is available. This meant that
PrismRenderParser was being tested on Ruby 3.3 and RipperRenderParser
was tested on Ruby < 3.3. Additionally, if someone were to add prism to
the rails/rails Gemfile because they wrote a tool that uses it then the
RipperRenderParser would end up completely untested.
This commit is a small refactor to enable testing both RenderParsers in
all Ruby versions so that the prism gem can be added to the Gemfile.
The Rails documentation uses the `:include:` directive to inline the
README of the framework into the main documentation page. As the
README's aren't in the root directory from where SDoc is run we need to
add the framework path to the include:
# :include: activesupport/README.md
This results in a warning when installing the gems as generating the rdoc for the gem is run from the gem/framework root:
Couldn't find file to include 'activesupport/README.rdoc' from lib/active_support.rb
The `:include:` RDoc directive supports includes relative to the current
file as well:
# :include: ../README.md
This makes sure it works for the Rails API docs and the separate gems.
Co-authored-by: Jonathan Hefner <jonathan@hefner.pro>
Fixes#50774
When the server boots up, 2 threads hit the same `UnboundTemplate`
instance before it has set up `@templates`. Both threads get past the
`unless template = @templates[locals]` check because
`@templates[locals]` isn't set yet. However, with `@write_lock`, one
thread waits while the other one proceeds, setting `@templates` to a
frozen hash. The second thread then gets the write lock and tries to
modify `@templates` but it has been frozen.
Currently there's about a 35% difference between tags generated using
the `TagBuilder` and tags generated by passing a positional argument to
`#tag`.
This commit optimizes `TagBuilder` to reduce that difference down to 13%.
The first change is to perform less hash allocations by not splatting
the options twice in the `TagBuilder` (one at the `tag.a` invocation,
and one at `tag_string`). The extra splat for `tag_string` was moved
into `method_missing` since that is the only other caller of this
private method.
The other change is to only escape the content in `tag_string` if it a
non-empty.
Additionally, a test was tweaked to ensure that passing `options` to a
`self_closing_element` is tested as it was previously not.
Benchmark:
```
require "action_view"
require "benchmark/ips"
class Foo
include ActionView::Helpers
end
helpers = Foo.new
Benchmark.ips do |x|
x.report("tag") { helpers.tag("a", href: "foo") }
x.report("tag_builder") { helpers.tag.a(href: "foo") }
x.compare!
end
```
Before:
```
ruby 3.2.2 (2023-03-30 revision e51014f9c0) [arm64-darwin22]
Warming up --------------------------------------
tag 67.180k i/100ms
tag_builder 50.267k i/100ms
Calculating -------------------------------------
tag 673.064k (± 0.4%) i/s - 3.426M in 5.090520s
tag_builder 504.971k (± 0.4%) i/s - 2.564M in 5.076842s
Comparison:
tag: 673063.7 i/s
tag_builder: 504971.4 i/s - 1.33x slower
```
After:
```
ruby 3.2.2 (2023-03-30 revision e51014f9c0) [arm64-darwin22]
Warming up --------------------------------------
tag 67.374k i/100ms
tag_builder 59.702k i/100ms
Calculating -------------------------------------
tag 670.837k (± 0.4%) i/s - 3.369M in 5.021714s
tag_builder 592.727k (± 1.3%) i/s - 2.985M in 5.037088s
Comparison:
tag: 670836.6 i/s
tag_builder: 592726.7 i/s - 1.13x slower
```
Co-authored-by: Sean Doyle <seanpdoyle@users.noreply.github.com>
Previously, the `render_template.action_view` and
`render_layout.action_view` events would always be handled as if they
had subscribers even if the log level of its subscribers result in
nothing being logged. For regular `LogSubscriber`s,
`subscribe_log_level` could be used to optimize these cases but the
Start subscriber is not a subclass of `LogSubscriber`.
This commit implements a `#subscribed?` method for the Start subscriber
so that it can also benefit from the `subscribe_log_level` optimization.
Follow-up to #50699.
This prevents a `NoMethodError` from being masked when the missing
method is itself named `render_in`.
Co-authored-by: Hartley McGuire <skipkayhil@gmail.com>
Follow-up to #50665.
Unconditionally converting `NoMethodError` to `ArgumentError` can mask a
legitimate `NoMethodError` from within the `render_in` method. This
commit adds a check to prevent that.
When calling `render` with a `:renderable` argument, ensure that the
object responds to `#render_in`. If it doesn't, raise an
`ArgumentError`.
This commit also adjusts the `ArgumentError` that when a `:partial`
argument isn't Active Model compatible. Prior to this commit, the
message used `:` as a prefix to `to_partial_path`. This commit replaces
that with a `#` prefix to denote that it's expected to be an instance
method on the object.
RDoc treats consecutive indented lines as a single code block. For code
examples that span multiple files / languages, this confuses the syntax
highlighter and makes the examples harder to read. Unfortunately, RDoc
doesn't provide syntax to prevent this, and it ignores multiple
consecutive blank lines. However, by inserting an empty tag such as
`<code></code>`, we can force RDoc to recognize separate code blocks.