From c3f2b545f86748c0e792ef0de3211f9d948b92a6 Mon Sep 17 00:00:00 2001 From: zzak Date: Mon, 27 Mar 2023 12:14:18 +0900 Subject: [PATCH] Introduce markdownlint for guides MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This is a follow up to rails#47186, this time for all markdown content. [markdownlint](https://github.com/markdownlint/markdownlint) is an excellent tool, and I've found it very useful for finding issues in the guides. Many of the rules are common style issues I'm correcting on PRs, so it will be nice to have that automated. We should also be able to use the same config with our editors, so that errors show up in real-time ๐Ÿ™ and will update the contributing docs once this gets merged with how to debug and use mdl appropriately. --- .github/workflows/mdl.yml | 24 ++++++++++++ .mdlrc | 1 + .mdlrc.rb | 23 ++++++++++++ Gemfile | 5 +++ Gemfile.lock | 23 +++++++++++- guides/Rakefile | 8 ++++ guides/source/action_cable_overview.md | 28 +++++++------- guides/source/action_mailer_basics.md | 6 +-- guides/source/active_record_basics.md | 3 +- guides/source/active_record_encryption.md | 3 ++ guides/source/active_record_migrations.md | 8 ++-- .../active_record_multiple_databases.md | 6 +-- guides/source/active_storage_overview.md | 1 + guides/source/api_app.md | 3 +- guides/source/asset_pipeline.md | 37 ++++++++----------- guides/source/association_basics.md | 13 ++++--- guides/source/command_line.md | 1 + guides/source/configuring.md | 2 +- .../source/contributing_to_ruby_on_rails.md | 1 + guides/source/debugging_rails_applications.md | 22 +++++------ guides/source/error_reporting.md | 3 ++ guides/source/form_helpers.md | 1 + guides/source/maintenance_policy.md | 2 +- guides/source/testing.md | 2 +- guides/source/upgrading_ruby_on_rails.md | 33 ++++++++++------- .../working_with_javascript_in_rails.md | 11 ++---- 26 files changed, 178 insertions(+), 92 deletions(-) create mode 100644 .github/workflows/mdl.yml create mode 100644 .mdlrc create mode 100644 .mdlrc.rb diff --git a/.github/workflows/mdl.yml b/.github/workflows/mdl.yml new file mode 100644 index 0000000000..8634b8b17e --- /dev/null +++ b/.github/workflows/mdl.yml @@ -0,0 +1,24 @@ +name: Markdown Lint [Guides] + +on: [pull_request] + +permissions: + contents: read + +jobs: + mdl: + runs-on: ubuntu-latest + env: + BUNDLE_ONLY: mdl + + steps: + - uses: actions/checkout@v3 + + - name: Set up Ruby 3.2 + uses: ruby/setup-ruby@v1 + with: + ruby-version: 3.2 + bundler-cache: true + + - name: Run mdl + run: bundle exec rake -f guides/Rakefile guides:lint diff --git a/.mdlrc b/.mdlrc new file mode 100644 index 0000000000..4e92d0f58c --- /dev/null +++ b/.mdlrc @@ -0,0 +1 @@ +style "#{File.dirname(__FILE__)}/.mdlrc.rb" \ No newline at end of file diff --git a/.mdlrc.rb b/.mdlrc.rb new file mode 100644 index 0000000000..78d01e5ccd --- /dev/null +++ b/.mdlrc.rb @@ -0,0 +1,23 @@ +# frozen_string_literal: true + +all + +exclude_rule "MD003" +exclude_rule "MD004" +exclude_rule "MD005" +exclude_rule "MD006" +exclude_rule "MD007" +exclude_rule "MD012" +exclude_rule "MD014" +exclude_rule "MD024" +exclude_rule "MD026" +exclude_rule "MD033" +exclude_rule "MD034" +exclude_rule "MD036" +exclude_rule "MD040" +exclude_rule "MD041" + +rule "MD013", line_length: 2000, ignore_code_blocks: true +# rule "MD024", allow_different_nesting: true # This did not work as intended, see action_cable_overview.md +rule "MD029", style: :ordered +# rule "MD046", style: :consistent # default (:fenced) diff --git a/Gemfile b/Gemfile index 5d762e177f..050d5580f1 100644 --- a/Gemfile +++ b/Gemfile @@ -49,6 +49,11 @@ group :rubocop do gem "rubocop-md", require: false end +group :mdl do + gem "mdl", require: false + gem "rake", ">= 13", require: false +end + group :doc do gem "sdoc", ">= 2.6.0" gem "rdoc", "~> 6.5" diff --git a/Gemfile.lock b/Gemfile.lock index 90c4af8b62..7673192b54 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -160,6 +160,8 @@ GEM regexp_parser (>= 1.5, < 3.0) xpath (~> 3.2) cgi (0.3.6) + chef-utils (18.1.29) + concurrent-ruby concurrent-ruby (1.1.10) connection_pool (2.3.0) crack (0.4.5) @@ -275,6 +277,10 @@ GEM railties (>= 6.0.0) json (2.6.3) jwt (2.6.0) + kramdown (2.4.0) + rexml + kramdown-parser-gfm (1.1.0) + kramdown (~> 2.0) libxml-ruby (4.0.0) listen (3.8.0) rb-fsevent (~> 0.10, >= 0.10.3) @@ -289,6 +295,12 @@ GEM net-smtp marcel (1.0.2) matrix (0.4.2) + mdl (0.12.0) + kramdown (~> 2.3) + kramdown-parser-gfm (~> 1.1) + mixlib-cli (~> 2.1, >= 2.1.1) + mixlib-config (>= 2.2.1, < 4) + mixlib-shellout memoist (0.16.2) mini_magick (4.12.0) mini_mime (1.1.2) @@ -303,6 +315,11 @@ GEM minitest (>= 5.0) minitest-server (1.0.7) minitest (~> 5.16) + mixlib-cli (2.1.8) + mixlib-config (3.0.27) + tomlrb + mixlib-shellout (3.2.7) + chef-utils mono_logger (1.1.1) msgpack (1.6.0) multi_json (1.15.0) @@ -327,7 +344,7 @@ GEM racc (~> 1.4) os (1.1.4) parallel (1.22.1) - parser (3.2.0.0) + parser (3.2.1.1) ast (~> 2.4.1) path_expander (1.1.1) pg (1.4.5) @@ -407,7 +424,7 @@ GEM rubocop-ast (>= 1.26.0, < 2.0) ruby-progressbar (~> 1.7) unicode-display_width (>= 2.4.0, < 3.0) - rubocop-ast (1.27.0) + rubocop-ast (1.28.0) parser (>= 3.2.1.0) rubocop-md (1.2.0) rubocop (>= 1.0) @@ -489,6 +506,7 @@ GEM thor (1.2.1) tilt (2.0.11) timeout (0.3.2) + tomlrb (2.0.3) trailblazer-option (0.1.2) turbo-rails (1.3.2) actionpack (>= 6.0.0) @@ -558,6 +576,7 @@ DEPENDENCIES json (>= 2.0.0) libxml-ruby listen (~> 3.3) + mdl minitest (>= 5.15.0) minitest-bisect minitest-ci diff --git a/guides/Rakefile b/guides/Rakefile index c7d7a40b3d..59cbe79869 100644 --- a/guides/Rakefile +++ b/guides/Rakefile @@ -24,6 +24,14 @@ namespace :guides do end end + desc "Lint guides, using `mdl`" + task :lint do + require "mdl" + all = Dir.glob("#{__dir__}/source/*.md") + files = all - Dir.glob("#{__dir__}/**/*_release_notes.md") # Ignore release notes + MarkdownLint.run files + end + # Validate guides ------------------------------------------------------------------------- desc 'Validate guides, use ONLY=foo to process just "foo.html"' task :validate do diff --git a/guides/source/action_cable_overview.md b/guides/source/action_cable_overview.md index f5b0a1e52e..95cadeab78 100644 --- a/guides/source/action_cable_overview.md +++ b/guides/source/action_cable_overview.md @@ -651,28 +651,28 @@ consumer.subscriptions.create("AppearanceChannel", { #### Client-Server Interaction 1. **Client** connects to the **Server** via `createConsumer()`. (`consumer.js`). The -**Server** identifies this connection by `current_user`. + **Server** identifies this connection by `current_user`. 2. **Client** subscribes to the appearance channel via -`consumer.subscriptions.create({ channel: "AppearanceChannel" })`. (`appearance_channel.js`) + `consumer.subscriptions.create({ channel: "AppearanceChannel" })`. (`appearance_channel.js`) 3. **Server** recognizes a new subscription has been initiated for the -appearance channel and runs its `subscribed` callback, calling the `appear` -method on `current_user`. (`appearance_channel.rb`) + appearance channel and runs its `subscribed` callback, calling the `appear` + method on `current_user`. (`appearance_channel.rb`) 4. **Client** recognizes that a subscription has been established and calls -`connected` (`appearance_channel.js`), which in turn calls `install` and `appear`. -`appear` calls `AppearanceChannel#appear(data)` on the server, and supplies a -data hash of `{ appearing_on: this.appearingOn }`. This is -possible because the server-side channel instance automatically exposes all -public methods declared on the class (minus the callbacks), so that these can be -reached as remote procedure calls via a subscription's `perform` method. + `connected` (`appearance_channel.js`), which in turn calls `install` and `appear`. + `appear` calls `AppearanceChannel#appear(data)` on the server, and supplies a + data hash of `{ appearing_on: this.appearingOn }`. This is + possible because the server-side channel instance automatically exposes all + public methods declared on the class (minus the callbacks), so that these can be + reached as remote procedure calls via a subscription's `perform` method. 5. **Server** receives the request for the `appear` action on the appearance -channel for the connection identified by `current_user` -(`appearance_channel.rb`). **Server** retrieves the data with the -`:appearing_on` key from the data hash and sets it as the value for the `:on` -key being passed to `current_user.appear`. + channel for the connection identified by `current_user` + (`appearance_channel.rb`). **Server** retrieves the data with the + `:appearing_on` key from the data hash and sets it as the value for the `:on` + key being passed to `current_user.appear`. ### Example 2: Receiving New Web Notifications diff --git a/guides/source/action_mailer_basics.md b/guides/source/action_mailer_basics.md index 3c2bb5b808..e388db74bf 100644 --- a/guides/source/action_mailer_basics.md +++ b/guides/source/action_mailer_basics.md @@ -116,10 +116,10 @@ a full list of all available options, please have a look further down at the Complete List of Action Mailer user-settable attributes section. * The [`default`][] method sets default values for all emails sent from -this mailer. In this case, we use it to set the `:from` header value for all -messages in this class. This can be overridden on a per-email basis. + this mailer. In this case, we use it to set the `:from` header value for all + messages in this class. This can be overridden on a per-email basis. * The [`mail`][] method creates the actual email message. We use it to specify -the values of headers like `:to` and `:subject` per email. + the values of headers like `:to` and `:subject` per email. [`default`]: https://api.rubyonrails.org/classes/ActionMailer/Base.html#method-c-default [`mail`]: https://api.rubyonrails.org/classes/ActionMailer/Base.html#method-i-mail diff --git a/guides/source/active_record_basics.md b/guides/source/active_record_basics.md index 7b2ca6ad44..bec28cc622 100644 --- a/guides/source/active_record_basics.md +++ b/guides/source/active_record_basics.md @@ -88,8 +88,7 @@ singularizing) both regular and irregular words. When using class names composed of two or more words, the model class name should follow the Ruby conventions, using the CamelCase form, while the table name must use the snake_case form. Examples: -* Model Class - Singular with the first letter of each word capitalized (e.g., -`BookClub`). +* Model Class - Singular with the first letter of each word capitalized (e.g., `BookClub`). * Database Table - Plural with underscores separating words (e.g., `book_clubs`). | Model / Class | Table / Schema | diff --git a/guides/source/active_record_encryption.md b/guides/source/active_record_encryption.md index f25ebf4faa..1fa2dbe663 100644 --- a/guides/source/active_record_encryption.md +++ b/guides/source/active_record_encryption.md @@ -265,6 +265,7 @@ When generating the filter parameter, it will use the model name as a prefix. E. ```ruby config.active_record.encryption.add_to_filter_parameters = false ``` + In case you want exclude specific columns from this automatic filtering, add them to `config.active_record.encryption.excluded_from_filter_parameters`. ### Encoding @@ -534,6 +535,7 @@ ActiveRecord::Encryption.without_encryption do ... end ``` + This means that reading encrypted text will return the ciphertext, and saved content will be stored unencrypted. ##### Protect Encrypted Data @@ -545,4 +547,5 @@ ActiveRecord::Encryption.protecting_encrypted_data do ... end ``` + This can be handy if you want to protect encrypted data while still running arbitrary code against it (e.g. in a Rails console). diff --git a/guides/source/active_record_migrations.md b/guides/source/active_record_migrations.md index b1bdf718f5..6b58966e44 100644 --- a/guides/source/active_record_migrations.md +++ b/guides/source/active_record_migrations.md @@ -517,14 +517,14 @@ Column modifiers can be applied when creating or changing a column: * `comment` Adds a comment for the column. * `collation` Specifies the collation for a `string` or `text` column. * `default` Allows to set a default value on the column. Note that if you -are using a dynamic value (such as a date), the default will only be calculated -the first time (i.e. on the date the migration is applied). Use `nil` for `NULL`. + are using a dynamic value (such as a date), the default will only be calculated + the first time (i.e. on the date the migration is applied). Use `nil` for `NULL`. * `limit` Sets the maximum number of characters for a `string` column -and the maximum number of bytes for `text/binary/integer` columns. + and the maximum number of bytes for `text/binary/integer` columns. * `null` Allows or disallows `NULL` values in the column. * `precision` Specifies the precision for `decimal/numeric/datetime/time` columns. * `scale` Specifies the scale for the `decimal` and `numeric` columns, -representing the number of digits after the decimal point. + representing the number of digits after the decimal point. NOTE: For `add_column` or `change_column` there is no option for adding indexes. They need to be added separately using `add_index`. diff --git a/guides/source/active_record_multiple_databases.md b/guides/source/active_record_multiple_databases.md index 5ae8900a12..1503b337fe 100644 --- a/guides/source/active_record_multiple_databases.md +++ b/guides/source/active_record_multiple_databases.md @@ -23,10 +23,8 @@ At this time the following features are supported: * Multiple writer databases and a replica for each * Automatic connection switching for the model you're working with -* Automatic swapping between the writer and replica depending on the HTTP verb -and recent writes -* Rails tasks for creating, dropping, migrating, and interacting with the multiple -databases +* Automatic swapping between the writer and replica depending on the HTTP verb and recent writes +* Rails tasks for creating, dropping, migrating, and interacting with the multiple databases The following features are not (yet) supported: diff --git a/guides/source/active_storage_overview.md b/guides/source/active_storage_overview.md index c9506aa8b4..fd04792d1b 100644 --- a/guides/source/active_storage_overview.md +++ b/guides/source/active_storage_overview.md @@ -183,6 +183,7 @@ amazon: server_side_encryption: "" # 'aws:kms' or 'AES256' cache_control: "private, max-age=<%= 1.day.to_i %>" ``` + TIP: Set sensible client HTTP timeouts and retry limits for your application. In certain failure scenarios, the default AWS client configuration may cause connections to be held for up to several minutes and lead to request queuing. Add the [`aws-sdk-s3`](https://github.com/aws/aws-sdk-ruby) gem to your `Gemfile`: diff --git a/guides/source/api_app.md b/guides/source/api_app.md index 3ad8175b47..c0838a5c21 100644 --- a/guides/source/api_app.md +++ b/guides/source/api_app.md @@ -548,7 +548,8 @@ Some common modules you might want to add: self.cache_store = :mem_cache_store end ``` - Rails does *not* pass this configuration automatically. + + Rails does *not* pass this configuration automatically. The best place to add a module is in your `ApplicationController`, but you can also add modules to individual controllers. diff --git a/guides/source/asset_pipeline.md b/guides/source/asset_pipeline.md index 929fec5c4b..e0c90f6060 100644 --- a/guides/source/asset_pipeline.md +++ b/guides/source/asset_pipeline.md @@ -113,26 +113,17 @@ with a built-in helper. In the source the generated code looked like this: The query string strategy has several disadvantages: -1. **Not all caches will reliably cache content where the filename only differs by -query parameters** +1. **Not all caches will reliably cache content where the filename only differs by query parameters** - [Steve Souders recommends](https://www.stevesouders.com/blog/2008/08/23/revving-filenames-dont-use-querystring/), -"...avoiding a querystring for cacheable resources". He found that in this -case 5-20% of requests will not be cached. Query strings in particular do not -work at all with some CDNs for cache invalidation. + [Steve Souders recommends][], "...avoiding a querystring for cacheable resources". He found that in this case 5-20% of requests will not be cached. Query strings in particular do not work at all with some CDNs for cache invalidation. 2. **The file name can change between nodes in multi-server environments.** - The default query string in Rails 2.x is based on the modification time of -the files. When assets are deployed to a cluster, there is no guarantee that the -timestamps will be the same, resulting in different values being used depending -on which server handles the request. + The default query string in Rails 2.x is based on the modification time of the files. When assets are deployed to a cluster, there is no guarantee that the timestamps will be the same, resulting in different values being used depending on which server handles the request. 3. **Too much cache invalidation** - When static assets are deployed with each new release of code, the mtime -(time of last modification) of _all_ these files changes, forcing all remote -clients to fetch them again, even when the content of those assets has not changed. + When static assets are deployed with each new release of code, the mtime (time of last modification) of _all_ these files changes, forcing all remote clients to fetch them again, even when the content of those assets has not changed. Fingerprinting fixes these problems by avoiding query strings, and by ensuring that filenames are consistent based on their content. @@ -147,7 +138,7 @@ More reading: * [Revving Filenames: don't use querystring](http://www.stevesouders.com/blog/2008/08/23/revving-filenames-dont-use-querystring/) [`config.assets.digest`]: configuring.html#config-assets-digest - +[Steve Souders recommends]: https://www.stevesouders.com/blog/2008/08/23/revving-filenames-dont-use-querystring/ How to Use the Asset Pipeline ----------------------------- @@ -207,15 +198,15 @@ Pipeline assets can be placed inside an application in one of three locations: `app/assets`, `lib/assets` or `vendor/assets`. * `app/assets` is for assets that are owned by the application, such as custom -images, JavaScript files, or stylesheets. + images, JavaScript files, or stylesheets. * `lib/assets` is for your own libraries' code that doesn't really fit into the -scope of the application or those libraries which are shared across applications. + scope of the application or those libraries which are shared across applications. * `vendor/assets` is for assets that are owned by outside entities, such as -code for JavaScript plugins and CSS frameworks. Keep in mind that third party -code with references to other files also processed by the asset Pipeline (images, -stylesheets, etc.), will need to be rewritten to use helpers like `asset_path`. + code for JavaScript plugins and CSS frameworks. Keep in mind that third party + code with references to other files also processed by the asset Pipeline (images, + stylesheets, etc.), will need to be rewritten to use helpers like `asset_path`. #### Search Paths @@ -760,9 +751,9 @@ $ RAILS_ENV=production rails assets:precompile Note the following caveats: -* If precompiled assets are available, they will be served โ€” even if they no - longer match the original (uncompiled) assets, _even on the development - server._ +* If precompiled assets are available, they will be served โ€” even if they no + longer match the original (uncompiled) assets, _even on the development + server._ To ensure that the development server always compiles assets on-the-fly (and thus always reflects the most recent state of the code), the development @@ -777,6 +768,7 @@ Note the following caveats: ```ruby config.assets.prefix = "/dev-assets" ``` + * The asset precompile task in your deployment tool (_e.g.,_ Capistrano) should be disabled. * Any necessary compressors or minifiers must be available on your development @@ -1141,6 +1133,7 @@ and any other environments you define with production behavior (not `application.rb`). TIP: For further details have a look at the docs of your production web server: + - [Apache](https://tn123.org/mod_xsendfile/) - [NGINX](https://www.nginx.com/resources/wiki/start/topics/examples/xsendfile/) diff --git a/guides/source/association_basics.md b/guides/source/association_basics.md index efb0912609..60793fe1d0 100644 --- a/guides/source/association_basics.md +++ b/guides/source/association_basics.md @@ -1131,14 +1131,14 @@ towards the counter. To fix a stale counter cache, use [`reset_counters`][]. If you set the `:dependent` option to: * `:destroy`, when the object is destroyed, `destroy` will be called on its -associated objects. + associated objects. * `:delete`, when the object is destroyed, all its associated objects will be -deleted directly from the database without calling their `destroy` method. + deleted directly from the database without calling their `destroy` method. * `:destroy_async`: when the object is destroyed, an `ActiveRecord::DestroyAssociationAsyncJob` -job is enqueued which will call destroy on its associated objects. Active Job must be set up -for this to work. Do not use this option if the association is backed by foreign key -constraints in your database. The foreign key constraint actions will occur inside the same -transaction that deletes its owner. + job is enqueued which will call destroy on its associated objects. Active Job must be set up + for this to work. Do not use this option if the association is backed by foreign key + constraints in your database. The foreign key constraint actions will occur inside the same + transaction that deletes its owner. WARNING: You should not specify this option on a `belongs_to` association that is connected with a `has_many` association on the other class. Doing so can lead to orphaned records in your database. @@ -2626,6 +2626,7 @@ def check_credit_limit(book) throw(:abort) if limit_reached? end ``` + NOTE: These callbacks are called only when the associated objects are added or removed through the association collection: ```ruby diff --git a/guides/source/command_line.md b/guides/source/command_line.md index 4534e38d27..460ea599bc 100644 --- a/guides/source/command_line.md +++ b/guides/source/command_line.md @@ -486,6 +486,7 @@ $ bin/rails generate model Oops create test/models/oops_test.rb create test/fixtures/oops.yml ``` + ```bash $ bin/rails destroy model Oops invoke active_record diff --git a/guides/source/configuring.md b/guides/source/configuring.md index a1e5a026d4..8ddad6906f 100644 --- a/guides/source/configuring.md +++ b/guides/source/configuring.md @@ -1458,7 +1458,7 @@ whether a foreign key's name should be dumped to db/schema.rb or not. By default, foreign key names starting with `fk_rails_` are not exported to the database schema dump. Defaults to `/^fk_rails_[0-9a-f]{10}$/`. - #### `config.active_record.encryption.hash_digest_class` +#### `config.active_record.encryption.hash_digest_class` Sets the digest algorithm used by Active Record Encryption. diff --git a/guides/source/contributing_to_ruby_on_rails.md b/guides/source/contributing_to_ruby_on_rails.md index e7b3a2dc29..4b2bd349c2 100644 --- a/guides/source/contributing_to_ruby_on_rails.md +++ b/guides/source/contributing_to_ruby_on_rails.md @@ -437,6 +437,7 @@ For MySQL and PostgreSQL, it is sufficient to run: $ cd activerecord $ bundle exec rake db:mysql:build ``` + Or: ```bash diff --git a/guides/source/debugging_rails_applications.md b/guides/source/debugging_rails_applications.md index b39c632f2d..01b3bdf52f 100644 --- a/guides/source/debugging_rails_applications.md +++ b/guides/source/debugging_rails_applications.md @@ -827,9 +827,9 @@ do that with `local_variables`. ### Settings * `config.web_console.allowed_ips`: Authorized list of IPv4 or IPv6 -addresses and networks (defaults: `127.0.0.1/8, ::1`). + addresses and networks (defaults: `127.0.0.1/8, ::1`). * `config.web_console.whiny_requests`: Log a message when a console rendering -is prevented (defaults: `true`). + is prevented (defaults: `true`). Since `web-console` evaluates plain Ruby code remotely on the server, don't try to use it in production. @@ -869,18 +869,18 @@ There are some Rails plugins to help you to find errors and debug your application. Here is a list of useful plugins for debugging: * [Query Trace](https://github.com/ruckus/active-record-query-trace/tree/master) Adds query -origin tracing to your logs. + origin tracing to your logs. * [Exception Notifier](https://github.com/smartinez87/exception_notification/tree/master) -Provides a mailer object and a default set of templates for sending email -notifications when errors occur in a Rails application. + Provides a mailer object and a default set of templates for sending email + notifications when errors occur in a Rails application. * [Better Errors](https://github.com/charliesome/better_errors) Replaces the -standard Rails error page with a new one containing more contextual information, -like source code and variable inspection. + standard Rails error page with a new one containing more contextual information, + like source code and variable inspection. * [RailsPanel](https://github.com/dejan/rails_panel) Chrome extension for Rails -development that will end your tailing of development.log. Have all information -about your Rails app requests in the browser โ€” in the Developer Tools panel. -Provides insight to db/rendering/total times, parameter list, rendered views and -more. + development that will end your tailing of development.log. Have all information + about your Rails app requests in the browser โ€” in the Developer Tools panel. + Provides insight to db/rendering/total times, parameter list, rendered views and + more. * [Pry](https://github.com/pry/pry) An IRB alternative and runtime developer console. References diff --git a/guides/source/error_reporting.md b/guides/source/error_reporting.md index 090dc856e9..5d7134fa53 100644 --- a/guides/source/error_reporting.md +++ b/guides/source/error_reporting.md @@ -73,6 +73,7 @@ NOTE: The Rails error-reporter will always call registered subscribers, regardle There are three ways you can use the error reporter: #### Reporting and Swallowing Errors + [`Rails.error.handle`](https://api.rubyonrails.org/classes/ActiveSupport/ErrorReporter.html#method-i-handle) will report any error raised within the block. It will then **swallow** the error, and the rest of your code outside the block will continue as normal. ```ruby @@ -92,6 +93,7 @@ end ``` #### Reporting and Re-raising Errors + [`Rails.error.record`](https://api.rubyonrails.org/classes/ActiveSupport/ErrorReporter.html#method-i-record) will report errors to all registered subscribers and then re-raise the error, meaning that the rest of your code won't execute. ```ruby @@ -104,6 +106,7 @@ end If no error is raised in the block, `Rails.error.record` will return the result of the block. #### Manually Reporting Errors + You can also manually report errors by calling [`Rails.error.report`](https://api.rubyonrails.org/classes/ActiveSupport/ErrorReporter.html#method-i-report): ```ruby diff --git a/guides/source/form_helpers.md b/guides/source/form_helpers.md index 4165747370..adfa32a0d6 100644 --- a/guides/source/form_helpers.md +++ b/guides/source/form_helpers.md @@ -366,6 +366,7 @@ Rails works around this issue by emulating other methods over POST through a com ``` + [formmethod]: https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formmethod [button-name]: https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-name [button-value]: https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-value diff --git a/guides/source/maintenance_policy.md b/guides/source/maintenance_policy.md index b427a40c3a..3519adc8c1 100644 --- a/guides/source/maintenance_policy.md +++ b/guides/source/maintenance_policy.md @@ -106,4 +106,4 @@ Due to a constraint with npm, we are unable to use the 4th digit for security releases of [NPM packages][] provided by Rails. This means that instead of the equivalent gem version `7.0.1.4`, the NPM package will be versioned `7.0.1-4`. -[NPM packages]: https://www.npmjs.com/org/rails \ No newline at end of file +[NPM packages]: https://www.npmjs.com/org/rails diff --git a/guides/source/testing.md b/guides/source/testing.md index b65b07c730..ed51179cd4 100644 --- a/guides/source/testing.md +++ b/guides/source/testing.md @@ -2174,4 +2174,4 @@ assert_equal Date.new(2004, 10, 24), user.activation_date Please see [`ActiveSupport::Testing::TimeHelpers`][time_helpers_api] API reference for more information about the available time helpers. [travel_to]: https://api.rubyonrails.org/classes/ActiveSupport/Testing/TimeHelpers.html#method-i-travel_to -[time_helpers_api]: https://api.rubyonrails.org/classes/ActiveSupport/Testing/TimeHelpers.html \ No newline at end of file +[time_helpers_api]: https://api.rubyonrails.org/classes/ActiveSupport/Testing/TimeHelpers.html diff --git a/guides/source/upgrading_ruby_on_rails.md b/guides/source/upgrading_ruby_on_rails.md index b38288a471..7c3a24472f 100644 --- a/guides/source/upgrading_ruby_on_rails.md +++ b/guides/source/upgrading_ruby_on_rails.md @@ -543,6 +543,7 @@ You will then need to change existing image transformation code to the `image_processing` macros, and replace ImageMagick's options with libvips' options. #### Replace resize with resize_to_limit + ```diff - variant(resize: "100x") + variant(resize_to_limit: [100, nil]) @@ -551,6 +552,7 @@ You will then need to change existing image transformation code to the If you don't do this, when you switch to vips you will see this error: `no implicit conversion to float from string`. #### Use an array when cropping + ```diff - variant(crop: "1920x1080+0+0") + variant(crop: [0, 0, 1920, 1080]) @@ -568,6 +570,7 @@ Vips is more strict than ImageMagick when it comes to cropping: If you don't do this when migrating to vips, you will see the following error: `extract_area: bad extract area` #### Adjust the background color used for `resize_and_pad` + Vips uses black as the default background color `resize_and_pad`, instead of white like ImageMagick. Fix that by using the `background` option: ```diff @@ -576,6 +579,7 @@ Vips uses black as the default background color `resize_and_pad`, instead of whi ``` #### Remove any EXIF based rotation + Vips will auto rotate images using the EXIF value when processing variants. If you were storing rotation values from user uploaded photos to apply rotation with ImageMagick, you must stop doing that: ```diff @@ -584,6 +588,7 @@ Vips will auto rotate images using the EXIF value when processing variants. If y ``` #### Replace monochrome with colourspace + Vips uses a different option to make monochrome images: ```diff @@ -592,6 +597,7 @@ Vips uses a different option to make monochrome images: ``` #### Switch to libvips options for compressing images + JPEG ```diff @@ -621,6 +627,7 @@ GIF ``` #### Deploy to production + Active Storage encodes into the url for the image the list of transformations that must be performed. If your app is caching these urls, your images will break after you deploy the new code to production. Because of this you must manually invalidate your affected cache keys. @@ -1895,7 +1902,7 @@ The migration procedure is as follows: 2. run `bundle install`. 3. run `bin/rake db:schema:dump`. 4. make sure that `db/schema.rb` contains every foreign key definition with -the necessary options. + the necessary options. Upgrading from Rails 4.0 to Rails 4.1 ------------------------------------- @@ -2441,12 +2448,12 @@ Rails 4.0 no longer supports loading plugins from `vendor/plugins`. You must rep * Rails 4.0 has changed `serialized_attributes` and `attr_readonly` to class methods only. You shouldn't use instance methods since it's now deprecated. You should change them to use class methods, e.g. `self.serialized_attributes` to `self.class.serialized_attributes`. * When using the default coder, assigning `nil` to a serialized attribute will save it -to the database as `NULL` instead of passing the `nil` value through YAML (`"--- \n...\n"`). + to the database as `NULL` instead of passing the `nil` value through YAML (`"--- \n...\n"`). * Rails 4.0 has removed `attr_accessible` and `attr_protected` feature in favor of Strong Parameters. You can use the [Protected Attributes gem](https://github.com/rails/protected_attributes) for a smooth upgrade path. * If you are not using Protected Attributes, you can remove any options related to -this gem such as `whitelist_attributes` or `mass_assignment_sanitizer` options. + this gem such as `whitelist_attributes` or `mass_assignment_sanitizer` options. * Rails 4.0 requires that scopes use a callable object such as a Proc or lambda: @@ -2512,7 +2519,7 @@ Rails 4.0 extracted Active Resource to its own gem. If you still need the featur ### Action Pack -* Rails 4.0 introduces `ActiveSupport::KeyGenerator` and uses this as a base from which to generate and verify signed cookies (among other things). Existing signed cookies generated with Rails 3.x will be transparently upgraded if you leave your existing `secret_token` in place and add the new `secret_key_base`. +* Rails 4.0 introduces `ActiveSupport::KeyGenerator` and uses this as a base from which to generate and verify signed cookies (among other things). Existing signed cookies generated with Rails 3.x will be transparently upgraded if you leave your existing `secret_token` in place and add the new `secret_key_base`. ```ruby # config/initializers/secret_token.rb @@ -2524,7 +2531,7 @@ Rails 4.0 extracted Active Resource to its own gem. If you still need the featur If you are relying on the ability for external applications or JavaScript to be able to read your Rails app's signed session cookies (or signed cookies in general) you should not set `secret_key_base` until you have decoupled these concerns. -* Rails 4.0 encrypts the contents of cookie-based sessions if `secret_key_base` has been set. Rails 3.x signed, but did not encrypt, the contents of cookie-based session. Signed cookies are "secure" in that they are verified to have been generated by your app and are tamper-proof. However, the contents can be viewed by end users, and encrypting the contents eliminates this caveat/concern without a significant performance penalty. +* Rails 4.0 encrypts the contents of cookie-based sessions if `secret_key_base` has been set. Rails 3.x signed, but did not encrypt, the contents of cookie-based session. Signed cookies are "secure" in that they are verified to have been generated by your app and are tamper-proof. However, the contents can be viewed by end users, and encrypting the contents eliminates this caveat/concern without a significant performance penalty. Please read [Pull Request #9978](https://github.com/rails/rails/pull/9978) for details on the move to encrypted session cookies. @@ -2543,13 +2550,13 @@ Rails 4.0 extracted Active Resource to its own gem. If you still need the featur * Rails 4.0 deprecates the `dom_id` and `dom_class` methods in controllers (they are fine in views). You will need to include the `ActionView::RecordIdentifier` module in controllers requiring this feature. * Rails 4.0 deprecates the `:confirm` option for the `link_to` helper. You should -instead rely on a data attribute (e.g. `data: { confirm: 'Are you sure?' }`). -This deprecation also concerns the helpers based on this one (such as `link_to_if` -or `link_to_unless`). + instead rely on a data attribute (e.g. `data: { confirm: 'Are you sure?' }`). + This deprecation also concerns the helpers based on this one (such as `link_to_if` + or `link_to_unless`). * Rails 4.0 changed how `assert_generates`, `assert_recognizes`, and `assert_routing` work. Now all these assertions raise `Assertion` instead of `ActionController::RoutingError`. -* Rails 4.0 raises an `ArgumentError` if clashing named routes are defined. This can be triggered by explicitly defined named routes or by the `resources` method. Here are two examples that clash with routes named `example_path`: +* Rails 4.0 raises an `ArgumentError` if clashing named routes are defined. This can be triggered by explicitly defined named routes or by the `resources` method. Here are two examples that clash with routes named `example_path`: ```ruby get 'one' => 'test#example', as: :example @@ -2566,7 +2573,7 @@ or `link_to_unless`). the `resources` method to restrict the routes created as detailed in the [Routing Guide](routing.html#restricting-the-routes-created). -* Rails 4.0 also changed the way unicode character routes are drawn. Now you can draw unicode character routes directly. If you already draw such routes, you must change them, for example: +* Rails 4.0 also changed the way unicode character routes are drawn. Now you can draw unicode character routes directly. If you already draw such routes, you must change them, for example: ```ruby get Rack::Utils.escape('ใ“ใ‚“ใซใกใฏ'), controller: 'welcome', action: 'index' @@ -2578,7 +2585,7 @@ or `link_to_unless`). get 'ใ“ใ‚“ใซใกใฏ', controller: 'welcome', action: 'index' ``` -* Rails 4.0 requires that routes using `match` must specify the request method. For example: +* Rails 4.0 requires that routes using `match` must specify the request method. For example: ```ruby # Rails 3.x @@ -2591,7 +2598,7 @@ or `link_to_unless`). get '/' => 'root#index' ``` -* Rails 4.0 has removed `ActionDispatch::BestStandardsSupport` middleware, `` already triggers standards mode per https://msdn.microsoft.com/en-us/library/jj676915(v=vs.85).aspx and ChromeFrame header has been moved to `config.action_dispatch.default_headers`. +* Rails 4.0 has removed `ActionDispatch::BestStandardsSupport` middleware, `` already triggers standards mode per https://msdn.microsoft.com/en-us/library/jj676915(v=vs.85).aspx and ChromeFrame header has been moved to `config.action_dispatch.default_headers`. Remember you must also remove any references to the middleware from your application code, for example: @@ -2602,7 +2609,7 @@ or `link_to_unless`). Also check your environment settings for `config.action_dispatch.best_standards_support` and remove it if present. -* Rails 4.0 allows configuration of HTTP headers by setting `config.action_dispatch.default_headers`. The defaults are as follows: +* Rails 4.0 allows configuration of HTTP headers by setting `config.action_dispatch.default_headers`. The defaults are as follows: ```ruby config.action_dispatch.default_headers = { diff --git a/guides/source/working_with_javascript_in_rails.md b/guides/source/working_with_javascript_in_rails.md index a5a6affcdd..52008e163d 100644 --- a/guides/source/working_with_javascript_in_rails.md +++ b/guides/source/working_with_javascript_in_rails.md @@ -11,7 +11,7 @@ After reading this guide, you will know: * How to use Rails without the need for a Node.js, Yarn, or a JavaScript bundler. * How to create a new Rails application using import maps, esbuild, rollup, or webpack to bundle -your JavaScript. + your JavaScript. * What Turbo is, and how to use it. * How to use the Turbo HTML helpers provided by Rails. @@ -130,13 +130,10 @@ that you should choose a traditional bundler include: * If your code requires a transpilation step, such as JSX or TypeScript. * If you need to use JavaScript libraries that include CSS or otherwise rely on -[Webpack loaders](https://webpack.js.org/loaders/). + [Webpack loaders](https://webpack.js.org/loaders/). * If you are absolutely sure that you need -[tree-shaking](https://webpack.js.org/guides/tree-shaking/). -* If you will install Bootstrap, Bulma, PostCSS, or Dart CSS through the -[cssbundling-rails gem](https://github.com/rails/cssbundling-rails). All options provided by this -gem except Tailwind and Sass will automatically install `esbuild` for you if you do not specify a different -option in `rails new`. + [tree-shaking](https://webpack.js.org/guides/tree-shaking/). +* If you will install Bootstrap, Bulma, PostCSS, or Dart CSS through the [cssbundling-rails gem](https://github.com/rails/cssbundling-rails). All options provided by this gem except Tailwind and Sass will automatically install `esbuild` for you if you do not specify a different option in `rails new`. Turbo -----