diff options
Diffstat (limited to 'guides/source')
25 files changed, 524 insertions, 350 deletions
diff --git a/guides/source/4_0_release_notes.md b/guides/source/4_0_release_notes.md index 37afb25181..2793d9025f 100644 --- a/guides/source/4_0_release_notes.md +++ b/guides/source/4_0_release_notes.md @@ -113,7 +113,7 @@ Please refer to the [Changelog](https://github.com/rails/rails/blob/master/activ * Add `ActiveModel::ForbiddenAttributesProtection`, a simple module to protect attributes from mass assignment when non-permitted attributes are passed. -* Added `ActiveModel::Model`, a mixin to make Ruby objects work with AP out of box. +* Added `ActiveModel::Model`, a mixin to make Ruby objects work with ActionPack out of box. ### Deprecations diff --git a/guides/source/action_controller_overview.md b/guides/source/action_controller_overview.md index 5e99063da8..db91425c76 100644 --- a/guides/source/action_controller_overview.md +++ b/guides/source/action_controller_overview.md @@ -27,6 +27,16 @@ A controller can thus be thought of as a middle man between models and views. It NOTE: For more details on the routing process, see [Rails Routing from the Outside In](routing.html). +Controller Naming Convention +---------------------------- + +The naming convention of controllers in Rails favors pluralization of the last word in the controller's name, although it is not strictly required (e.g. `ApplicationController`). For example, `ClientsController` is preferable to `ClientController`, `SiteAdminsController` is preferable to `SiteAdminController` or `SitesAdminsController`, and so on. + +Following this convention will allow you to use the default route generators (e.g. `resources`, etc) without needing to qualify each `:path` or `:controller`, and keeps URL and path helpers' usage consistent throughout your application. See [Layouts & Rendering Guide](layouts_and_rendering.html) for more details. + +NOTE: The controller naming convention differs from the naming convention of models, which expected to be named in singular form. + + Methods and Actions ------------------- @@ -561,7 +571,7 @@ Note that while for session values you set the key to `nil`, to delete a cookie Rendering xml and json data --------------------------- -ActionController makes it extremely easy to render `xml` or `json` data. If you generate a controller using scaffolding then it would look something like this: +ActionController makes it extremely easy to render `xml` or `json` data. If you've generated a controller using scaffolding, it would look something like this: ```ruby class UsersController < ApplicationController @@ -576,7 +586,7 @@ class UsersController < ApplicationController end ``` -Notice that in the above case code is `render xml: @users` and not `render xml: @users.to_xml`. That is because if the input is not string then rails automatically invokes `to_xml` . +You may notice in the above code that we're using `render xml: @users`, not `render xml: @users.to_xml`. If the object is not a String, then Rails will automatically invoke `to_xml` for us. Filters ------- @@ -599,15 +609,6 @@ class ApplicationController < ActionController::Base redirect_to new_login_url # halts request cycle end end - - # The logged_in? method simply returns true if the user is logged - # in and false otherwise. It does this by "booleanizing" the - # current_user method we created previously using a double ! operator. - # Note that this is not common in Ruby and is discouraged unless you - # really mean to convert something into true or false. - def logged_in? - !!current_user - end end ``` @@ -788,7 +789,7 @@ Rails comes with two built-in HTTP authentication mechanisms: HTTP basic authentication is an authentication scheme that is supported by the majority of browsers and other HTTP clients. As an example, consider an administration section which will only be available by entering a username and a password into the browser's HTTP basic dialog window. Using the built-in authentication is quite easy and only requires you to use one method, `http_basic_authenticate_with`. ```ruby -class AdminController < ApplicationController +class AdminsController < ApplicationController http_basic_authenticate_with name: "humbaba", password: "5baa61e4" end ``` @@ -800,7 +801,7 @@ With this in place, you can create namespaced controllers that inherit from `Adm HTTP digest authentication is superior to the basic authentication as it does not require the client to send an unencrypted password over the network (though HTTP basic authentication is safe over HTTPS). Using digest authentication with Rails is quite easy and only requires using one method, `authenticate_or_request_with_http_digest`. ```ruby -class AdminController < ApplicationController +class AdminsController < ApplicationController USERS = { "lifo" => "world" } before_action :authenticate diff --git a/guides/source/action_mailer_basics.md b/guides/source/action_mailer_basics.md index a0d962f9c4..ec7b8d4e17 100644 --- a/guides/source/action_mailer_basics.md +++ b/guides/source/action_mailer_basics.md @@ -1,7 +1,9 @@ Action Mailer Basics ==================== -This guide should provide you with all you need to get started in sending and receiving emails from and to your application, and many internals of Action Mailer. It also covers how to test your mailers. +This guide should provide you with all you need to get started in sending and +receiving emails from and to your application, and many internals of Action +Mailer. It also covers how to test your mailers. After reading this guide, you will know: @@ -9,17 +11,19 @@ After reading this guide, you will know: * How to generate and edit an Action Mailer class and mailer view. * How to configure Action Mailer for your environment. * How to test your Action Mailer classes. + -------------------------------------------------------------------------------- Introduction ------------ -Action Mailer allows you to send emails from your application using a mailer model and views. So, in Rails, emails are used by creating mailers that inherit from `ActionMailer::Base` and live in `app/mailers`. Those mailers have associated views that appear alongside controller views in `app/views`. +Action Mailer allows you to send emails from your application using mailer classes and views. Mailers work very similarly to controllers. They inherit from `ActionMailer::Base` and live in `app/mailers`, and they have associated views that appear in `app/views`. Sending Emails -------------- -This section will provide a step-by-step guide to creating a mailer and its views. +This section will provide a step-by-step guide to creating a mailer and its +views. ### Walkthrough to Generating a Mailer @@ -34,10 +38,25 @@ invoke test_unit create test/mailers/user_mailer_test.rb ``` -So we got the mailer, the views, and the tests. +As you can see, you can generate mailers just like you use other generators with +Rails. Mailers are conceptually similar to controllers, and so we get a mailer, +a directory for views, and a test. + +If you didn't want to use a generator, you could create your own file inside of +app/mailers, just make sure that it inherits from `ActionMailer::Base`: + +```ruby +class MyMailer < ActionMailer::Base +end +``` #### Edit the Mailer +Mailers are very similar to Rails controllers. They also have methods called +"actions" and use views to structure the content. Where a controller generates +content like HTML to send back to the client, a Mailer creates a message to be +delivered via email. + `app/mailers/user_mailer.rb` contains an empty mailer: ```ruby @@ -46,7 +65,8 @@ class UserMailer < ActionMailer::Base end ``` -Let's add a method called `welcome_email`, that will send an email to the user's registered email address: +Let's add a method called `welcome_email`, that will send an email to the user's +registered email address: ```ruby class UserMailer < ActionMailer::Base @@ -55,21 +75,25 @@ class UserMailer < ActionMailer::Base def welcome_email(user) @user = user @url = 'http://example.com/login' - mail(to: user.email, subject: 'Welcome to My Awesome Site') + mail(to: @user.email, subject: 'Welcome to My Awesome Site') end end ``` -Here is a quick explanation of the items presented in the preceding method. For a full list of all available options, please have a look further down at the Complete List of Action Mailer user-settable attributes section. +Here is a quick explanation of the items presented in the preceding method. For +a full list of all available options, please have a look further down at the +Complete List of Action Mailer user-settable attributes section. -* `default Hash` - This is a hash of default values for any email you send, in this case we are setting the `:from` header to a value for all messages in this class, this can be overridden on a per email basis +* `default Hash` - This is a hash of default values for any email you send from this mailer. In this case we are setting the `:from` header to a value for all messages in this class. This can be overridden on a per-email basis. * `mail` - The actual email message, we are passing the `:to` and `:subject` headers in. -Just like controllers, any instance variables we define in the method become available for use in the views. +Just like controllers, any instance variables we define in the method become +available for use in the views. #### Create a Mailer View -Create a file called `welcome_email.html.erb` in `app/views/user_mailer/`. This will be the template used for the email, formatted in HTML: +Create a file called `welcome_email.html.erb` in `app/views/user_mailer/`. This +will be the template used for the email, formatted in HTML: ```html+erb <!DOCTYPE html> @@ -91,7 +115,9 @@ Create a file called `welcome_email.html.erb` in `app/views/user_mailer/`. This </html> ``` -It is also a good idea to make a text part for this email. To do this, create a file called `welcome_email.text.erb` in `app/views/user_mailer/`: +Let's also make a text part for this email. Not all clients prefer HTML emails, +and so sending both is best practice. To do this, create a file called +`welcome_email.text.erb` in `app/views/user_mailer/`: ```erb Welcome to example.com, <%= @user.name %> @@ -105,22 +131,29 @@ To login to the site, just follow this link: <%= @url %>. Thanks for joining and have a great day! ``` -When you call the `mail` method now, Action Mailer will detect the two templates (text and HTML) and automatically generate a `multipart/alternative` email. +When you call the `mail` method now, Action Mailer will detect the two templates +(text and HTML) and automatically generate a `multipart/alternative` email. -#### Wire It Up So That the System Sends the Email When a User Signs Up +#### Calling the Mailer -There are several ways to do this, some people create Rails Observers to fire off emails, others do it inside of the User Model. However, mailers are really just another way to render a view. Instead of rendering a view and sending out the HTTP protocol, they are just sending it out through the Email protocols instead. Due to this, it makes sense to just have your controller tell the mailer to send an email when a user is successfully created. +Mailers are really just another way to render a view. Instead of rendering a +view and sending out the HTTP protocol, they are just sending it out through the +Email protocols instead. Due to this, it makes sense to just have your +controller tell the Mailer to send an email when a user is successfully created. Setting this up is painfully simple. -First off, we need to create a simple `User` scaffold: +First, let's create a simple `User` scaffold: ```bash $ rails generate scaffold user name email login $ rake db:migrate ``` -Now that we have a user model to play with, we will just edit the `app/controllers/users_controller.rb` make it instruct the UserMailer to deliver an email to the newly created user by editing the create action and inserting a call to `UserMailer.welcome_email` right after the user is successfully saved: +Now that we have a user model to play with, we will just edit the +`app/controllers/users_controller.rb` make it instruct the UserMailer to deliver +an email to the newly created user by editing the create action and inserting a +call to `UserMailer.welcome_email` right after the user is successfully saved: ```ruby class UsersController < ApplicationController @@ -145,63 +178,50 @@ class UsersController < ApplicationController end ``` -This provides a much simpler implementation that does not require the registering of observers and the like. - -The method `welcome_email` returns a `Mail::Message` object which can then just be told `deliver` to send itself out. +The method `welcome_email` returns a `Mail::Message` object which can then just +be told `deliver` to send itself out. ### Auto encoding header values -Action Mailer now handles the auto encoding of multibyte characters inside of headers and bodies. - -If you are using UTF-8 as your character set, you do not have to do anything special, just go ahead and send in UTF-8 data to the address fields, subject, keywords, filenames or body of the email and Action Mailer will auto encode it into quoted printable for you in the case of a header field or Base64 encode any body parts that are non US-ASCII. +Action Mailer handles the auto encoding of multibyte characters inside of +headers and bodies. -For more complex examples such as defining alternate character sets or self-encoding text first, please refer to the Mail library. +For more complex examples such as defining alternate character sets or +self-encoding text first, please refer to the +[Mail](https://github.com/mikel/mail) library. ### Complete List of Action Mailer Methods -There are just three methods that you need to send pretty much any email message: - -* `headers` - Specifies any header on the email you want. You can pass a hash of header field names and value pairs, or you can call `headers[:field_name] = 'value'`. -* `attachments` - Allows you to add attachments to your email. For example, `attachments['file-name.jpg'] = File.read('file-name.jpg')`. -* `mail` - Sends the actual email itself. You can pass in headers as a hash to the mail method as a parameter, mail will then create an email, either plain text, or multipart, depending on what email templates you have defined. +There are just three methods that you need to send pretty much any email +message: -#### Custom Headers - -Defining custom headers are simple, you can do it one of three ways: - -* Defining a header field as a parameter to the `mail` method: - - ```ruby - mail('X-Spam' => value) - ``` - -* Passing in a key value assignment to the `headers` method: - - ```ruby - headers['X-Spam'] = value - ``` - -* Passing a hash of key value pairs to the `headers` method: - - ```ruby - headers {'X-Spam' => value, 'X-Special' => another_value} - ``` - -TIP: All `X-Value` headers per the RFC2822 can appear more than once. If you want to delete an `X-Value` header, you need to assign it a value of `nil`. +* `headers` - Specifies any header on the email you want. You can pass a hash of + header field names and value pairs, or you can call `headers[:field_name] = + 'value'`. +* `attachments` - Allows you to add attachments to your email. For example, + `attachments['file-name.jpg'] = File.read('file-name.jpg')`. +* `mail` - Sends the actual email itself. You can pass in headers as a hash to + the mail method as a parameter, mail will then create an email, either plain + text, or multipart, depending on what email templates you have defined. #### Adding Attachments -Adding attachments has been simplified in Action Mailer 3.0. +Action Mailer makes it very easy to add attachments. -* Pass the file name and content and Action Mailer and the Mail gem will automatically guess the mime_type, set the encoding and create the attachment. +* Pass the file name and content and Action Mailer and the + [Mail gem](https://github.com/mikel/mail) will automatically guess the + mime_type, set the encoding and create the attachment. ```ruby attachments['filename.jpg'] = File.read('/path/to/filename.jpg') ``` -NOTE: Mail will automatically Base64 encode an attachment. If you want something different, pre-encode your content and pass in the encoded content and encoding in a `Hash` to the `attachments` method. +NOTE: Mail will automatically Base64 encode an attachment. If you want something +different, encode your content and pass in the encoded content and encoding in a +`Hash` to the `attachments` method. -* Pass the file name and specify headers and content and Action Mailer and Mail will use the settings you pass in. +* Pass the file name and specify headers and content and Action Mailer and Mail + will use the settings you pass in. ```ruby encoded_content = SpecialEncode(File.read('/path/to/filename.jpg')) @@ -210,13 +230,14 @@ NOTE: Mail will automatically Base64 encode an attachment. If you want something content: encoded_content } ``` -NOTE: If you specify an encoding, Mail will assume that your content is already encoded and not try to Base64 encode it. +NOTE: If you specify an encoding, Mail will assume that your content is already +encoded and not try to Base64 encode it. #### Making Inline Attachments Action Mailer 3.0 makes inline attachments, which involved a lot of hacking in pre 3.0 versions, much simpler and trivial as they should be. -* Firstly, to tell Mail to turn an attachment into an inline attachment, you just call `#inline` on the attachments method within your Mailer: +* First, to tell Mail to turn an attachment into an inline attachment, you just call `#inline` on the attachments method within your Mailer: ```ruby def welcome @@ -224,7 +245,9 @@ Action Mailer 3.0 makes inline attachments, which involved a lot of hacking in p end ``` -* Then in your view, you can just reference `attachments[]` as a hash and specify which attachment you want to show, calling `url` on it and then passing the result into the `image_tag` method: +* Then in your view, you can just reference `attachments` as a hash and specify + which attachment you want to show, calling `url` on it and then passing the + result into the `image_tag` method: ```html+erb <p>Hello there, this is our image</p> @@ -232,7 +255,8 @@ Action Mailer 3.0 makes inline attachments, which involved a lot of hacking in p <%= image_tag attachments['image.jpg'].url %> ``` -* As this is a standard call to `image_tag` you can pass in an options hash after the attachment URL as you could for any other image: +* As this is a standard call to `image_tag` you can pass in an options hash + after the attachment URL as you could for any other image: ```html+erb <p>Hello there, this is our image</p> @@ -243,7 +267,10 @@ Action Mailer 3.0 makes inline attachments, which involved a lot of hacking in p #### Sending Email To Multiple Recipients -It is possible to send email to one or more recipients in one email (e.g., informing all admins of a new signup) by setting the list of emails to the `:to` key. The list of emails can be an array of email addresses or a single string with the addresses separated by commas. +It is possible to send email to one or more recipients in one email (e.g., +informing all admins of a new signup) by setting the list of emails to the `:to` +key. The list of emails can be an array of email addresses or a single string +with the addresses separated by commas. ```ruby class AdminMailer < ActionMailer::Base @@ -257,12 +284,14 @@ class AdminMailer < ActionMailer::Base end ``` -The same format can be used to set carbon copy (Cc:) and blind carbon copy (Bcc:) recipients, by using the `:cc` and `:bcc` keys respectively. +The same format can be used to set carbon copy (Cc:) and blind carbon copy +(Bcc:) recipients, by using the `:cc` and `:bcc` keys respectively. #### Sending Email With Name -Sometimes you wish to show the name of the person instead of just their email address when they receive the email. The trick to doing that is -to format the email address in the format `"Name <email>"`. +Sometimes you wish to show the name of the person instead of just their email +address when they receive the email. The trick to doing that is to format the +email address in the format `"Full Name <email>"`. ```ruby def welcome_email(user) @@ -274,7 +303,11 @@ end ### Mailer Views -Mailer views are located in the `app/views/name_of_mailer_class` directory. The specific mailer view is known to the class because its name is the same as the mailer method. In our example from above, our mailer view for the `welcome_email` method will be in `app/views/user_mailer/welcome_email.html.erb` for the HTML version and `welcome_email.text.erb` for the plain text version. +Mailer views are located in the `app/views/name_of_mailer_class` directory. The +specific mailer view is known to the class because its name is the same as the +mailer method. In our example from above, our mailer view for the +`welcome_email` method will be in `app/views/user_mailer/welcome_email.html.erb` +for the HTML version and `welcome_email.text.erb` for the plain text version. To change the default mailer view for your action you do something like: @@ -285,7 +318,7 @@ class UserMailer < ActionMailer::Base def welcome_email(user) @user = user @url = 'http://example.com/login' - mail(to: user.email, + mail(to: @user.email, subject: 'Welcome to My Awesome Site', template_path: 'notifications', template_name: 'another') @@ -293,9 +326,12 @@ class UserMailer < ActionMailer::Base end ``` -In this case it will look for templates at `app/views/notifications` with name `another`. You can also specify an array of paths for `template_path`, and they will be searched in order. +In this case it will look for templates at `app/views/notifications` with name +`another`. You can also specify an array of paths for `template_path`, and they +will be searched in order. -If you want more flexibility you can also pass a block and render specific templates or even render inline or text without using a template file: +If you want more flexibility you can also pass a block and render specific +templates or even render inline or text without using a template file: ```ruby class UserMailer < ActionMailer::Base @@ -304,23 +340,28 @@ class UserMailer < ActionMailer::Base def welcome_email(user) @user = user @url = 'http://example.com/login' - mail(to: user.email, + mail(to: @user.email, subject: 'Welcome to My Awesome Site') do |format| format.html { render 'another_template' } format.text { render text: 'Render text' } end end - end ``` -This will render the template 'another_template.html.erb' for the HTML part and use the rendered text for the text part. The render command is the same one used inside of Action Controller, so you can use all the same options, such as `:text`, `:inline` etc. +This will render the template 'another_template.html.erb' for the HTML part and +use the rendered text for the text part. The render command is the same one used +inside of Action Controller, so you can use all the same options, such as +`:text`, `:inline` etc. ### Action Mailer Layouts -Just like controller views, you can also have mailer layouts. The layout name needs to be the same as your mailer, such as `user_mailer.html.erb` and `user_mailer.text.erb` to be automatically recognized by your mailer as a layout. +Just like controller views, you can also have mailer layouts. The layout name +needs to be the same as your mailer, such as `user_mailer.html.erb` and +`user_mailer.text.erb` to be automatically recognized by your mailer as a +layout. -In order to use a different file just use: +In order to use a different file, call `layout` in your mailer: ```ruby class UserMailer < ActionMailer::Base @@ -328,9 +369,11 @@ class UserMailer < ActionMailer::Base end ``` -Just like with controller views, use `yield` to render the view inside the layout. +Just like with controller views, use `yield` to render the view inside the +layout. -You can also pass in a `layout: 'layout_name'` option to the render call inside the format block to specify different layouts for different actions: +You can also pass in a `layout: 'layout_name'` option to the render call inside +the format block to specify different layouts for different actions: ```ruby class UserMailer < ActionMailer::Base @@ -343,13 +386,37 @@ class UserMailer < ActionMailer::Base end ``` -Will render the HTML part using the `my_layout.html.erb` file and the text part with the usual `user_mailer.text.erb` file if it exists. +Will render the HTML part using the `my_layout.html.erb` file and the text part +with the usual `user_mailer.text.erb` file if it exists. ### Generating URLs in Action Mailer Views -URLs can be generated in mailer views using `url_for` or named routes. +Unlike controllers, the mailer instance doesn't have any context about the +incoming request so you'll need to provide the `:host` parameter yourself. + +As the `:host` usually is consistent across the application you can configure it +globally in `config/application.rb`: + +```ruby +config.action_mailer.default_url_options = { host: 'example.com' } +``` + +#### generating URLs with `url_for` + +You need to pass the `only_path: false` option when using `url_for`. This will +ensure that absolute URLs are generated because the `url_for` view helper will, +by default, generate relative URLs when a `:host` option isn't explicitly +provided. + +```erb +<%= url_for(controller: 'welcome', + action: 'greeting', + only_path: false) %> +``` + +If you did not configure the `:host` option globally make sure to pass it to +`url_for`. -Unlike controllers, the mailer instance doesn't have any context about the incoming request so you'll need to provide the `:host`, `:controller`, and `:action`: ```erb <%= url_for(host: 'example.com', @@ -357,27 +424,32 @@ Unlike controllers, the mailer instance doesn't have any context about the incom action: 'greeting') %> ``` -When using named routes you only need to supply the `:host`: +NOTE: When you explicitly pass the `:host` Rails will always generate absolute +URLs, so there is no need to pass `only_path: false`. -```erb -<%= user_url(@user, host: 'example.com') %> -``` +#### generating URLs with named routes -Email clients have no web context and so paths have no base URL to form complete web addresses. Thus, when using named routes only the "_url" variant makes sense. +Email clients have no web context and so paths have no base URL to form complete +web addresses. Thus, you should always use the "_url" variant of named route +helpers. -It is also possible to set a default host that will be used in all mailers by setting the `:host` option as a configuration option in `config/application.rb`: +If you did not configure the `:host` option globally make sure to pass it to the +url helper. -```ruby -config.action_mailer.default_url_options = { host: 'example.com' } +```erb +<%= user_url(@user, host: 'example.com') %> ``` -If you use this setting, you should pass the `only_path: false` option when using `url_for`. This will ensure that absolute URLs are generated because the `url_for` view helper will, by default, generate relative URLs when a `:host` option isn't explicitly provided. - ### Sending Multipart Emails -Action Mailer will automatically send multipart emails if you have different templates for the same action. So, for our UserMailer example, if you have `welcome_email.text.erb` and `welcome_email.html.erb` in `app/views/user_mailer`, Action Mailer will automatically send a multipart email with the HTML and text versions setup as different parts. +Action Mailer will automatically send multipart emails if you have different +templates for the same action. So, for our UserMailer example, if you have +`welcome_email.text.erb` and `welcome_email.html.erb` in +`app/views/user_mailer`, Action Mailer will automatically send a multipart email +with the HTML and text versions setup as different parts. -The order of the parts getting inserted is determined by the `:parts_order` inside of the `ActionMailer::Base.default` method. +The order of the parts getting inserted is determined by the `:parts_order` +inside of the `ActionMailer::Base.default` method. ### Sending Emails with Attachments @@ -389,38 +461,51 @@ class UserMailer < ActionMailer::Base @user = user @url = user_url(@user) attachments['terms.pdf'] = File.read('/path/terms.pdf') - mail(to: user.email, + mail(to: @user.email, subject: 'Please see the Terms and Conditions attached') end end ``` -The above will send a multipart email with an attachment, properly nested with the top level being `multipart/mixed` and the first part being a `multipart/alternative` containing the plain text and HTML email messages. +The above will send a multipart email with an attachment, properly nested with +the top level being `multipart/mixed` and the first part being a +`multipart/alternative` containing the plain text and HTML email messages. ### Sending Emails with Dynamic Delivery Options -If you wish to override the default delivery options (e.g. SMTP credentials) while delivering emails, you can do this using `delivery_method_options` in the mailer action. +If you wish to override the default delivery options (e.g. SMTP credentials) +while delivering emails, you can do this using `delivery_method_options` in the +mailer action. ```ruby class UserMailer < ActionMailer::Base def welcome_email(user, company) @user = user @url = user_url(@user) - delivery_options = { user_name: company.smtp_user, password: company.smtp_password, address: company.smtp_host } - mail(to: user.email, subject: "Please see the Terms and Conditions attached", delivery_method_options: delivery_options) + delivery_options = { user_name: company.smtp_user, + password: company.smtp_password, + address: company.smtp_host } + mail(to: @user.email, + subject: "Please see the Terms and Conditions attached", + delivery_method_options: delivery_options) end end ``` ### Sending Emails without Template Rendering -There may be cases in which you want to skip the template rendering step and supply the email body as a string. You can achieve this using the `:body` option. -In such cases don't forget to add the `:content_type` option. Rails will default to `text/plain` otherwise. +There may be cases in which you want to skip the template rendering step and +supply the email body as a string. You can achieve this using the `:body` +option. In such cases don't forget to add the `:content_type` option. Rails +will default to `text/plain` otherwise. ```ruby class UserMailer < ActionMailer::Base def welcome_email(user, email_body) - mail(to: user.email, body: email_body, content_type: "text/html", subject: "Already rendered!") + mail(to: user.email, + body: email_body, + content_type: "text/html", + subject: "Already rendered!") end end ``` @@ -428,13 +513,21 @@ end Receiving Emails ---------------- -Receiving and parsing emails with Action Mailer can be a rather complex endeavor. Before your email reaches your Rails app, you would have had to configure your system to somehow forward emails to your app, which needs to be listening for that. So, to receive emails in your Rails app you'll need to: +Receiving and parsing emails with Action Mailer can be a rather complex +endeavor. Before your email reaches your Rails app, you would have had to +configure your system to somehow forward emails to your app, which needs to be +listening for that. So, to receive emails in your Rails app you'll need to: * Implement a `receive` method in your mailer. -* Configure your email server to forward emails from the address(es) you would like your app to receive to `/path/to/app/bin/rails runner 'UserMailer.receive(STDIN.read)'`. +* Configure your email server to forward emails from the address(es) you would + like your app to receive to `/path/to/app/bin/rails runner + 'UserMailer.receive(STDIN.read)'`. -Once a method called `receive` is defined in any mailer, Action Mailer will parse the raw incoming email into an email object, decode it, instantiate a new mailer, and pass the email object to the mailer `receive` instance method. Here's an example: +Once a method called `receive` is defined in any mailer, Action Mailer will +parse the raw incoming email into an email object, decode it, instantiate a new +mailer, and pass the email object to the mailer `receive` instance +method. Here's an example: ```ruby class UserMailer < ActionMailer::Base @@ -460,17 +553,23 @@ end Action Mailer Callbacks --------------------------- -Action Mailer allows for you to specify a `before_action`, `after_action` and `around_action`. +Action Mailer allows for you to specify a `before_action`, `after_action` and +`around_action`. -* Filters can be specified with a block or a symbol to a method in the mailer class similar to controllers. +* Filters can be specified with a block or a symbol to a method in the mailer + class similar to controllers. -* You could use a `before_action` to prepopulate the mail object with defaults, delivery_method_options or insert default headers and attachments. +* You could use a `before_action` to populate the mail object with defaults, + delivery_method_options or insert default headers and attachments. -* You could use an `after_action` to do similar setup as a `before_action` but using instance variables set in your mailer action. +* You could use an `after_action` to do similar setup as a `before_action` but + using instance variables set in your mailer action. ```ruby class UserMailer < ActionMailer::Base - after_action :set_delivery_options, :prevent_delivery_to_guests, :set_business_headers + after_action :set_delivery_options, + :prevent_delivery_to_guests, + :set_business_headers def feedback_message(business, user) @business = business @@ -486,7 +585,8 @@ class UserMailer < ActionMailer::Base private def set_delivery_options - # You have access to the mail instance and @business and @user instance variables here + # You have access to the mail instance, + # @business and @user instance variables here if @business && @business.has_smtp_settings? mail.delivery_method.settings.merge!(@business.smtp_settings) end @@ -511,12 +611,14 @@ end Using Action Mailer Helpers --------------------------- -Action Mailer now just inherits from Abstract Controller, so you have access to the same generic helpers as you do in Action Controller. +Action Mailer now just inherits from `AbstractController`, so you have access to +the same generic helpers as you do in Action Controller. Action Mailer Configuration --------------------------- -The following configuration options are best made in one of the environment files (environment.rb, production.rb, etc...) +The following configuration options are best made in one of the environment +files (environment.rb, production.rb, etc...) | Configuration | Description | |---------------|-------------| @@ -529,9 +631,14 @@ The following configuration options are best made in one of the environment file |`deliveries`|Keeps an array of all the emails sent out through the Action Mailer with delivery_method :test. Most useful for unit and functional testing.| |`default_options`|Allows you to set default values for the `mail` method options (`:from`, `:reply_to`, etc.).| +For a complete writeup of possible configurations see the +[Action Mailer section](configuring.html#configuring-action-mailer) in +our Configuring Rails Applications guide. + ### Example Action Mailer Configuration -An example would be adding the following to your appropriate `config/environments/$RAILS_ENV.rb` file: +An example would be adding the following to your appropriate +`config/environments/$RAILS_ENV.rb` file: ```ruby config.action_mailer.delivery_method = :sendmail @@ -542,19 +649,20 @@ config.action_mailer.delivery_method = :sendmail # } config.action_mailer.perform_deliveries = true config.action_mailer.raise_delivery_errors = true -config.action_mailer.default_options = {from: 'no-replay@example.org'} +config.action_mailer.default_options = {from: 'no-replay@example.com'} ``` -### Action Mailer Configuration for GMail +### Action Mailer Configuration for Gmail -As Action Mailer now uses the Mail gem, this becomes as simple as adding to your `config/environments/$RAILS_ENV.rb` file: +As Action Mailer now uses the Mail gem, this becomes as simple as adding to your +`config/environments/$RAILS_ENV.rb` file: ```ruby config.action_mailer.delivery_method = :smtp config.action_mailer.smtp_settings = { address: 'smtp.gmail.com', port: 587, - domain: 'baci.lindsaar.net', + domain: 'example.com', user_name: '<username>', password: '<password>', authentication: 'plain', @@ -564,12 +672,15 @@ config.action_mailer.smtp_settings = { Mailer Testing -------------- -You can find detailed instructions on how to test your mailers in our +You can find detailed instructions on how to test your mailers in the [testing guide](testing.html#testing-your-mailers). Intercepting Emails ------------------- -There are situations where you need to edit an email before it's delivered. Fortunately Action Mailer provides hooks to intercept every email. You can register an interceptor to make modifications to mail messages right before they are handed to the delivery agents. +There are situations where you need to edit an email before it's +delivered. Fortunately Action Mailer provides hooks to intercept every +email. You can register an interceptor to make modifications to mail messages +right before they are handed to the delivery agents. ```ruby class SandboxEmailInterceptor @@ -579,10 +690,15 @@ class SandboxEmailInterceptor end ``` -Before the interceptor can do its job you need to register it with the Action Mailer framework. You can do this in an initializer file `config/initializers/sandbox_email_interceptor.rb` +Before the interceptor can do its job you need to register it with the Action +Mailer framework. You can do this in an initializer file +`config/initializers/sandbox_email_interceptor.rb` ```ruby ActionMailer::Base.register_interceptor(SandboxEmailInterceptor) if Rails.env.staging? ``` -NOTE: The example above uses a custom environment called "staging" for a production like server but for testing purposes. You can read [Creating Rails environments](./configuring.html#creating-rails-environments) for more information about custom Rails environments. +NOTE: The example above uses a custom environment called "staging" for a +production like server but for testing purposes. You can read +[Creating Rails environments](./configuring.html#creating-rails-environments) +for more information about custom Rails environments. diff --git a/guides/source/action_view_overview.md b/guides/source/action_view_overview.md index 3b5963efc2..dea1ddef71 100644 --- a/guides/source/action_view_overview.md +++ b/guides/source/action_view_overview.md @@ -172,7 +172,7 @@ That code will pull in the partial from `app/views/shared/_menu.html.erb`. #### Using Partials to simplify Views -One way to use partials is to treat them as the equivalent of subroutines: as a way to move details out of a view so that you can grasp what's going on more easily. For example, you might have a view that looked like this: +One way to use partials is to treat them as the equivalent of subroutines; a way to move details out of a view so that you can grasp what's going on more easily. For example, you might have a view that looks like this: ```html+erb <%= render "shared/ad_banner" %> @@ -269,12 +269,7 @@ Rails will render the `_product_ruler` partial (with no data passed to it) betwe ### Layouts -TODO... - -Using Templates, Partials and Layouts "The Rails Way" --------------------------------------------------------- - -TODO... +Layouts can be used to render a common view template around the results of Rails controller actions. Typically, every Rails has a couple of overall layouts that most pages are rendered within. For example, a site might have a layout for a logged in user, and a layout for the marketing or sales side of the site. The logged in user layout might include top-level navigation that should be present across many controller actions. The sales layout for a SaaS app might include top-level navigation for things like "Pricing" and "Contact Us." You would expect each layout to have a different look and feel. You can read more details about Layouts in the [Layouts and Rendering in Rails](layouts_and_rendering.html) guide. Partial Layouts --------------- diff --git a/guides/source/active_record_basics.md b/guides/source/active_record_basics.md index 69d7333e6f..fc8fac4651 100644 --- a/guides/source/active_record_basics.md +++ b/guides/source/active_record_basics.md @@ -1,14 +1,14 @@ Active Record Basics ==================== - + This guide is an introduction to Active Record. After reading this guide, you will know: -* What Object Relational Mapping and Active Record are and how they are used in +* What Object Relational Mapping and Active Record are and how they are used in Rails. * How Active Record fits into the Model-View-Controller paradigm. -* How to use Active Record models to manipulate data stored in a relational +* How to use Active Record models to manipulate data stored in a relational database. * Active Record schema naming conventions. * The concepts of database migrations, validations and callbacks. @@ -18,33 +18,34 @@ After reading this guide, you will know: What is Active Record? ---------------------- -Active Record is the M in [MVC](getting_started.html#the-mvc-architecture) - the -model - which is the layer of the system responsible for representing business -data and logic. Active Record facilitates the creation and use of business -objects whose data requires persistent storage to a database. It is an -implementation of the Active Record pattern which itself is a description of an +Active Record is the M in [MVC](getting_started.html#the-mvc-architecture) - the +model - which is the layer of the system responsible for representing business +data and logic. Active Record facilitates the creation and use of business +objects whose data requires persistent storage to a database. It is an +implementation of the Active Record pattern which itself is a description of an Object Relational Mapping system. ### The Active Record Pattern -Active Record was described by Martin Fowler in his book _Patterns of Enterprise -Application Architecture_. In Active Record, objects carry both persistent data -and behavior which operates on that data. Active Record takes the opinion that -ensuring data access logic is part of the object will educate users of that +[Active Record was described by Martin Fowler](http://www.martinfowler.com/eaaCatalog/activeRecord.html) +in his book _Patterns of Enterprise Application Architecture_. In +Active Record, objects carry both persistent data and behavior which +operates on that data. Active Record takes the opinion that ensuring +data access logic is part of the object will educate users of that object on how to write to and read from the database. ### Object Relational Mapping -Object-Relational Mapping, commonly referred to as its abbreviation ORM, is -a technique that connects the rich objects of an application to tables in -a relational database management system. Using ORM, the properties and -relationships of the objects in an application can be easily stored and -retrieved from a database without writing SQL statements directly and with less +Object-Relational Mapping, commonly referred to as its abbreviation ORM, is +a technique that connects the rich objects of an application to tables in +a relational database management system. Using ORM, the properties and +relationships of the objects in an application can be easily stored and +retrieved from a database without writing SQL statements directly and with less overall database access code. ### Active Record as an ORM Framework -Active Record gives us several mechanisms, the most important being the ability +Active Record gives us several mechanisms, the most important being the ability to: * Represent models and their data @@ -56,29 +57,29 @@ to: Convention over Configuration in Active Record ---------------------------------------------- -When writing applications using other programming languages or frameworks, it -may be necessary to write a lot of configuration code. This is particularly true -for ORM frameworks in general. However, if you follow the conventions adopted by -Rails, you'll need to write very little configuration (in some case no -configuration at all) when creating Active Record models. The idea is that if -you configure your applications in the very same way most of the times then this -should be the default way. In this cases, explicit configuration would be needed +When writing applications using other programming languages or frameworks, it +may be necessary to write a lot of configuration code. This is particularly true +for ORM frameworks in general. However, if you follow the conventions adopted by +Rails, you'll need to write very little configuration (in some case no +configuration at all) when creating Active Record models. The idea is that if +you configure your applications in the very same way most of the times then this +should be the default way. In this cases, explicit configuration would be needed only in those cases where you can't follow the conventions for any reason. ### Naming Conventions -By default, Active Record uses some naming conventions to find out how the -mapping between models and database tables should be created. Rails will -pluralize your class names to find the respective database table. So, for -a class `Book`, you should have a database table called **books**. The Rails -pluralization mechanisms are very powerful, being capable to pluralize (and -singularize) 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 contain the words separated +By default, Active Record uses some naming conventions to find out how the +mapping between models and database tables should be created. Rails will +pluralize your class names to find the respective database table. So, for +a class `Book`, you should have a database table called **books**. The Rails +pluralization mechanisms are very powerful, being capable to pluralize (and +singularize) 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 contain the words separated by underscores. Examples: * Database Table - Plural with underscores separating words (e.g., `book_clubs`) -* Model Class - Singular with the first letter of each word capitalized (e.g., +* Model Class - Singular with the first letter of each word capitalized (e.g., `BookClub`) | Model / Class | Table / Schema | @@ -92,33 +93,35 @@ by underscores. Examples: ### Schema Conventions -Active Record uses naming conventions for the columns in database tables, +Active Record uses naming conventions for the columns in database tables, depending on the purpose of these columns. -* **Foreign keys** - These fields should be named following the pattern - `singularized_table_name_id` (e.g., `item_id`, `order_id`). These are the - fields that Active Record will look for when you create associations between +* **Foreign keys** - These fields should be named following the pattern + `singularized_table_name_id` (e.g., `item_id`, `order_id`). These are the + fields that Active Record will look for when you create associations between your models. -* **Primary keys** - By default, Active Record will use an integer column named - `id` as the table's primary key. When using [Rails - Migrations](migrations.html) to create your tables, this column will be +* **Primary keys** - By default, Active Record will use an integer column named + `id` as the table's primary key. When using [Rails + Migrations](migrations.html) to create your tables, this column will be automatically created. -There are also some optional column names that will create additional features +There are also some optional column names that will create additional features to Active Record instances: -* `created_at` - Automatically gets set to the current date and time when the +* `created_at` - Automatically gets set to the current date and time when the record is first created. -* `updated_at` - Automatically gets set to the current date and time whenever +* `updated_at` - Automatically gets set to the current date and time whenever the record is updated. -* `lock_version` - Adds [optimistic - locking](http://api.rubyonrails.org/classes/ActiveRecord/Locking.html) to +* `lock_version` - Adds [optimistic + locking](http://api.rubyonrails.org/classes/ActiveRecord/Locking.html) to a model. -* `type` - Specifies that the model uses [Single Table +* `type` - Specifies that the model uses [Single Table Inheritance](http://api.rubyonrails.org/classes/ActiveRecord/Base.html) -* `(table_name)_count` - Used to cache the number of belonging objects on - associations. For example, a `comments_count` column in a `Post` class that - has many instances of `Comment` will cache the number of existent comments +* `(association_name)_type` - Stores the type for + [polymorphic associations](association_basics.html#polymorphic-associations). +* `(table_name)_count` - Used to cache the number of belonging objects on + associations. For example, a `comments_count` column in a `Post` class that + has many instances of `Comment` will cache the number of existent comments for each post. NOTE: While these column names are optional, they are in fact reserved by Active Record. Steer clear of reserved keywords unless you want the extra functionality. For example, `type` is a reserved keyword used to designate a table using Single Table Inheritance (STI). If you are not using STI, try an analogous keyword like "context", that may still accurately describe the data you are modeling. @@ -126,7 +129,7 @@ NOTE: While these column names are optional, they are in fact reserved by Active Creating Active Record Models ----------------------------- -It is very easy to create Active Record models. All you have to do is to +It is very easy to create Active Record models. All you have to do is to subclass the `ActiveRecord::Base` class and you're good to go: ```ruby @@ -134,9 +137,9 @@ class Product < ActiveRecord::Base end ``` -This will create a `Product` model, mapped to a `products` table at the -database. By doing this you'll also have the ability to map the columns of each -row in that table with the attributes of the instances of your model. Suppose +This will create a `Product` model, mapped to a `products` table at the +database. By doing this you'll also have the ability to map the columns of each +row in that table with the attributes of the instances of your model. Suppose that the `products` table was created using an SQL sentence like: ```sql @@ -147,7 +150,7 @@ CREATE TABLE products ( ); ``` -Following the table schema above, you would be able to write code like the +Following the table schema above, you would be able to write code like the following: ```ruby @@ -159,11 +162,11 @@ puts p.name # "Some Book" Overriding the Naming Conventions --------------------------------- -What if you need to follow a different naming convention or need to use your -Rails application with a legacy database? No problem, you can easily override +What if you need to follow a different naming convention or need to use your +Rails application with a legacy database? No problem, you can easily override the default conventions. -You can use the `ActiveRecord::Base.table_name=` method to specify the table +You can use the `ActiveRecord::Base.table_name=` method to specify the table name that should be used: ```ruby @@ -172,8 +175,8 @@ class Product < ActiveRecord::Base end ``` -If you do so, you will have to define manually the class name that is hosting -the fixtures (class_name.yml) using the `set_fixture_class` method in your test +If you do so, you will have to define manually the class name that is hosting +the fixtures (class_name.yml) using the `set_fixture_class` method in your test definition: ```ruby @@ -184,7 +187,7 @@ class FunnyJoke < ActiveSupport::TestCase end ``` -It's also possible to override the column that should be used as the table's +It's also possible to override the column that should be used as the table's primary key using the `ActiveRecord::Base.set_primary_key` method: ```ruby @@ -196,17 +199,17 @@ end CRUD: Reading and Writing Data ------------------------------ -CRUD is an acronym for the four verbs we use to operate on data: **C**reate, -**R**ead, **U**pdate and **D**elete. Active Record automatically creates methods +CRUD is an acronym for the four verbs we use to operate on data: **C**reate, +**R**ead, **U**pdate and **D**elete. Active Record automatically creates methods to allow an application to read and manipulate data stored within its tables. ### Create -Active Record objects can be created from a hash, a block or have their -attributes manually set after creation. The `new` method will return a new +Active Record objects can be created from a hash, a block or have their +attributes manually set after creation. The `new` method will return a new object while `create` will return the object and save it to the database. -For example, given a model `User` with attributes of `name` and `occupation`, +For example, given a model `User` with attributes of `name` and `occupation`, the `create` method call will create and save a new record into the database: ```ruby @@ -223,7 +226,7 @@ user.occupation = "Code Artist" A call to `user.save` will commit the record to the database. -Finally, if a block is provided, both `create` and `new` will yield the new +Finally, if a block is provided, both `create` and `new` will yield the new object to that block for initialization: ```ruby @@ -235,7 +238,7 @@ end ### Read -Active Record provides a rich API for accessing data within a database. Below +Active Record provides a rich API for accessing data within a database. Below are a few examples of different data access methods provided by Active Record. ```ruby @@ -258,12 +261,12 @@ david = User.find_by_name('David') users = User.where(name: 'David', occupation: 'Code Artist').order('created_at DESC') ``` -You can learn more about querying an Active Record model in the [Active Record +You can learn more about querying an Active Record model in the [Active Record Query Interface](active_record_querying.html) guide. ### Update -Once an Active Record object has been retrieved, its attributes can be modified +Once an Active Record object has been retrieved, its attributes can be modified and it can be saved to the database. ```ruby @@ -272,7 +275,7 @@ user.name = 'Dave' user.save ``` -A shorthand for this is to use a hash mapping attribute names to the desired +A shorthand for this is to use a hash mapping attribute names to the desired value, like so: ```ruby @@ -280,8 +283,8 @@ user = User.find_by_name('David') user.update(name: 'Dave') ``` -This is most useful when updating several attributes at once. If, on the other -hand, you'd like to update several records in bulk, you may find the +This is most useful when updating several attributes at once. If, on the other +hand, you'd like to update several records in bulk, you may find the `update_all` class method useful: ```ruby @@ -290,7 +293,7 @@ User.update_all "max_login_attempts = 3, must_change_password = 'true'" ### Delete -Likewise, once retrieved an Active Record object can be destroyed which removes +Likewise, once retrieved an Active Record object can be destroyed which removes it from the database. ```ruby @@ -301,46 +304,46 @@ user.destroy Validations ----------- -Active Record allows you to validate the state of a model before it gets written -into the database. There are several methods that you can use to check your -models and validate that an attribute value is not empty, is unique and not +Active Record allows you to validate the state of a model before it gets written +into the database. There are several methods that you can use to check your +models and validate that an attribute value is not empty, is unique and not already in the database, follows a specific format and many more. -Validation is a very important issue to consider when persisting to database, so -the methods `create`, `save` and `update` take it into account when -running: they return `false` when validation fails and they didn't actually -perform any operation on database. All of these have a bang counterpart (that -is, `create!`, `save!` and `update!`), which are stricter in that -they raise the exception `ActiveRecord::RecordInvalid` if validation fails. +Validation is a very important issue to consider when persisting to database, so +the methods `create`, `save` and `update` take it into account when +running: they return `false` when validation fails and they didn't actually +perform any operation on database. All of these have a bang counterpart (that +is, `create!`, `save!` and `update!`), which are stricter in that +they raise the exception `ActiveRecord::RecordInvalid` if validation fails. A quick example to illustrate: ```ruby class User < ActiveRecord::Base - validates_presence_of :name + validates :name, presence: true end User.create # => false User.create! # => ActiveRecord::RecordInvalid: Validation failed: Name can't be blank ``` -You can learn more about validations in the [Active Record Validations +You can learn more about validations in the [Active Record Validations guide](active_record_validations.html). Callbacks --------- -Active Record callbacks allow you to attach code to certain events in the -life-cycle of your models. This enables you to add behavior to your models by -transparently executing code when those events occur, like when you create a new -record, update it, destroy it and so on. You can learn more about callbacks in +Active Record callbacks allow you to attach code to certain events in the +life-cycle of your models. This enables you to add behavior to your models by +transparently executing code when those events occur, like when you create a new +record, update it, destroy it and so on. You can learn more about callbacks in the [Active Record Callbacks guide](active_record_callbacks.html). Migrations ---------- -Rails provides a domain-specific language for managing a database schema called -migrations. Migrations are stored in files which are executed against any -database that Active Record support using `rake`. Here's a migration that +Rails provides a domain-specific language for managing a database schema called +migrations. Migrations are stored in files which are executed against any +database that Active Record support using `rake`. Here's a migration that creates a table: ```ruby @@ -361,10 +364,10 @@ class CreatePublications < ActiveRecord::Migration end ``` -Rails keeps track of which files have been committed to the database and +Rails keeps track of which files have been committed to the database and provides rollback features. To actually create the table, you'd run `rake db:migrate` and to roll it back, `rake db:rollback`. -Note that the above code is database-agnostic: it will run in MySQL, postgresql, -Oracle and others. You can learn more about migrations in the [Active Record +Note that the above code is database-agnostic: it will run in MySQL, postgresql, +Oracle and others. You can learn more about migrations in the [Active Record Migrations guide](migrations.html) diff --git a/guides/source/active_support_core_extensions.md b/guides/source/active_support_core_extensions.md index 43529e3e96..101a4f5b42 100644 --- a/guides/source/active_support_core_extensions.md +++ b/guides/source/active_support_core_extensions.md @@ -1039,6 +1039,8 @@ For convenience `class_attribute` also defines an instance predicate which is th When `:instance_reader` is `false`, the instance predicate returns a `NoMethodError` just like the reader method. +If you do not want the instance predicate, pass `instance_predicate: false` and it will not be defined. + NOTE: Defined in `active_support/core_ext/class/attribute.rb` #### `cattr_reader`, `cattr_writer`, and `cattr_accessor` diff --git a/guides/source/asset_pipeline.md b/guides/source/asset_pipeline.md index 448f0e1f9a..43df544e28 100644 --- a/guides/source/asset_pipeline.md +++ b/guides/source/asset_pipeline.md @@ -547,35 +547,7 @@ This directive is available if the core module that provides this feature was co If you're compiling nginx with Phusion Passenger you'll need to pass that option when prompted. -Apache is also able to serve the [gzipped](http://en.wikipedia.org/wiki/Gzip) version of your assets; however, it requires a bit more work: - -```apache -<LocationMatch "^/assets/.*$"> - Header unset ETag - FileETag None - - # RFC says only cache for 1 year - ExpiresActive On - ExpiresDefault "access plus 1 year" - - RewriteEngine On - RewriteCond %{HTTP:Accept-Encoding} gzip - RewriteCond %{HTTP_USER_AGENT} !Konqueror - RewriteCond %{REQUEST_FILENAME}.gz -f - RewriteRule ^(.+).(css|js)$ $1.$2.gz [QSA,L] -</LocationMatch> - -<FilesMatch \.css\.gz> - ForceType text/css -</FilesMatch> - -<FilesMatch \.js\.gz> - ForceType application/javascript -</FilesMatch> -AddEncoding gzip .gz -``` - -NOTE: You will need to make sure `mod_headers`, `mod_mime` and `mod_rewrite` are loaded; otherwise, the above configuration will fail. +A robust configuration for Apache is possible but tricky; please Google around. (Or help update this Guide if you have a good example configuration for Apache.) ### Local Precompilation diff --git a/guides/source/caching_with_rails.md b/guides/source/caching_with_rails.md index abab3dd983..e1fc3d0f53 100644 --- a/guides/source/caching_with_rails.md +++ b/guides/source/caching_with_rails.md @@ -5,8 +5,8 @@ This guide will teach you what you need to know about avoiding that expensive ro After reading this guide, you will know: -* Page, action, and fragment caching. -* Sweepers. +* Page and action caching (moved to separate gems as of Rails 4). +* Fragment caching. * Alternative cache stores. * Conditional GET support. diff --git a/guides/source/command_line.md b/guides/source/command_line.md index 4711186522..7b7f5963fd 100644 --- a/guides/source/command_line.md +++ b/guides/source/command_line.md @@ -445,12 +445,12 @@ NOTE. When using specific annotations and custom annotations, the annotation nam By default, `rake notes` will look in the `app`, `config`, `lib`, `bin` and `test` directories. If you would like to search other directories, you can provide them as a comma separated list in an environment variable `SOURCE_ANNOTATION_DIRECTORIES`. ```bash -$ export SOURCE_ANNOTATION_DIRECTORIES='rspec,vendor' +$ export SOURCE_ANNOTATION_DIRECTORIES='spec,vendor' $ rake notes (in /home/foobar/commandsapp) app/models/user.rb: * [ 35] [FIXME] User should have a subscription at this point -rspec/model/user_spec.rb: +spec/models/user_spec.rb: * [122] [TODO] Verify the user that has a subscription works ``` diff --git a/guides/source/configuring.md b/guides/source/configuring.md index 9ea493325d..a0ab707b51 100644 --- a/guides/source/configuring.md +++ b/guides/source/configuring.md @@ -268,7 +268,7 @@ config.middleware.delete "Rack::MethodOverride" * `config.active_record.lock_optimistically` controls whether Active Record will use optimistic locking and is true by default. -* +config.active_record.cache_timestamp_format+ controls the format of the timestamp value in the cache key. Default is +:number+. +* `config.active_record.cache_timestamp_format` controls the format of the timestamp value in the cache key. Default is `:number`. The MySQL adapter adds one additional configuration option: diff --git a/guides/source/credits.html.erb b/guides/source/credits.html.erb index ff76fa2b85..34be07ef81 100644 --- a/guides/source/credits.html.erb +++ b/guides/source/credits.html.erb @@ -28,7 +28,7 @@ Ruby on Rails Guides: Credits <h3 class="section">Rails Guides Authors</h3> <%= author('Ryan Bigg', 'radar', 'radar.png') do %> -Ryan Bigg works as a consultant at <a href="http://rubyx.com">RubyX</a> and has been working with Rails since 2006. He's co-authoring a book called <a href="http://manning.com/katz">Rails 3 in Action</a> and he's written many gems which can be seen on <a href="https://github.com/radar">his GitHub page</a> and he also tweets prolifically as <a href="http://twitter.com/ryanbigg">@ryanbigg</a>. + Ryan Bigg works as the Community Manager at <a href="http://spreecommerce.com">Spree Commerce</a> and has been working with Rails since 2006. He's the author of <a href="https://leanpub.com/multi-tenancy-rails">Multi Tenancy With Rails</a> and co-author of <a href="http://manning.com/bigg2">Rails 4 in Action</a>. He's written many gems which can be seen on <a href="https://github.com/radar">his GitHub page</a> and he also tweets prolifically as <a href="http://twitter.com/ryanbigg">@ryanbigg</a>. <% end %> <%= author('Oscar Del Ben', 'oscardelben', 'oscardelben.jpg') do %> diff --git a/guides/source/debugging_rails_applications.md b/guides/source/debugging_rails_applications.md index 6699098e51..8f1d2922ac 100644 --- a/guides/source/debugging_rails_applications.md +++ b/guides/source/debugging_rails_applications.md @@ -655,21 +655,18 @@ Plugins for Debugging There are some Rails plugins to help you to find errors and debug your application. Here is a list of useful plugins for debugging: -* [Footnotes](https://github.com/josevalim/rails-footnotes:) Every Rails page has footnotes that give request information and link back to your source via TextMate. -* [Query Trace](https://github.com/ntalbott/query_trace/tree/master:) Adds query origin tracing to your logs. -* [Query Reviewer](https://github.com/nesquena/query_reviewer:) This rails plugin not only runs "EXPLAIN" before each of your select queries in development, but provides a small DIV in the rendered output of each page with the summary of warnings for each query that it analyzed. -* [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. +* [Footnotes](https://github.com/josevalim/rails-footnotes) Every Rails page has footnotes that give request information and link back to your source via TextMate. +* [Query Trace](https://github.com/ntalbott/query_trace/tree/master) Adds query origin tracing to your logs. +* [Query Reviewer](https://github.com/nesquena/query_reviewer) This rails plugin not only runs "EXPLAIN" before each of your select queries in development, but provides a small DIV in the rendered output of each page with the summary of warnings for each query that it analyzed. +* [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. References ---------- * [ruby-debug Homepage](http://bashdb.sourceforge.net/ruby-debug/home-page.html) * [debugger Homepage](https://github.com/cldwalker/debugger) -* [Article: Debugging a Rails application with ruby-debug](http://www.sitepoint.com/article/debug-rails-app-ruby-debug/) -* [ruby-debug Basics screencast](http://brian.maybeyoureinsane.net/blog/2007/05/07/ruby-debug-basics-screencast/) +* [Article: Debugging a Rails application with ruby-debug](http://www.sitepoint.com/debug-rails-app-ruby-debug/) * [Ryan Bates' debugging ruby (revised) screencast](http://railscasts.com/episodes/54-debugging-ruby-revised) * [Ryan Bates' stack trace screencast](http://railscasts.com/episodes/24-the-stack-trace) * [Ryan Bates' logger screencast](http://railscasts.com/episodes/56-the-logger) * [Debugging with ruby-debug](http://bashdb.sourceforge.net/ruby-debug.html) -* [ruby-debug cheat sheet](http://cheat.errtheblog.com/s/rdebug/) -* [Ruby on Rails Wiki: How to Configure Logging](http://wiki.rubyonrails.org/rails/pages/HowtoConfigureLogging) diff --git a/guides/source/development_dependencies_install.md b/guides/source/development_dependencies_install.md index 6493c1e1ec..14ca44d2a1 100644 --- a/guides/source/development_dependencies_install.md +++ b/guides/source/development_dependencies_install.md @@ -21,9 +21,9 @@ In case you can't use the Rails development box, see section above, these are th Ruby on Rails uses Git for source code control. The [Git homepage](http://git-scm.com/) has installation instructions. There are a variety of resources on the net that will help you get familiar with Git: -* [Try Git course](http://try.github.com/) is an interactive course that will teach you the basics. +* [Try Git course](http://try.github.io/) is an interactive course that will teach you the basics. * The [official Documentation](http://git-scm.com/documentation) is pretty comprehensive and also contains some videos with the basics of Git -* [Everyday Git](http://schacon.github.com/git/everyday.html) will teach you just enough about Git to get by. +* [Everyday Git](http://schacon.github.io/git/everyday.html) will teach you just enough about Git to get by. * The [PeepCode screencast](https://peepcode.com/products/git) on Git ($9) is easier to follow. * [GitHub](http://help.github.com) offers links to a variety of Git resources. * [Pro Git](http://git-scm.com/book) is an entire book about Git with a Creative Commons license. diff --git a/guides/source/documents.yaml b/guides/source/documents.yaml index c73bbeb90d..1b16f4e516 100644 --- a/guides/source/documents.yaml +++ b/guides/source/documents.yaml @@ -36,6 +36,11 @@ name: Views documents: - + name: Action View Overview + url: action_view_overview.html + description: This guide provides an introduction to Action View and introduces a few of the more common view helpers. + work_in_progress: true + - name: Layouts and Rendering in Rails url: layouts_and_rendering.html description: This guide covers the basic layout features of Action Controller and Action View, including rendering and redirecting, using content_for blocks, and working with partials. @@ -68,7 +73,6 @@ - name: Action Mailer Basics url: action_mailer_basics.html - work_in_progress: true description: This guide describes how to use Action Mailer to send and receive emails. - name: Testing Rails Applications diff --git a/guides/source/engines.md b/guides/source/engines.md index ac76f00832..663e59b5c3 100644 --- a/guides/source/engines.md +++ b/guides/source/engines.md @@ -461,7 +461,7 @@ NOTE: Other engines, such as Devise, handle this a little differently by making The engine contains migrations for the `blorgh_posts` and `blorgh_comments` table which need to be created in the application's database so that the engine's models can query them correctly. To copy these migrations into the application use this command: ```bash -$ rake blorgh:install:migrations +$ rake blorgh_engine:install:migrations ``` If you have multiple engines that need migrations copied over, use `railties:install:migrations` instead: @@ -612,50 +612,50 @@ This section covers how to make the `User` class configurable, followed by gener #### Setting configuration settings in the application -The next step is to make the class that represents a `User` in the application customizable for the engine. This is because, as explained before, that class may not always be `User`. To make this customizable, the engine will have a configuration setting called `user_class` that will be used to specify what the class representing users is inside the application. +The next step is to make the class that represents a `User` in the application customizable for the engine. This is because, as explained before, that class may not always be `User`. To make this customizable, the engine will have a configuration setting called `author_class` that will be used to specify what the class representing users is inside the application. To define this configuration setting, you should use a `mattr_accessor` inside the `Blorgh` module for the engine, located at `lib/blorgh.rb` inside the engine. Inside this module, put this line: ```ruby -mattr_accessor :user_class +mattr_accessor :author_class ``` -This method works like its brothers `attr_accessor` and `cattr_accessor`, but provides a setter and getter method on the module with the specified name. To use it, it must be referenced using `Blorgh.user_class`. +This method works like its brothers `attr_accessor` and `cattr_accessor`, but provides a setter and getter method on the module with the specified name. To use it, it must be referenced using `Blorgh.author_class`. The next step is switching the `Blorgh::Post` model over to this new setting. For the `belongs_to` association inside this model (`app/models/blorgh/post.rb`), it will now become this: ```ruby -belongs_to :author, class_name: Blorgh.user_class +belongs_to :author, class_name: Blorgh.author_class ``` The `set_author` method also located in this class should also use this class: ```ruby -self.author = Blorgh.user_class.constantize.find_or_create_by(name: author_name) +self.author = Blorgh.author_class.constantize.find_or_create_by(name: author_name) ``` -To save having to call `constantize` on the `user_class` result all the time, you could instead just override the `user_class` getter method inside the `Blorgh` module in the `lib/blorgh.rb` file to always call `constantize` on the saved value before returning the result: +To save having to call `constantize` on the `author_class` result all the time, you could instead just override the `author_class` getter method inside the `Blorgh` module in the `lib/blorgh.rb` file to always call `constantize` on the saved value before returning the result: ```ruby -def self.user_class - @@user_class.constantize +def self.author_class + @@author_class.constantize end ``` This would then turn the above code for `set_author` into this: ```ruby -self.author = Blorgh.user_class.find_or_create_by(name: author_name) +self.author = Blorgh.author_class.find_or_create_by(name: author_name) ``` -Resulting in something a little shorter, and more implicit in its behavior. The `user_class` method should always return a `Class` object. +Resulting in something a little shorter, and more implicit in its behavior. The `author_class` method should always return a `Class` object. -Since we changed the `user_class` method to no longer return a +Since we changed the `author_class` method to no longer return a `String` but a `Class` we must also modify our `belongs_to` definition in the `Blorgh::Post` model: ```ruby -belongs_to :author, class_name: Blorgh.user_class.to_s +belongs_to :author, class_name: Blorgh.author_class.to_s ``` To set this configuration setting within the application, an initializer should be used. By using an initializer, the configuration will be set up before the application starts and calls the engine's models which may depend on this configuration setting existing. @@ -663,7 +663,7 @@ To set this configuration setting within the application, an initializer should Create a new initializer at `config/initializers/blorgh.rb` inside the application where the `blorgh` engine is installed and put this content in it: ```ruby -Blorgh.user_class = "User" +Blorgh.author_class = "User" ``` WARNING: It's very important here to use the `String` version of the class, rather than the class itself. If you were to use the class, Rails would attempt to load that class and then reference the related table, which could lead to problems if the table wasn't already existing. Therefore, a `String` should be used and then converted to a class using `constantize` in the engine later on. diff --git a/guides/source/form_helpers.md b/guides/source/form_helpers.md index 3f16ebcf1d..a4dab39d55 100644 --- a/guides/source/form_helpers.md +++ b/guides/source/form_helpers.md @@ -221,7 +221,7 @@ Upon form submission the value entered by the user will be stored in `params[:pe WARNING: You must pass the name of an instance variable, i.e. `:person` or `"person"`, not an actual instance of your model object. -Rails provides helpers for displaying the validation errors associated with a model object. These are covered in detail by the [Active Record Validations and Callbacks](./active_record_validations_callbacks.html#displaying-validation-errors-in-the-view) guide. +Rails provides helpers for displaying the validation errors associated with a model object. These are covered in detail by the [Active Record Validations](./active_record_validations.html#displaying-validation-errors-in-views) guide. ### Binding a Form to an Object @@ -836,17 +836,14 @@ Active Record provides model level support via the `accepts_nested_attributes_f class Person < ActiveRecord::Base has_many :addresses accepts_nested_attributes_for :addresses - - attr_accessible :name, :addresses_attributes end class Address < ActiveRecord::Base belongs_to :person - attr_accessible :kind, :street end ``` -This creates an `addresses_attributes=` method on `Person` that allows you to create, update and (optionally) destroy addresses. When using `attr_accessible` or `attr_protected` you must mark `addresses_attributes` as accessible as well as the other attributes of `Person` and `Address` that should be mass assigned. +This creates an `addresses_attributes=` method on `Person` that allows you to create, update and (optionally) destroy addresses. ### Building the Form diff --git a/guides/source/getting_started.md b/guides/source/getting_started.md index 3881bb1195..d49a30d02f 100644 --- a/guides/source/getting_started.md +++ b/guides/source/getting_started.md @@ -1043,7 +1043,7 @@ REST convention, so to create a new `Post` object it will look for a route named `posts_path`, and to update a `Post` object it will look for a route named `post_path` and pass the current object. Similarly, rails knows that it should create new objects via POST and update them via -PUT. +PATCH. If you run `rake routes` from the console you'll see that we already have a `posts_path` route, which was created automatically by Rails when we @@ -1054,13 +1054,13 @@ received an error before. With your server running you can view your routes by v ```bash $ rake routes - posts GET /posts(.:format) posts#index -posts_new GET /posts/new(.:format) posts#new - POST /posts(.:format) posts#create - GET /posts/:id(.:format) posts#show - GET /posts/:id/edit(.:format) posts#edit - PUT /posts/:id(.:format) posts#update - root / welcome#index + posts GET /posts(.:format) posts#index +posts_new GET /posts/new(.:format) posts#new + POST /posts(.:format) posts#create + GET /posts/:id(.:format) posts#show + GET /posts/:id/edit(.:format) posts#edit + PATCH /posts/:id(.:format) posts#update + root / welcome#index ``` To fix this, open `config/routes.rb` and modify the `get "posts/:id"` @@ -1197,6 +1197,7 @@ $ rake routes new_post GET /posts/new(.:format) posts#new edit_post GET /posts/:id/edit(.:format) posts#edit post GET /posts/:id(.:format) posts#show + PATCH /posts/:id(.:format) posts#update PUT /posts/:id(.:format) posts#update DELETE /posts/:id(.:format) posts#destroy root / welcome#index diff --git a/guides/source/i18n.md b/guides/source/i18n.md index 5304ca4285..d187d3a03a 100644 --- a/guides/source/i18n.md +++ b/guides/source/i18n.md @@ -837,6 +837,28 @@ en: NOTE: In order to use this helper, you need to install [DynamicForm](https://github.com/joelmoss/dynamic_form) gem by adding this line to your Gemfile: `gem 'dynamic_form'`. +### Translations for Action Mailer E-Mail Subjects + +If you don't pass a subject to the `mail` method, Action Mailer will try to find +it in your translations. The performed lookup will use the pattern +`<mailer_scope>.<action_name>.subject` to construct the key. + +```ruby +# user_mailer.rb +class UserMailer < ActionMailer::Base + def welcome(user) + #... + end +end +``` + +```yaml +en: + user_mailer: + welcome: + subject: "Welcome to Rails Guides!" +``` + ### Overview of Other Built-In Methods that Provide I18n Support Rails uses fixed strings and other localizations, such as format strings and other format information in a couple of helpers. Here's a brief overview. diff --git a/guides/source/layouts_and_rendering.md b/guides/source/layouts_and_rendering.md index a3b3472701..addc0a5430 100644 --- a/guides/source/layouts_and_rendering.md +++ b/guides/source/layouts_and_rendering.md @@ -1,7 +1,7 @@ Layouts and Rendering in Rails ============================== -This guide covers the basic layout features of Action Controller and Action View. By referring to this guide, you will be able to: +This guide covers the basic layout features of Action Controller and Action View. After reading this guide, you will know: @@ -319,7 +319,62 @@ render status: 500 render status: :forbidden ``` -Rails understands both numeric and symbolic status codes. +Rails understands both numeric status codes and the corresponding symbols shown below: + +| HTTP Status Code | Symbol | +| ---------------- | -------------------------------- | +| 100 | :continue | +| 101 | :switching_protocols | +| 102 | :processing | +| 200 | :ok | +| 201 | :created | +| 202 | :accepted | +| 203 | :non_authoritative_information | +| 204 | :no_content | +| 205 | :reset_content | +| 206 | :partial_content | +| 207 | :multi_status | +| 226 | :im_used | +| 300 | :multiple_choices | +| 301 | :moved_permanently | +| 302 | :found | +| 303 | :see_other | +| 304 | :not_modified | +| 305 | :use_proxy | +| 306 | :reserved | +| 307 | :temporary_redirect | +| 400 | :bad_request | +| 401 | :unauthorized | +| 402 | :payment_required | +| 403 | :forbidden | +| 404 | :not_found | +| 405 | :method_not_allowed | +| 406 | :not_acceptable | +| 407 | :proxy_authentication_required | +| 408 | :request_timeout | +| 409 | :conflict | +| 410 | :gone | +| 411 | :length_required | +| 412 | :precondition_failed | +| 413 | :request_entity_too_large | +| 414 | :request_uri_too_long | +| 415 | :unsupported_media_type | +| 416 | :requested_range_not_satisfiable | +| 417 | :expectation_failed | +| 418 | :i'm_a_teapot | +| 422 | :unprocessable_entity | +| 423 | :locked | +| 424 | :failed_dependency | +| 426 | :upgrade_required | +| 500 | :internal_server_error | +| 501 | :not_implemented | +| 502 | :bad_gateway | +| 503 | :service_unavailable | +| 504 | :gateway_timeout | +| 505 | :http_version_not_supported | +| 506 | :variant_also_negotiates | +| 507 | :insufficient_storage | +| 510 | :not_extended | ##### The `:location` Option diff --git a/guides/source/rails_application_templates.md b/guides/source/rails_application_templates.md index 77138d8871..b548eaede8 100644 --- a/guides/source/rails_application_templates.md +++ b/guides/source/rails_application_templates.md @@ -13,7 +13,7 @@ After reading this guide, you will know: Usage ----- -To apply a template, you need to provide the Rails generator with the location of the template you wish to apply, using -m option. This can either be path to a file or a URL. +To apply a template, you need to provide the Rails generator with the location of the template you wish to apply using the -m option. This can either be a path to a file or a URL. ```bash $ rails new blog -m ~/template.rb @@ -30,7 +30,7 @@ $ rake rails:template LOCATION=http://example.com/template.rb Template API ------------ -Rails templates API is very self explanatory and easy to understand. Here's an example of a typical Rails template: +The Rails templates API is easy to understand. Here's an example of a typical Rails template: ```ruby # template.rb @@ -43,7 +43,7 @@ git add: "." git commit: %Q{ -m 'Initial commit' } ``` -The following sections outlines the primary methods provided by the API: +The following sections outline the primary methods provided by the API: ### gem(*args) @@ -66,7 +66,7 @@ bundle install Wraps gem entries inside a group. -For example, if you want to load `rspec-rails` only in `development` and `test` group: +For example, if you want to load `rspec-rails` only in the `development` and `test` groups: ```ruby gem_group :development, :test do @@ -100,7 +100,7 @@ A block can be used in place of the `data` argument. Adds an initializer to the generated application’s `config/initializers` directory. -Lets say you like using `Object#not_nil?` and `Object#not_blank?`: +Let's say you like using `Object#not_nil?` and `Object#not_blank?`: ```ruby initializer 'bloatlol.rb', <<-CODE @@ -116,9 +116,9 @@ initializer 'bloatlol.rb', <<-CODE CODE ``` -Similarly `lib()` creates a file in the `lib/` directory and `vendor()` creates a file in the `vendor/` directory. +Similarly, `lib()` creates a file in the `lib/` directory and `vendor()` creates a file in the `vendor/` directory. -There is even `file()`, which accepts a relative path from `Rails.root` and creates all the directories/file needed: +There is even `file()`, which accepts a relative path from `Rails.root` and creates all the directories/files needed: ```ruby file 'app/components/foo.rb', <<-CODE @@ -127,7 +127,7 @@ file 'app/components/foo.rb', <<-CODE CODE ``` -That’ll create `app/components` directory and put `foo.rb` in there. +That’ll create the `app/components` directory and put `foo.rb` in there. ### rakefile(filename, data = nil, &block) @@ -179,7 +179,7 @@ rake "db:migrate", env: 'production' ### route(routing_code) -Adds a routing entry to the `config/routes.rb` file. In above steps, we generated a person scaffold and also removed `README.rdoc`. Now to make `PeopleController#index` as the default page for the application: +Adds a routing entry to the `config/routes.rb` file. In the steps above, we generated a person scaffold and also removed `README.rdoc`. Now, to make `PeopleController#index` the default page for the application: ```ruby route "root to: 'person#index'" @@ -197,7 +197,7 @@ end ### ask(question) -`ask()` gives you a chance to get some feedback from the user and use it in your templates. Lets say you want your user to name the new shiny library you’re adding: +`ask()` gives you a chance to get some feedback from the user and use it in your templates. Let's say you want your user to name the new shiny library you’re adding: ```ruby lib_name = ask("What do you want to call the shiny library ?") @@ -211,7 +211,7 @@ CODE ### yes?(question) or no?(question) -These methods let you ask questions from templates and decide the flow based on the user’s answer. Lets say you want to freeze rails only if the user want to: +These methods let you ask questions from templates and decide the flow based on the user’s answer. Let's say you want to freeze rails only if the user wants to: ```ruby rake("rails:freeze:gems") if yes?("Freeze rails gems?") diff --git a/guides/source/rails_on_rack.md b/guides/source/rails_on_rack.md index d8477d89e3..de8f3f483f 100644 --- a/guides/source/rails_on_rack.md +++ b/guides/source/rails_on_rack.md @@ -28,7 +28,10 @@ Rails on Rack ### Rails Application's Rack Object -`ApplicationName::Application` is the primary Rack application object of a Rails application. Any Rack compliant web server should be using `ApplicationName::Application` object to serve a Rails application. +`ApplicationName::Application` is the primary Rack application object of a Rails +application. Any Rack compliant web server should be using +`ApplicationName::Application` object to serve a Rails +application. `Rails.application` refers to the same application object. ### `rails server` @@ -79,11 +82,11 @@ To use `rackup` instead of Rails' `rails server`, you can put the following insi ```ruby # Rails.root/config.ru -require "config/environment" +require ::File.expand_path('../config/environment', __FILE__) use Rack::Debugger use Rack::ContentLength -run ApplicationName::Application +run Rails.application ``` And start the server: @@ -101,7 +104,7 @@ $ rackup --help Action Dispatcher Middleware Stack ---------------------------------- -Many of Action Dispatchers's internal components are implemented as Rack middlewares. `Rails::Application` uses `ActionDispatch::MiddlewareStack` to combine various internal and external middlewares to form a complete Rails Rack application. +Many of Action Dispatcher's internal components are implemented as Rack middlewares. `Rails::Application` uses `ActionDispatch::MiddlewareStack` to combine various internal and external middlewares to form a complete Rails Rack application. NOTE: `ActionDispatch::MiddlewareStack` is Rails equivalent of `Rack::Builder`, but built for better flexibility and more features to meet Rails' requirements. @@ -324,7 +327,7 @@ config.middleware.clear ```ruby # config.ru use MyOwnStackFromScratch -run ApplicationName::Application +run Rails.application ``` Resources @@ -332,7 +335,7 @@ Resources ### Learning Rack -* [Official Rack Website](http://rack.github.com) +* [Official Rack Website](http://rack.github.io) * [Introducing Rack](http://chneukirchen.org/blog/archive/2007/02/introducing-rack.html) * [Ruby on Rack #1 - Hello Rack!](http://m.onkey.org/ruby-on-rack-1-hello-rack) * [Ruby on Rack #2 - The Builder](http://m.onkey.org/ruby-on-rack-2-the-builder) diff --git a/guides/source/routing.md b/guides/source/routing.md index 04098f0a5c..f4cb8fe15b 100644 --- a/guides/source/routing.md +++ b/guides/source/routing.md @@ -138,6 +138,12 @@ Sometimes, you have a resource that clients always look up without referencing a get 'profile', to: 'users#show' ``` +Passing a `String` to `match` will expect a `controller#action` format, while passing a `Symbol` will map directly to an action: + +```ruby +get 'profile', to: :show +``` + This resourceful route: ```ruby diff --git a/guides/source/security.md b/guides/source/security.md index d56ce47b3c..b2d09369e2 100644 --- a/guides/source/security.md +++ b/guides/source/security.md @@ -1,4 +1,4 @@ -Ruby On Rails Security Guide +Ruby on Rails Security Guide ============================ This manual describes common security problems in web applications and how to avoid them with Rails. diff --git a/guides/source/testing.md b/guides/source/testing.md index 70061dc815..4c0a61bc5e 100644 --- a/guides/source/testing.md +++ b/guides/source/testing.md @@ -128,12 +128,12 @@ When you use `rails generate scaffold`, for a resource among other things it cre $ rails generate scaffold post title:string body:text ... create app/models/post.rb -create test/unit/post_test.rb +create test/models/post_test.rb create test/fixtures/posts.yml ... ``` -The default test stub in `test/unit/post_test.rb` looks like this: +The default test stub in `test/models/post_test.rb` looks like this: ```ruby require 'test_helper' @@ -222,10 +222,10 @@ TIP: You can see all these rake tasks and their descriptions by running `rake -- ### Running Tests -Running a test is as simple as invoking the file containing the test cases through `rails test` command. +Running a test is as simple as invoking the file containing the test cases through `rake test` command. ```bash -$ rails test test/models/post_test.rb +$ rake test test/models/post_test.rb . Finished tests in 0.009262s, 107.9680 tests/s, 107.9680 assertions/s. @@ -233,10 +233,10 @@ Finished tests in 0.009262s, 107.9680 tests/s, 107.9680 assertions/s. 1 tests, 1 assertions, 0 failures, 0 errors, 0 skips ``` -You can also run a particular test method from the test case by running the test and using `-n` switch with the `test method name`. +You can also run a particular test method from the test case by running the test and providing the `test method name`. ```bash -$ rails test test/models/post_test.rb -n test_the_truth +$ rake test test/models/post_test.rb test_the_truth . Finished tests in 0.009064s, 110.3266 tests/s, 110.3266 assertions/s. @@ -260,7 +260,7 @@ end Let us run this newly added test. ```bash -$ rails test test/models/post_test.rb -n test_should_not_save_post_without_title +$ rake test test/models/post_test.rb test_should_not_save_post_without_title F Finished tests in 0.044632s, 22.4054 tests/s, 22.4054 assertions/s. @@ -300,7 +300,7 @@ end Now the test should pass. Let us verify by running the test again: ```bash -$ rails test test/models/post_test.rb -n test_should_not_save_post_without_title +$ rake test test/models/post_test.rb test_should_not_save_post_without_title . Finished tests in 0.047721s, 20.9551 tests/s, 20.9551 assertions/s. @@ -325,7 +325,7 @@ end Now you can see even more output in the console from running the tests: ```bash -$ rails test test/models/post_test.rb -n test_should_report_error +$ rake test test/models/post_test.rb test_should_report_error E Finished tests in 0.030974s, 32.2851 tests/s, 0.0000 assertions/s. @@ -714,17 +714,17 @@ class UserFlowsTest < ActionDispatch::IntegrationTest test "login and browse site" do - # User avs logs in - avs = login(:david) + # User david logs in + david = login(:david) # User guest logs in guest = login(:guest) # Both are now available in different sessions - assert_equal 'Welcome david!', avs.flash[:notice] + assert_equal 'Welcome david!', david.flash[:notice] assert_equal 'Welcome guest!', guest.flash[:notice] - # User avs can browse site - avs.browses_site + # User david can browse site + david.browses_site # User guest can browse site as well guest.browses_site @@ -761,14 +761,14 @@ You don't need to set up and run your tests by hand on a test-by-test basis. Rai | Tasks | Description | | ------------------------ | ----------- | -| `rails test` | Runs all unit, functional and integration tests. You can also simply run `rails test` as Rails will run all the tests by default| -| `rails test controllers` | Runs all the controller tests from `test/controllers`| -| `rails test functionals` | Runs all the functional tests from `test/controllers`, `test/mailers`, and `test/functional`| -| `rails test helpers` | Runs all the helper tests from `test/helpers`| -| `rails test integration` | Runs all the integration tests from `test/integration`| -| `rails test mailers` | Runs all the mailer tests from `test/mailers`| -| `rails test models` | Runs all the model tests from `test/models`| -| `rails test units` | Runs all the unit tests from `test/models`, `test/helpers`, and `test/unit`| +| `rake test` | Runs all unit, functional and integration tests. You can also simply run `rake test` as Rails will run all the tests by default| +| `rake test:controllers` | Runs all the controller tests from `test/controllers`| +| `rake test:functionals` | Runs all the functional tests from `test/controllers`, `test/mailers`, and `test/functional`| +| `rake test:helpers` | Runs all the helper tests from `test/helpers`| +| `rake test:integration` | Runs all the integration tests from `test/integration`| +| `rake test:mailers` | Runs all the mailer tests from `test/mailers`| +| `rake test:models` | Runs all the model tests from `test/models`| +| `rake test:units` | Runs all the unit tests from `test/models`, `test/helpers`, and `test/unit`| There're also some test commands which you can initiate by running rake tasks: diff --git a/guides/source/upgrading_ruby_on_rails.md b/guides/source/upgrading_ruby_on_rails.md index a8182617f3..51d6775c3e 100644 --- a/guides/source/upgrading_ruby_on_rails.md +++ b/guides/source/upgrading_ruby_on_rails.md @@ -71,7 +71,7 @@ Rails 4.0 extracted Active Resource to its own gem. If you still need the featur * Rails 4.0 has changed how errors attach with the `ActiveModel::Validations::ConfirmationValidator`. Now when confirmation validations fail, the error will be attached to `:#{attribute}_confirmation` instead of `attribute`. -* Rails 4.0 has changed `ActiveModel::Serializers::JSON.include_root_in_json` default value to `false`. Now, Active Model Serializers and Active Record objects have the same default behavior. This means that you can comment or remove the following option in the `config/initializers/wrap_parameters.rb` file: +* Rails 4.0 has changed `ActiveModel::Serializers::JSON.include_root_in_json` default value to `false`. Now, Active Model Serializers and Active Record objects have the same default behaviour. This means that you can comment or remove the following option in the `config/initializers/wrap_parameters.rb` file: ```ruby # Disable root element in JSON by default. @@ -320,7 +320,7 @@ config.assets.debug = true Again, most of the changes below are for the asset pipeline. You can read more about these in the [Asset Pipeline](asset_pipeline.html) guide. ```ruby -# Compress JavaScript and CSS +# Compress JavaScripts and CSS config.assets.compress = true # Don't fallback to assets pipeline if a precompiled asset is missed |