aboutsummaryrefslogtreecommitdiffstats
path: root/railties/guides
diff options
context:
space:
mode:
Diffstat (limited to 'railties/guides')
-rw-r--r--railties/guides/assets/images/rails_guides_kindle_cover.jpgbin0 -> 31785 bytes
-rw-r--r--railties/guides/assets/stylesheets/kindle.css11
-rw-r--r--railties/guides/assets/stylesheets/main.css8
-rw-r--r--railties/guides/code/getting_started/README.rdoc (renamed from railties/guides/code/getting_started/README)0
-rw-r--r--railties/guides/code/getting_started/app/views/layouts/application.html.erb2
-rw-r--r--railties/guides/code/getting_started/config/application.rb5
-rw-r--r--railties/guides/code/getting_started/config/environments/development.rb10
-rw-r--r--railties/guides/code/getting_started/config/environments/production.rb4
-rw-r--r--railties/guides/code/getting_started/config/environments/test.rb8
-rw-r--r--railties/guides/rails_guides/generator.rb109
-rw-r--r--railties/guides/rails_guides/helpers.rb8
-rw-r--r--railties/guides/rails_guides/levenshtein.rb2
-rw-r--r--railties/guides/source/3_2_release_notes.textile443
-rw-r--r--railties/guides/source/_license.html.erb2
-rw-r--r--railties/guides/source/_welcome.html.erb19
-rw-r--r--railties/guides/source/action_controller_overview.textile2
-rw-r--r--railties/guides/source/action_mailer_basics.textile15
-rw-r--r--railties/guides/source/active_record_basics.textile4
-rw-r--r--railties/guides/source/active_record_querying.textile78
-rw-r--r--railties/guides/source/active_support_core_extensions.textile213
-rw-r--r--railties/guides/source/asset_pipeline.textile16
-rw-r--r--railties/guides/source/caching_with_rails.textile30
-rw-r--r--railties/guides/source/command_line.textile26
-rw-r--r--railties/guides/source/configuring.textile13
-rw-r--r--railties/guides/source/contributing_to_ruby_on_rails.textile4
-rw-r--r--railties/guides/source/debugging_rails_applications.textile2
-rw-r--r--railties/guides/source/documents.yaml153
-rw-r--r--railties/guides/source/form_helpers.textile2
-rw-r--r--railties/guides/source/generators.textile2
-rw-r--r--railties/guides/source/getting_started.textile25
-rw-r--r--railties/guides/source/i18n.textile4
-rw-r--r--railties/guides/source/index.html.erb189
-rw-r--r--railties/guides/source/initialization.textile22
-rw-r--r--railties/guides/source/kindle/KINDLE.md26
-rw-r--r--railties/guides/source/kindle/copyright.html.erb1
-rw-r--r--railties/guides/source/kindle/layout.html.erb27
-rw-r--r--railties/guides/source/kindle/rails_guides.opf.erb52
-rw-r--r--railties/guides/source/kindle/toc.html.erb24
-rw-r--r--railties/guides/source/kindle/toc.ncx.erb64
-rw-r--r--railties/guides/source/kindle/welcome.html.erb5
-rw-r--r--railties/guides/source/layout.html.erb3
-rw-r--r--railties/guides/source/layouts_and_rendering.textile63
-rw-r--r--railties/guides/source/migrations.textile533
-rw-r--r--railties/guides/source/performance_testing.textile2
-rw-r--r--railties/guides/source/rails_on_rack.textile1
-rw-r--r--railties/guides/source/routing.textile2
-rw-r--r--railties/guides/source/testing.textile2
47 files changed, 1609 insertions, 627 deletions
diff --git a/railties/guides/assets/images/rails_guides_kindle_cover.jpg b/railties/guides/assets/images/rails_guides_kindle_cover.jpg
new file mode 100644
index 0000000000..9eb16720a9
--- /dev/null
+++ b/railties/guides/assets/images/rails_guides_kindle_cover.jpg
Binary files differ
diff --git a/railties/guides/assets/stylesheets/kindle.css b/railties/guides/assets/stylesheets/kindle.css
new file mode 100644
index 0000000000..b26cd1786a
--- /dev/null
+++ b/railties/guides/assets/stylesheets/kindle.css
@@ -0,0 +1,11 @@
+p { text-indent: 0; }
+
+p, H1, H2, H3, H4, H5, H6, H7, H8, table { margin-top: 1em;}
+
+.pagebreak { page-break-before: always; }
+#toc H3 {
+ text-indent: 1em;
+}
+#toc .document {
+ text-indent: 2em;
+} \ No newline at end of file
diff --git a/railties/guides/assets/stylesheets/main.css b/railties/guides/assets/stylesheets/main.css
index cf6e9e5cc8..4a775f632c 100644
--- a/railties/guides/assets/stylesheets/main.css
+++ b/railties/guides/assets/stylesheets/main.css
@@ -341,6 +341,14 @@ h6 {
margin-top: 0.25em;
}
+#mainCol dd.kindle, #subCol dd.kindle {
+ background: #d5e9f6 url(../images/tab_info.gif) no-repeat left top;
+ border: none;
+ padding: 1.25em 1em 1.25em 48px;
+ margin-left: 0;
+ margin-top: 0.25em;
+}
+
#mainCol div.warning, #subCol dd.warning {
background: #f9d9d8 url(../images/tab_red.gif) no-repeat left top;
border: none;
diff --git a/railties/guides/code/getting_started/README b/railties/guides/code/getting_started/README.rdoc
index 7c36f2356e..7c36f2356e 100644
--- a/railties/guides/code/getting_started/README
+++ b/railties/guides/code/getting_started/README.rdoc
diff --git a/railties/guides/code/getting_started/app/views/layouts/application.html.erb b/railties/guides/code/getting_started/app/views/layouts/application.html.erb
index 1e1e4b9a99..7fd6b4f516 100644
--- a/railties/guides/code/getting_started/app/views/layouts/application.html.erb
+++ b/railties/guides/code/getting_started/app/views/layouts/application.html.erb
@@ -2,7 +2,7 @@
<html>
<head>
<title>Blog</title>
- <%= stylesheet_link_tag "application" %>
+ <%= stylesheet_link_tag "application", :media => "all" %>
<%= javascript_include_tag "application" %>
<%= csrf_meta_tags %>
</head>
diff --git a/railties/guides/code/getting_started/config/application.rb b/railties/guides/code/getting_started/config/application.rb
index e914b5a80e..e16da30f72 100644
--- a/railties/guides/code/getting_started/config/application.rb
+++ b/railties/guides/code/getting_started/config/application.rb
@@ -39,6 +39,11 @@ module Blog
# Configure sensitive parameters which will be filtered from the log file.
config.filter_parameters += [:password]
+ # Use SQL instead of Active Record's schema dumper when creating the database.
+ # This is necessary if your schema can't be completely dumped by the schema dumper,
+ # like if you have constraints or database-specific column types
+ # config.active_record.schema_format = :sql
+
# Enable the asset pipeline
config.assets.enabled = true
diff --git a/railties/guides/code/getting_started/config/environments/development.rb b/railties/guides/code/getting_started/config/environments/development.rb
index 89932bf19b..aefd25c6b6 100644
--- a/railties/guides/code/getting_started/config/environments/development.rb
+++ b/railties/guides/code/getting_started/config/environments/development.rb
@@ -6,9 +6,6 @@ Blog::Application.configure do
# since you don't have to restart the web server when you make code changes.
config.cache_classes = false
- # Log error messages when you accidentally call methods on nil.
- config.whiny_nils = true
-
# Show full error reports and disable caching
config.consider_all_requests_local = true
config.action_controller.perform_caching = false
@@ -22,6 +19,13 @@ Blog::Application.configure do
# Only use best-standards-support built into browsers
config.action_dispatch.best_standards_support = :builtin
+ # Raise exception on mass assignment protection for ActiveRecord models
+ config.active_record.mass_assignment_sanitizer = :strict
+
+ # Log the query plan for queries taking more than this (works
+ # with SQLite, MySQL, and PostgreSQL)
+ config.active_record.auto_explain_threshold_in_seconds = 0.5
+
# Do not compress assets
config.assets.compress = false
diff --git a/railties/guides/code/getting_started/config/environments/production.rb b/railties/guides/code/getting_started/config/environments/production.rb
index dee8acfdfe..c9b2f41c39 100644
--- a/railties/guides/code/getting_started/config/environments/production.rb
+++ b/railties/guides/code/getting_started/config/environments/production.rb
@@ -60,4 +60,8 @@ Blog::Application.configure do
# Send deprecation notices to registered listeners
config.active_support.deprecation = :notify
+
+ # Log the query plan for queries taking more than this (works
+ # with SQLite, MySQL, and PostgreSQL)
+ # config.active_record.auto_explain_threshold_in_seconds = 0.5
end
diff --git a/railties/guides/code/getting_started/config/environments/test.rb b/railties/guides/code/getting_started/config/environments/test.rb
index 833241ace3..1d45541d5c 100644
--- a/railties/guides/code/getting_started/config/environments/test.rb
+++ b/railties/guides/code/getting_started/config/environments/test.rb
@@ -11,9 +11,6 @@ Blog::Application.configure do
config.serve_static_assets = true
config.static_cache_control = "public, max-age=3600"
- # Log error messages when you accidentally call methods on nil
- config.whiny_nils = true
-
# Show full error reports and disable caching
config.consider_all_requests_local = true
config.action_controller.perform_caching = false
@@ -29,11 +26,6 @@ Blog::Application.configure do
# ActionMailer::Base.deliveries array.
config.action_mailer.delivery_method = :test
- # Use SQL instead of Active Record's schema dumper when creating the test database.
- # This is necessary if your schema can't be completely dumped by the schema dumper,
- # like if you have constraints or database-specific column types
- # config.active_record.schema_format = :sql
-
# Print deprecation notices to the stderr
config.active_support.deprecation = :stderr
diff --git a/railties/guides/rails_guides/generator.rb b/railties/guides/rails_guides/generator.rb
index 6f6d3bda80..49ad8f7769 100644
--- a/railties/guides/rails_guides/generator.rb
+++ b/railties/guides/rails_guides/generator.rb
@@ -47,6 +47,11 @@
# Set to "1" to indicate generated guides should be marked as edge. This
# inserts a badge and changes the preamble of the home page.
#
+# KINDLE
+# Set to "1" to generate the .mobi with all the guides. The kindlegen
+# executable must be in your PATH. You can get it for free from
+# http://www.amazon.com/kindlepublishing
+#
# ---------------------------------------------------------------------------
require 'set'
@@ -65,37 +70,81 @@ module RailsGuides
class Generator
attr_reader :guides_dir, :source_dir, :output_dir, :edge, :warnings, :all
- GUIDES_RE = /\.(?:textile|html\.erb)$/
+ GUIDES_RE = /\.(?:textile|erb)$/
def initialize(output=nil)
- @lang = ENV['GUIDES_LANGUAGE']
+ set_flags_from_environment
+
+ if kindle?
+ check_for_kindlegen
+ register_kindle_mime_types
+ end
+
initialize_dirs(output)
create_output_dir_if_needed
- set_flags_from_environment
+ end
+
+ def set_flags_from_environment
+ @edge = ENV['EDGE'] == '1'
+ @warnings = ENV['WARNINGS'] == '1'
+ @all = ENV['ALL'] == '1'
+ @kindle = ENV['KINDLE'] == '1'
+ @version = ENV['RAILS_VERSION'] || `git rev-parse --short HEAD`.chomp
+ @lang = ENV['GUIDES_LANGUAGE']
+ end
+
+ def register_kindle_mime_types
+ Mime::Type.register_alias("application/xml", :opf, %w(opf))
+ Mime::Type.register_alias("application/xml", :ncx, %w(ncx))
end
def generate
generate_guides
copy_assets
+ generate_mobi if kindle?
end
private
+
+ def kindle?
+ @kindle
+ end
+
+ def check_for_kindlegen
+ if `which kindlegen`.blank?
+ raise "Can't create a kindle version without `kindlegen`."
+ end
+ end
+
+ def generate_mobi
+ opf = "#{output_dir}/rails_guides.opf"
+ out = "#{output_dir}/kindlegen.out"
+
+ system "kindlegen #{opf} -o #{mobi} > #{out} 2>&1"
+ puts "Guides compiled as Kindle book to #{mobi}"
+ puts "(kindlegen log at #{out})."
+ end
+
+ def mobi
+ "ruby_on_rails_guides_#@version%s.mobi" % (@lang.present? ? ".#@lang" : '')
+ end
+
def initialize_dirs(output)
@guides_dir = File.join(File.dirname(__FILE__), '..')
- @source_dir = File.join(@guides_dir, "source", @lang.to_s)
- @output_dir = output || File.join(@guides_dir, "output", @lang.to_s)
+ @source_dir = "#@guides_dir/source/#@lang"
+ @output_dir = if output
+ output
+ elsif kindle?
+ "#@guides_dir/output/kindle/#@lang"
+ else
+ "#@guides_dir/output/#@lang"
+ end.sub(%r</$>, '')
end
def create_output_dir_if_needed
FileUtils.mkdir_p(output_dir)
end
- def set_flags_from_environment
- @edge = ENV['EDGE'] == '1'
- @warnings = ENV['WARNINGS'] == '1'
- @all = ENV['ALL'] == '1'
- end
-
def generate_guides
guides_to_generate.each do |guide|
output_file = output_file_for(guide)
@@ -105,6 +154,13 @@ module RailsGuides
def guides_to_generate
guides = Dir.entries(source_dir).grep(GUIDES_RE)
+
+ if kindle?
+ Dir.entries("#{source_dir}/kindle").grep(GUIDES_RE).map do |entry|
+ guides << "kindle/#{entry}"
+ end
+ end
+
ENV.key?('ONLY') ? select_only(guides) : guides
end
@@ -120,36 +176,47 @@ module RailsGuides
end
def output_file_for(guide)
- guide.sub(GUIDES_RE, '.html')
+ if guide =~/\.textile$/
+ guide.sub(/\.textile$/, '.html')
+ else
+ guide.sub(/\.erb$/, '')
+ end
+ end
+
+ def output_path_for(output_file)
+ File.join(output_dir, File.basename(output_file))
end
def generate?(source_file, output_file)
fin = File.join(source_dir, source_file)
- fout = File.join(output_dir, output_file)
+ fout = output_path_for(output_file)
all || !File.exists?(fout) || File.mtime(fout) < File.mtime(fin)
end
def generate_guide(guide, output_file)
- puts "Generating #{output_file}"
- File.open(File.join(output_dir, output_file), 'w') do |f|
- view = ActionView::Base.new(source_dir, :edge => edge)
+ output_path = output_path_for(output_file)
+ puts "Generating #{guide} as #{output_file}"
+ layout = kindle? ? 'kindle/layout' : 'layout'
+
+ File.open(output_path, 'w') do |f|
+ view = ActionView::Base.new(source_dir, :edge => @edge, :version => @version, :mobi => "kindle/#{mobi}")
view.extend(Helpers)
- if guide =~ /\.html\.erb$/
+ if guide =~ /\.(\w+)\.erb$/
# Generate the special pages like the home.
# Passing a template handler in the template name is deprecated. So pass the file name without the extension.
- result = view.render(:layout => 'layout', :file => $`)
+ result = view.render(:layout => layout, :formats => [$1], :file => $`)
else
body = File.read(File.join(source_dir, guide))
body = set_header_section(body, view)
body = set_index(body, view)
- result = view.render(:layout => 'layout', :text => textile(body))
+ result = view.render(:layout => layout, :text => textile(body))
warn_about_broken_links(result) if @warnings
end
- f.write result
+ f.write(result)
end
end
@@ -216,7 +283,7 @@ module RailsGuides
anchors = Set.new
html.scan(/<h\d\s+id="([^"]+)/).flatten.each do |anchor|
if anchors.member?(anchor)
- puts "*** DUPLICATE ID: #{anchor}, please put and explicit ID, e.g. h4(#explicit-id), or consider rewording"
+ puts "*** DUPLICATE ID: #{anchor}, please use an explicit ID, e.g. h4(#explicit-id), or consider rewording"
else
anchors << anchor
end
diff --git a/railties/guides/rails_guides/helpers.rb b/railties/guides/rails_guides/helpers.rb
index 463df8a7a8..45ad9b9588 100644
--- a/railties/guides/rails_guides/helpers.rb
+++ b/railties/guides/rails_guides/helpers.rb
@@ -11,6 +11,14 @@ module RailsGuides
result << content_tag(:dd, capture(&block))
result
end
+
+ def documents_by_section
+ @documents_by_section ||= YAML.load_file(File.expand_path('../../source/documents.yaml', __FILE__))
+ end
+
+ def documents_flat
+ documents_by_section.map {|section| section['documents']}.flatten
+ end
def author(name, nick, image = 'credits_pic_blank.gif', &block)
image = "images/#{image}"
diff --git a/railties/guides/rails_guides/levenshtein.rb b/railties/guides/rails_guides/levenshtein.rb
index f99c6e6ba8..489aa3ea7a 100644
--- a/railties/guides/rails_guides/levenshtein.rb
+++ b/railties/guides/rails_guides/levenshtein.rb
@@ -1,6 +1,6 @@
module RailsGuides
module Levenshtein
- # Based on the pseudocode in http://en.wikipedia.org/wiki/Levenshtein_distance.
+ # Based on the pseudocode in http://en.wikipedia.org/wiki/Levenshtein_distance
def self.distance(s1, s2)
s = s1.unpack('U*')
t = s2.unpack('U*')
diff --git a/railties/guides/source/3_2_release_notes.textile b/railties/guides/source/3_2_release_notes.textile
new file mode 100644
index 0000000000..c1afee004e
--- /dev/null
+++ b/railties/guides/source/3_2_release_notes.textile
@@ -0,0 +1,443 @@
+h2. Ruby on Rails 3.2 Release Notes
+
+Highlights in Rails 3.2:
+
+* Faster Development Mode
+* New Routing Engine
+* Automatic Query Explains
+* Tagged Logging
+
+These release notes cover the major changes, but don't include every little bug fix and change. If you want to see everything, check out the "list of commits":https://github.com/rails/rails/commits/3-2-stable in the main Rails repository on GitHub.
+
+endprologue.
+
+h3. Upgrading to Rails 3.2
+
+If you're upgrading an existing application, it's a great idea to have good test coverage before going in. You should also first upgrade to Rails 3.1 in case you haven't and make sure your application still runs as expected before attempting to update to Rails 3.2. Then take heed of the following changes:
+
+h4. Rails 3.2 requires at least Ruby 1.8.7
+
+Rails 3.2 requires Ruby 1.8.7 or higher. Support for all of the previous Ruby versions has been dropped officially and you should upgrade as early as possible. Rails 3.2 is also compatible with Ruby 1.9.2.
+
+TIP: Note that Ruby 1.8.7 p248 and p249 have marshaling bugs that crash Rails. Ruby Enterprise Edition have these fixed since release 1.8.7-2010.02. On the 1.9 front, Ruby 1.9.1 is not usable because it outright segfaults, so if you want to use 1.9.x, jump on 1.9.2 or 1.9.3 for smooth sailing.
+
+h3. Creating a Rails 3.2 application
+
+<shell>
+# You should have the 'rails' rubygem installed
+$ rails new myapp
+$ cd myapp
+</shell>
+
+h4. Vendoring Gems
+
+Rails now uses a +Gemfile+ in the application root to determine the gems you require for your application to start. This +Gemfile+ is processed by the "Bundler":https://github.com/carlhuda/bundler gem, which then installs all your dependencies. It can even install all the dependencies locally to your application so that it doesn't depend on the system gems.
+
+More information: - "Bundler homepage":http://gembundler.com
+
+h4. Living on the Edge
+
++Bundler+ and +Gemfile+ makes freezing your Rails application easy as pie with the new dedicated +bundle+ command. If you want to bundle straight from the Git repository, you can pass the +--edge+ flag:
+
+<shell>
+$ rails new myapp --edge
+</shell>
+
+If you have a local checkout of the Rails repository and want to generate an application using that, you can pass the +--dev+ flag:
+
+<shell>
+$ ruby /path/to/rails/bin/rails new myapp --dev
+</shell>
+
+h3. Major Features
+
+h4. Faster Development Mode & Routing
+
+Rails 3.2 comes with a development mode that's noticeably faster. Inspired by "Active Reload":https://github.com/paneq/active_reload, Rails reloads classes only when files actually change. The performance gains are dramatic on a larger application. Route recognition also got a bunch faster thanks to the new "Journey":https://github.com/rails/journey engine.
+
+h4. Automatic Query Explains
+
+Rails 3.2 comes with a nice feature that explains queries generated by ARel by defining an +explain+ method in <tt>ActiveRecord::Relation</tt>. For example, you can run something like <tt>puts Person.active.limit(5).explain</tt> and the query ARel produces is explained. This allows to check for the proper indexes and further optimizations.
+
+Queries that take more than half a second to run are *automatically* explained in the development mode. This threshold, of course, can be changed.
+
+h4. Tagged Logging
+
+When running a multi-user, multi-account application, it's a great help to be able to filter the log by who did what. TaggedLogging in Active Support helps in doing exactly that by stamping log lines with subdomains, request ids, and anything else to aid debugging of such applications.
+
+h3. Railties
+
+* Speed up development by only reloading classes if dependencies files changed. This can be turned off by setting <tt>config.reload_classes_only_on_change</tt> to false.
+
+* New applications get a flag <tt>config.active_record.auto_explain_threshold_in_seconds</tt> in the environments configuration files. With a value of <tt>0.5</tt> in <tt>development.rb</tt> and commented out in <tt>production.rb</tt>. No mention in <tt>test.rb</tt>.
+
+* Added <tt>config.exceptions_app</tt> to set the exceptions application invoked by the +ShowException+ middleware when an exception happens. Defaults to <tt>ActionDispatch::PublicExceptions.new(Rails.public_path)</tt>.
+
+* Added a <tt>DebugExceptions</tt> middleware which contains features extracted from <tt>ShowExceptions</tt> middleware.
+
+* Display mounted engines' routes in <tt>rake routes</tt>.
+
+* Allow to change the loading order of railties with <tt>config.railties_order</tt> like:
+
+<ruby>
+config.railties_order = [Blog::Engine, :main_app, :all]
+</ruby>
+
+* Scaffold returns 204 No Content for API requests without content. This makes scaffold work with jQuery out of the box.
+
+* Update Rails::Rack::Logger middleware to apply any tags set in config.log_tags to the newly ActiveSupport::TaggedLogging Rails.logger. This makes it easy to tag log lines with debug information like subdomain and request id -- both very helpful in debugging multi-user production applications
+
+* Default options to +rails new+ can be set in <tt>~/.railsrc</tt>.
+
+* Add an alias +d+ for +destroy+. This works for engines too.
+
+* Attributes on scaffold and model generators default to string. This allows the following: <tt>rails g scaffold Post title body:text author</tt>
+
+* Allow scaffold/model/migration generators to accept "index" and "uniq" modifiers. For example,
+
+<ruby>
+rails g scaffold Post title:string:index author:uniq price:decimal{7,2}
+</ruby>
+
+will create indexes for +title+ and +author+ with the latter being an unique index. Some types such as decimal accept custom options. In the example, +price+ will be a decimal column with precision and scale set to 7 and 2 respectively.
+
+* Remove old plugin generator +rails generate plugin+ in favor of +rails plugin new+ command.
+
+* Remove old <tt>config.paths.app.controller</tt> API in favor of <tt>config.paths["app/controller"]</tt>.
+
+h3. Action Pack
+
+h4. Action Controller
+
+* Make <tt>ActiveSupport::Benchmarkable</tt> a default module for <tt>ActionController::Base,</tt> so the <tt>#benchmark</tt> method is once again available in the controller context like it used to be.
+
+* Added +:gzip+ option to +caches_page+. The default option can be configured globally using <tt>page_cache_compression</tt>.
+
+* Rails will now use your default layout (such as "layouts/application") when you specify a layout with <tt>:only</tt> and <tt>:except</tt> condition, and those conditions fail.
+
+<ruby>
+class CarsController
+ layout 'single_car', :only => :show
+end
+</ruby>
+
+Rails will use 'layouts/single_car' when a request comes in :show action, and use 'layouts/application' (or 'layouts/cars', if exists) when a request comes in for any other actions.
+
+* form_for is changed to use "#{action}_#{as}" as the css class and id if +:as+ option is provided. Earlier versions used "#{as}_#{action}".
+
+* <tt>ActionController::ParamsWrapper</tt> on ActiveRecord models now only wrap <tt>attr_accessible</tt> attributes if they were set. If not, only the attributes returned by the class method +attribute_names+ will be wrapped. This fixes the wrapping of nested attributes by adding them to +attr_accessible+.
+
+* Log "Filter chain halted as CALLBACKNAME rendered or redirected" every time a before callback halts.
+
+* <tt>ActionDispatch::ShowExceptions</tt> is refactored. The controller is responsible for choosing to show exceptions. It's possible to override +show_detailed_exceptions?+ in controllers to specify which requests should provide debugging information on errors.
+
+* Responders now return 204 No Content for API requests without a response body (as in the new scaffold).
+
+* <tt>ActionController::TestCase</tt> cookies is refactored. Assigning cookies for test cases should now use <tt>cookies[]</tt>
+
+<ruby>
+cookies[:email] = 'user@example.com'
+get :index
+assert_equal 'user@example.com', cookies[:email]
+</ruby>
+
+To clear the cookies, use +clear+.
+
+<ruby>
+cookies.clear
+get :index
+assert_nil cookies[:email]
+</ruby>
+
+We now no longer write out HTTP_COOKIE and the cookie jar is persistent between requests so if you need to manipulate the environment for your test you need to do it before the cookie jar is created.
+
+* <tt>send_file</tt> now guesses the MIME type from the file extension if +:type+ is not provided.
+
+* MIME type entries for PDF, ZIP and other formats were added.
+
+* Allow fresh_when/stale? to take a record instead of an options hash.
+
+* Changed log level of warning for missing CSRF token from <tt>:debug</tt> to <tt>:warn</tt>.
+
+* Assets should use the request protocol by default or default to relative if no request is available.
+
+h5. Deprecations
+
+* Deprecated implied layout lookup in controllers whose parent had a explicit layout set:
+
+<ruby>
+class ApplicationController
+ layout "application"
+end
+
+class PostsController < ApplicationController
+end
+</ruby>
+
+In the example above, Posts controller will no longer automatically look up for a posts layout. If you need this functionality you could either remove <tt>layout "application"</tt> from +ApplicationController+ or explicitly set it to +nil+ in +PostsController+.
+
+h4. Action Dispatch
+
+* Added <tt>ActionDispatch::RequestId</tt> middleware that'll make a unique X-Request-Id header available to the response and enables the <tt>ActionDispatch::Request#uuid</tt> method. This makes it easy to trace requests from end-to-end in the stack and to identify individual requests in mixed logs like Syslog.
+
+* The <tt>ShowExceptions</tt> middleware now accepts a exceptions application that is responsible to render an exception when the application fails. The application is invoked with a copy of the exception in +env["action_dispatch.exception"]+ and with the <tt>PATH_INFO</tt> rewritten to the status code.
+
+* Allow rescue responses to be configured through a railtie as in <tt>config.action_dispatch.rescue_responses</tt>.
+
+h4. Action View
+
+* Add +button_tag+ support to <tt>ActionView::Helpers::FormBuilder</tt>. This support mimics the default behavior of +submit_tag+.
+
+<ruby>
+<%= form_for @post do |f| %>
+ <%= f.button %>
+<% end %>
+</ruby>
+
+* Date helpers accept a new option <tt>:use_two_digit_numbers => true</tt>, that renders select boxes for months and days with a leading zero without changing the respective values. For example, this is useful for displaying ISO8601-style dates such as '2011-08-01'.
+
+* You can provide a namespace for your form to ensure uniqueness of id attributes on form elements. The namespace attribute will be prefixed with underscore on the generated HTML id.
+
+<ruby>
+<%= form_for(@offer, :namespace => 'namespace') do |f| %>
+ <%= f.label :version, 'Version' %>:
+ <%= f.text_field :version %>
+<% end %>
+</ruby>
+
+* Limit the number of options for +select_year+ to 1000. Pass +:max_years_allowed+ option to set your own limit.
+
+* +content_tag_for+ and +div_for+ can now take a collection of records. It will also yield the record as the first argument if you set a receiving argument in your block. So instead of having to do this:
+
+<ruby>
+@items.each do |item|
+ content_tag_for(:li, item) do
+ Title: <%= item.title %>
+ end
+end
+</ruby>
+
+You can do this:
+
+<ruby>
+content_tag_for(:li, @items) do |item|
+ Title: <%= item.title %>
+end
+</ruby>
+
+h5. Deprecations
+
+* Passing formats or handlers to render :template and friends like <tt>render :template => "foo.html.erb"</tt> is deprecated. Instead, you can provide :handlers and :formats directly as an options: <tt> render :template => "foo", :formats => [:html, :js], :handlers => :erb</tt>.
+
+h3. Active Record
+
+* Implemented <tt>ActiveRecord::Relation#explain</tt>.
+
+* Implements <tt>AR::Base.silence_auto_explain</tt> which allows the user to selectively disable automatic EXPLAINs within a block.
+
+* Implements automatic EXPLAIN logging for slow queries. A new configuration parameter +config.active_record.auto_explain_threshold_in_seconds+ determines what's to be considered a slow query. Setting that to nil disables this feature. Defaults are 0.5 in development mode, and nil in test and production modes. As of this writing there's support for SQLite, MySQL (mysql2 adapter), and PostgreSQL.
+
+* Added <tt>ActiveRecord::Base.store</tt> for declaring simple single-column key/value stores.
+
+<ruby>
+class User < ActiveRecord::Base
+ store :settings, accessors: [ :color, :homepage ]
+end
+
+u = User.new(color: 'black', homepage: '37signals.com')
+u.color # Accessor stored attribute
+u.settings[:country] = 'Denmark' # Any attribute, even if not specified with an accessor
+</ruby>
+
+* Added ability to run migrations only for a given scope, which allows to run migrations only from one engine (for example to revert changes from an engine that need to be removed).
+
+<ruby>
+rake db:migrate SCOPE=blog
+</ruby>
+
+* Migrations copied from engines are now scoped with engine's name, for example <tt>01_create_posts.blog.rb</tt>.
+
+* Implemented <tt>ActiveRecord::Relation#pluck</tt> method that returns an array of column values directly from the underlying table. This also works with serialized attributes.
+
+<ruby>
+Client.where(:active => true).pluck(:id)
+# SELECT id from clients where active = 1
+</ruby>
+
+* Generated association methods are created within a separate module to allow overriding and composition. For a class named MyModel, the module is named <tt>MyModel::GeneratedFeatureMethods</tt>. It is included into the model class immediately after the +generated_attributes_methods+ module defined in Active Model, so association methods override attribute methods of the same name.
+
+* Add <tt>ActiveRecord::Relation#uniq</tt> for generating unique queries.
+
+<ruby>
+Client.select('DISTINCT name')
+</ruby>
+
+..can be written as:
+
+<ruby>
+Client.select(:name).uniq
+</ruby>
+
+This also allows you to revert the uniqueness in a relation:
+
+<ruby>
+Client.select(:name).uniq.uniq(false)
+</ruby>
+
+* Support index sort order in SQLite, MySQL and PostgreSQL adapters.
+
+* Allow the +:class_name+ option for associations to take a symbol in addition to a string. This is to avoid confusing newbies, and to be consistent with the fact that other options like :foreign_key already allow a symbol or a string.
+
+<ruby>
+has_many :clients, :class_name => :Client # Note that the symbol need to be capitalized
+</ruby>
+
+* In development mode, <tt>db:drop</tt> also drops the test database in order to be symmetric with <tt>db:create</tt>.
+
+* Case-insensitive uniqueness validation avoids calling LOWER in MySQL when the column already uses a case-insensitive collation.
+
+* Transactional fixtures enlist all active database connections. You can test models on different connections without disabling transactional fixtures.
+
+* Add +first_or_create+, +first_or_create!+, +first_or_initialize+ methods to Active Record. This is a better approach over the old +find_or_create_by+ dynamic methods because it's clearer which arguments are used to find the record and which are used to create it.
+
+<ruby>
+User.where(:first_name => "Scarlett").first_or_create!(:last_name => "Johansson")
+</ruby>
+
+h4. Deprecations
+
+* Automatic closure of connections in threads is deprecated. For example the following code is deprecated:
+
+<ruby>
+Thread.new { Post.find(1) }.join
+</ruby>
+
+It should be changed to close the database connection at the end of the thread:
+
+<ruby>
+Thread.new {
+ Post.find(1)
+ Post.connection.close
+}.join
+</ruby>
+
+Only people who spawn threads in their application code need to worry about this change.
+
+* The +set_table_name+, +set_inheritance_column+, +set_sequence_name+, +set_primary_key+, +set_locking_column+ methods are deprecated. Use an assignment method instead. For example, instead of +set_table_name+, use <tt>self.table_name=</tt>.
+
+<ruby>
+class Project < ActiveRecord::Base
+ self.table_name = "project"
+end
+</ruby>
+
+Or define your own <tt>self.table_name</tt> method:
+
+<ruby>
+class Post < ActiveRecord::Base
+ def self.table_name
+ "special_" + super
+ end
+end
+
+Post.table_name # => "special_posts"
+
+</ruby>
+
+h3. Active Model
+
+* Add <tt>ActiveModel::Errors#added?</tt> to check if a specific error has been added.
+
+* Add ability to define strict validations with <tt>strict => true</tt> that always raises exception when fails.
+
+* Provide mass_assignment_sanitizer as an easy API to replace the sanitizer behavior. Also support both :logger (default) and :strict sanitizer behavior.
+
+h4. Deprecations
+
+* Deprecated <tt>define_attr_method</tt> in <tt>ActiveModel::AttributeMethods</tt> because this only existed to support methods like +set_table_name+ in Active Record, which are themselves being deprecated.
+
+* Deprecated <tt>Model.model_name.partial_path</tt> in favor of <tt>model.to_partial_path</tt>.
+
+h3. Active Resource
+
+* Redirect responses: 303 See Other and 307 Temporary Redirect now behave like 301 Moved Permanently and 302 Found.
+
+h3. Active Support
+
+* Added <tt>ActiveSupport:TaggedLogging</tt> that can wrap any standard +Logger+ class to provide tagging capabilities.
+
+<ruby>
+Logger = ActiveSupport::TaggedLogging.new(Logger.new(STDOUT))
+
+Logger.tagged("BCX") { Logger.info "Stuff" }
+# Logs "[BCX] Stuff"
+
+Logger.tagged("BCX", "Jason") { Logger.info "Stuff" }
+# Logs "[BCX] [Jason] Stuff"
+
+Logger.tagged("BCX") { Logger.tagged("Jason") { Logger.info "Stuff" } }
+# Logs "[BCX] [Jason] Stuff"
+</ruby>
+
+* The +beginning_of_week+ method in +Date+, +Time+ and +DateTime+ accepts an optional argument representing the day in which the week is assumed to start.
+
+* <tt>ActiveSupport::Notifications.subscribed</tt> provides subscriptions to events while a block runs.
+
+* Defined new methods <tt>Module#qualified_const_defined?</tt>, <tt>Module#qualified_const_get</tt> and <tt>Module#qualified_const_set</tt> that are analogous to the corresponding methods in the standard API, but accept qualified constant names.
+
+* Added +#deconstantize+ which complements +#demodulize+ in inflections. This removes the rightmost segment in a qualified constant name.
+
+* Added <tt>safe_constantize</tt> that constantizes a string but returns +nil+ instead of raising an exception if the constant (or part of it) does not exist.
+
+* <tt>ActiveSupport::OrderedHash</tt> is now marked as extractable when using <tt>Array#extract_options!</tt>.
+
+* Added <tt>Array#prepend</tt> as an alias for <tt>Array#unshift</tt> and <tt>Array#append</tt> as an alias for <tt>Array#<<</tt>.
+
+* The definition of a blank string for Ruby 1.9 has been extended to Unicode whitespace. Also, in Ruby 1.8 the ideographic space U+3000 is considered to be whitespace.
+
+* The inflector understands acronyms.
+
+* Added <tt>Time#all_day</tt>, <tt>Time#all_week</tt>, <tt>Time#all_quarter</tt> and <tt>Time#all_year</tt> as a way of generating ranges.
+
+<ruby>
+Event.where(:created_at => Time.now.all_week)
+Event.where(:created_at => Time.now.all_day)
+</ruby>
+
+* Added <tt>instance_accessor: false</tt> as an option to <tt>Class#cattr_accessor</tt> and friends.
+
+* <tt>ActiveSupport::OrderedHash</tt> now has different behavior for <tt>#each</tt> and <tt>#each_pair</tt> when given a block accepting its parameters with a splat.
+
+* Added <tt>ActiveSupport::Cache::NullStore</tt> for use in development and testing.
+
+* Removed <tt>ActiveSupport::SecureRandom</tt> in favor of <tt>SecureRandom</tt> from the standard library.
+
+h4. Deprecations
+
+* Deprecated <tt>ActiveSupport::Memoizable</tt> in favor of Ruby memoization pattern.
+
+* <tt>Module#synchronize</tt> is deprecated with no replacement. Please use monitor from ruby's standard library.
+
+* Deprecated <tt>ActiveSupport::MessageEncryptor#encrypt</tt> and <tt>ActiveSupport::MessageEncryptor#decrypt</tt>.
+
+* <tt>ActiveSupport::BufferedLogger#silence</tt> is deprecated. If you want to squelch logs for a certain block, change the log level for that block.
+
+* <tt>ActiveSupport::BufferedLogger#open_log</tt> is deprecated. This method should not have been public in the first place.
+
+* <tt>ActiveSupport::BufferedLogger's</tt> behavior of automatically creating the directory for your log file is deprecated. Please make sure to create the directory for your log file before instantiating.
+
+* <tt>ActiveSupport::BufferedLogger#auto_flushing</tt> is deprecated. Either set the sync level on the underlying file handle like this. Or tune your filesystem. The FS cache is now what controls flushing.
+
+<ruby>
+f = File.open('foo.log', 'w')
+f.sync = true
+ActiveSupport::BufferedLogger.new f
+</ruby>
+
+* <tt>ActiveSupport::BufferedLogger#flush</tt> is deprecated. Set sync on your filehandle, or tune your filesystem.
+
+h3. Credits
+
+See the "full list of contributors to Rails":http://contributors.rubyonrails.org/ for the many people who spent many hours making Rails, the stable and robust framework it is. Kudos to all of them.
+
+Rails 3.2 Release Notes were compiled by "Vijay Dev":https://github.com/vijaydev.
diff --git a/railties/guides/source/_license.html.erb b/railties/guides/source/_license.html.erb
new file mode 100644
index 0000000000..00b4466f50
--- /dev/null
+++ b/railties/guides/source/_license.html.erb
@@ -0,0 +1,2 @@
+<p>This work is licensed under a <a href="http://creativecommons.org/licenses/by-sa/3.0/">Creative Commons Attribution-Share Alike 3.0</a> License</p>
+<p>"Rails", "Ruby on Rails", and the Rails logo are trademarks of David Heinemeier Hansson. All rights reserved.</p>
diff --git a/railties/guides/source/_welcome.html.erb b/railties/guides/source/_welcome.html.erb
new file mode 100644
index 0000000000..bcbb49a0ec
--- /dev/null
+++ b/railties/guides/source/_welcome.html.erb
@@ -0,0 +1,19 @@
+<h2>Ruby on Rails Guides (<%= @version %>)</h2>
+
+<% if @edge %>
+<p>
+ These are <b>Edge Guides</b>, based on the current <a href="https://github.com/rails/rails/tree/<%= @version %>">master</a> branch.
+</p>
+<p>
+ If you are looking for the ones for the stable version, please check
+ <a href="http://guides.rubyonrails.org">http://guides.rubyonrails.org</a> instead.
+</p>
+<% else %>
+<p>
+ These are the new guides for Rails 3.1 based on <a href="https://github.com/rails/rails/tree/<%= @version %>"><%= @version %></a>.
+ These guides are designed to make you immediately productive with Rails, and to help you understand how all of the pieces fit together.
+</p>
+<% end %>
+<p>
+ The guides for Rails 2.3.x are available at <a href="http://guides.rubyonrails.org/v2.3.11/">http://guides.rubyonrails.org/v2.3.11/</a>.
+</p>
diff --git a/railties/guides/source/action_controller_overview.textile b/railties/guides/source/action_controller_overview.textile
index b34c223b31..bc85f07ecc 100644
--- a/railties/guides/source/action_controller_overview.textile
+++ b/railties/guides/source/action_controller_overview.textile
@@ -16,7 +16,7 @@ h3. What Does a Controller Do?
Action Controller is the C in MVC. After routing has determined which controller to use for a request, your controller is responsible for making sense of the request and producing the appropriate output. Luckily, Action Controller does most of the groundwork for you and uses smart conventions to make this as straightforward as possible.
-For most conventional RESTful applications, the controller will receive the request (this is invisible to you as the developer), fetch or save data from a model and use a view to create HTML output. If your controller needs to do things a little differently, that's not a problem, this is just the most common way for a controller to work.
+For most conventional "RESTful":http://en.wikipedia.org/wiki/Representational_state_transfer applications, the controller will receive the request (this is invisible to you as the developer), fetch or save data from a model and use a view to create HTML output. If your controller needs to do things a little differently, that's not a problem, this is just the most common way for a controller to work.
A controller can thus be thought of as a middle man between models and views. It makes the model data available to the view so it can display that data to the user, and it saves or updates data from the user to the model.
diff --git a/railties/guides/source/action_mailer_basics.textile b/railties/guides/source/action_mailer_basics.textile
index ad5b848d2c..26c95be031 100644
--- a/railties/guides/source/action_mailer_basics.textile
+++ b/railties/guides/source/action_mailer_basics.textile
@@ -362,21 +362,14 @@ When using named routes you only need to supply the +:host+:
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.
-It is also possible to set a default host that will be used in all mailers by setting the +:host+ option in the +ActionMailer::Base.default_url_options+ hash as follows:
+It is also possible to set a default host that will be used in all mailers by setting the <tt>:host</tt> option as a configuration option in <tt>config/application.rb</tt>:
<ruby>
-class UserMailer < ActionMailer::Base
- default_url_options[:host] = "example.com"
-
- def welcome_email(user)
- @user = user
- @url = user_url(@user)
- mail(:to => user.email,
- :subject => "Welcome to My Awesome Site")
- end
-end
+config.action_mailer.default_url_options = { :host => "example.com" }
</ruby>
+If you use this setting, you should pass the <tt>:only_path => false</tt> 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 <tt>:host</tt> option isn't explicitly provided.
+
h4. 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.
diff --git a/railties/guides/source/active_record_basics.textile b/railties/guides/source/active_record_basics.textile
index 66ad7b0255..487f8b70f9 100644
--- a/railties/guides/source/active_record_basics.textile
+++ b/railties/guides/source/active_record_basics.textile
@@ -101,11 +101,11 @@ h3. 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 the default conventions.
-You can use the +ActiveRecord::Base.set_table_name+ method to specify the table name that should be used:
+You can use the +ActiveRecord::Base.table_name=+ method to specify the table name that should be used:
<ruby>
class Product < ActiveRecord::Base
- set_table_name "PRODUCT"
+ self.table_name = "PRODUCT"
end
</ruby>
diff --git a/railties/guides/source/active_record_querying.textile b/railties/guides/source/active_record_querying.textile
index ad12dca7e8..beada85ce3 100644
--- a/railties/guides/source/active_record_querying.textile
+++ b/railties/guides/source/active_record_querying.textile
@@ -966,7 +966,7 @@ When a +lambda+ is used for a +scope+, it can take arguments:
<ruby>
class Post < ActiveRecord::Base
- scope :1_week_before, lambda { |time| where("created_at < ?", time)
+ scope :1_week_before, lambda { |time| where("created_at < ?", time) }
end
</ruby>
@@ -1146,6 +1146,30 @@ h3. +select_all+
Client.connection.select_all("SELECT * FROM clients WHERE id = '1'")
</ruby>
+h3. +pluck+
+
+<tt>pluck</tt> can be used to query a single column from the underlying table of a model. It accepts a column name as argument and returns an array of values of the specified column with the corresponding data type.
+
+<ruby>
+Client.where(:active => true).pluck(:id)
+# SELECT id FROM clients WHERE active = 1
+
+Client.uniq.pluck(:role)
+# SELECT DISTINCT role FROM clients
+</ruby>
+
++pluck+ makes it possible to replace code like
+
+<ruby>
+Client.select(:id).map { |c| c.id }
+</ruby>
+
+with
+
+<ruby>
+Client.pluck(:id)
+</ruby>
+
h3. Existence of Objects
If you simply want to check for the existence of the object there's a method called +exists?+. This method will query the database using the same query as +find+, but instead of returning an object or collection of objects it will return either +true+ or +false+.
@@ -1287,6 +1311,7 @@ User.where(:id => 1).joins(:posts).explain
may yield
<plain>
+EXPLAIN for: SELECT `users`.* FROM `users` INNER JOIN `posts` ON `posts`.`user_id` = `users`.`id` WHERE `users`.`id` = 1
<plus>----<plus>-------------<plus>-------<plus>-------<plus>---------------<plus>---------<plus>---------<plus>-------<plus>------<plus>-------------<plus>
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
<plus>----<plus>-------------<plus>-------<plus>-------<plus>---------------<plus>---------<plus>---------<plus>-------<plus>------<plus>-------------<plus>
@@ -1302,6 +1327,7 @@ Active Record performs a pretty printing that emulates the one of the database
shells. So, the same query running with the PostgreSQL adapter would yield instead
<plain>
+EXPLAIN for: SELECT "users".* FROM "users" INNER JOIN "posts" ON "posts"."user_id" = "users"."id" WHERE "users"."id" = 1
QUERY PLAN
------------------------------------------------------------------------------
Nested Loop Left Join (cost=0.00..37.24 rows=8 width=0)
@@ -1324,12 +1350,15 @@ User.where(:id => 1).includes(:posts).explain
yields
<plain>
+EXPLAIN for: SELECT `users`.* FROM `users` WHERE `users`.`id` = 1
<plus>----<plus>-------------<plus>-------<plus>-------<plus>---------------<plus>---------<plus>---------<plus>-------<plus>------<plus>-------<plus>
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
<plus>----<plus>-------------<plus>-------<plus>-------<plus>---------------<plus>---------<plus>---------<plus>-------<plus>------<plus>-------<plus>
| 1 | SIMPLE | users | const | PRIMARY | PRIMARY | 4 | const | 1 | |
<plus>----<plus>-------------<plus>-------<plus>-------<plus>---------------<plus>---------<plus>---------<plus>-------<plus>------<plus>-------<plus>
1 row in set (0.00 sec)
+
+EXPLAIN for: SELECT `posts`.* FROM `posts` WHERE `posts`.`user_id` IN (1)
<plus>----<plus>-------------<plus>-------<plus>------<plus>---------------<plus>------<plus>---------<plus>------<plus>------<plus>-------------<plus>
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
<plus>----<plus>-------------<plus>-------<plus>------<plus>---------------<plus>------<plus>---------<plus>------<plus>------<plus>-------------<plus>
@@ -1339,3 +1368,50 @@ yields
</plain>
under MySQL.
+
+h4. Automatic EXPLAIN
+
+Active Record is able to run EXPLAIN automatically on slow queries and log its
+output. This feature is controlled by the configuration parameter
+
+<ruby>
+config.active_record.auto_explain_threshold_in_seconds
+</ruby>
+
+If set to a number, any query exceeding those many seconds will have its EXPLAIN
+automatically triggered and logged. In the case of relations, the threshold is
+compared to the total time needed to fetch records. So, a relation is seen as a
+unit of work, no matter whether the implementation of eager loading involves
+several queries under the hood.
+
+A threshold of +nil+ disables automatic EXPLAINs.
+
+The default threshold in development mode is 0.5 seconds, and +nil+ in test and
+production modes.
+
+h5. Disabling Automatic EXPLAIN
+
+Automatic EXPLAIN can be selectively silenced with +ActiveRecord::Base.silence_auto_explain+:
+
+<ruby>
+ActiveRecord::Base.silence_auto_explain do
+ # no automatic EXPLAIN is triggered here
+end
+</ruby>
+
+That may be useful for queries you know are slow but fine, like a heavyweight
+report of an admin interface.
+
+As its name suggests, +silence_auto_explain+ only silences automatic EXPLAINs.
+Explicit calls to +ActiveRecord::Relation#explain+ run.
+
+h4. Interpreting EXPLAIN
+
+Interpretation of the output of EXPLAIN is beyond the scope of this guide. The
+following pointers may be helpful:
+
+* SQLite3: "EXPLAIN QUERY PLAN":http://www.sqlite.org/eqp.html
+
+* MySQL: "EXPLAIN Output Format":http://dev.mysql.com/doc/refman/5.6/en/explain-output.html
+
+* PostgreSQL: "Using EXPLAIN":http://www.postgresql.org/docs/current/static/using-explain.html
diff --git a/railties/guides/source/active_support_core_extensions.textile b/railties/guides/source/active_support_core_extensions.textile
index ff6c5f967f..1c82a2941f 100644
--- a/railties/guides/source/active_support_core_extensions.textile
+++ b/railties/guides/source/active_support_core_extensions.textile
@@ -177,19 +177,6 @@ end
NOTE: Defined in +active_support/core_ext/object/try.rb+.
-h4. +singleton_class+
-
-The method +singleton_class+ returns the singleton class of the receiver:
-
-<ruby>
-String.singleton_class # => #<Class:String>
-String.new.singleton_class # => #<Class:#<String:0x17a1d1c>>
-</ruby>
-
-WARNING: Fixnums and symbols have no singleton classes, +singleton_class+ raises +TypeError+ on them. Moreover, the singleton classes of +nil+, +true+, and +false+, are +NilClass+, +TrueClass+, and +FalseClass+, respectively.
-
-NOTE: Defined in +active_support/core_ext/kernel/singleton_class.rb+.
-
h4. +class_eval(*args, &block)+
You can evaluate code in the context of any object's singleton class using +class_eval+:
@@ -440,14 +427,16 @@ NOTE: Defined in +active_support/core_ext/kernel/reporting.rb+.
h4. +in?+
-The predicate +in?+ tests if an object is included in another object. An +ArgumentError+ exception will be raised if the argument passed does not respond to +include?+.
+The predicate +in?+ tests if an object is included in another object or a list of objects. An +ArgumentError+ exception will be raised if a single argument is passed and it does not respond to +include?+.
Examples of +in?+:
<ruby>
+1.in?(1,2) # => true
1.in?([1,2]) # => true
"lo".in?("hello") # => true
25.in?(30..50) # => false
+1.in?(1) # => ArgumentError
</ruby>
NOTE: Defined in +active_support/core_ext/object/inclusion.rb+.
@@ -571,7 +560,7 @@ NOTE: Defined in +active_support/core_ext/module/attr_accessor_with_default.rb+.
h5. Internal Attributes
-When you are defining an attribute in a class that is meant to be subclassed name collisions are a risk. That's remarkably important for libraries.
+When you are defining an attribute in a class that is meant to be subclassed, name collisions are a risk. That's remarkably important for libraries.
Active Support defines the macros +attr_internal_reader+, +attr_internal_writer+, and +attr_internal_accessor+. They behave like their Ruby built-in +attr_*+ counterparts, except they name the underlying instance variable in a way that makes collisions less likely.
@@ -783,30 +772,6 @@ Absolute qualified constant names like +::Math::PI+ raise +NameError+.
NOTE: Defined in +active_support/core_ext/module/qualified_const.rb+.
-h4. Synchronization
-
-The +synchronize+ macro declares a method to be synchronized:
-
-<ruby>
-class Counter
- @@mutex = Mutex.new
- attr_reader :value
-
- def initialize
- @value = 0
- end
-
- def incr
- @value += 1 # non-atomic
- end
- synchronize :incr, :with => '@@mutex'
-end
-</ruby>
-
-The method receives the name of an action, and a +:with+ option with code. The code is evaluated in the context of the receiver each time the method is invoked, and it should evaluate to a +Mutex+ instance or any other object that responds to +synchronize+ and accepts a block.
-
-NOTE: Defined in +active_support/core_ext/module/synchronization.rb+.
-
h4. Reachable
A named module is reachable if it is stored in its corresponding constant. It means you can reach the module object via the constant.
@@ -857,7 +822,7 @@ M.name # => "M"
N = Module.new
N.name # => "N"
-Module.new.name # => "" in 1.8, nil in 1.9
+Module.new.name # => nil
</ruby>
You can check whether a module has a name with the predicate +anonymous?+:
@@ -970,18 +935,6 @@ In the previous example the macro generates +avatar_size+ rather than +size+.
NOTE: Defined in +active_support/core_ext/module/delegation.rb+
-h4. Method Names
-
-The builtin methods +instance_methods+ and +methods+ return method names as strings or symbols depending on the Ruby version. Active Support defines +instance_method_names+ and +method_names+ to be equivalent to them, respectively, but always getting strings back.
-
-For example, +ActionView::Helpers::FormBuilder+ knows this array difference is going to work no matter the Ruby version:
-
-<ruby>
-self.field_helpers = (FormHelper.instance_method_names - ['form_for'])
-</ruby>
-
-NOTE: Defined in +active_support/core_ext/module/method_names.rb+
-
h4. Redefining Methods
There are cases where you need to define a method with +define_method+, but don't know whether a method with that name already exists. If it does, a warning is issued if they are enabled. No big deal, but not clean either.
@@ -1299,7 +1252,7 @@ NOTE: Defined in +active_support/core_ext/string/output_safety.rb+.
h5. Transformation
-As a rule of thumb, except perhaps for concatenation as explained above, any method that may change a string gives you an unsafe string. These are +donwcase+, +gsub+, +strip+, +chomp+, +underscore+, etc.
+As a rule of thumb, except perhaps for concatenation as explained above, any method that may change a string gives you an unsafe string. These are +downcase+, +gsub+, +strip+, +chomp+, +underscore+, etc.
In the case of in-place transformations like +gsub!+ the receiver itself becomes unsafe.
@@ -1849,43 +1802,6 @@ NOTE: Defined in +active_support/core_ext/string/inflections.rb+.
h4(#string-conversions). Conversions
-h5. +ord+
-
-Ruby 1.9 defines +ord+ to be the codepoint of the first character of the receiver. Active Support backports +ord+ for single-byte encodings like ASCII or ISO-8859-1 in Ruby 1.8:
-
-<ruby>
-"a".ord # => 97
-"à".ord # => 224, in ISO-8859-1
-</ruby>
-
-In Ruby 1.8 +ord+ doesn't work in general in UTF8 strings, use the multibyte support in Active Support for that:
-
-<ruby>
-"a".mb_chars.ord # => 97
-"à".mb_chars.ord # => 224, in UTF8
-</ruby>
-
-Note that the 224 is different in both examples. In ISO-8859-1 "à" is represented as a single byte, 224. Its single-character representation in UTF8 has two bytes, namely 195 and 160, but its Unicode codepoint is 224. If we call +ord+ on the UTF8 string "à" the return value will be 195 in Ruby 1.8. That is not an error, because UTF8 is unsupported, the call itself would be bogus.
-
-INFO: +ord+ is equivalent to +getbyte(0)+.
-
-NOTE: Defined in +active_support/core_ext/string/conversions.rb+.
-
-h5. +getbyte+
-
-Active Support backports +getbyte+ from Ruby 1.9:
-
-<ruby>
-"foo".getbyte(0) # => 102, same as "foo".ord
-"foo".getbyte(1) # => 111
-"foo".getbyte(9) # => nil
-"foo".getbyte(-1) # => 111
-</ruby>
-
-INFO: +getbyte+ is equivalent to +[]+.
-
-NOTE: Defined in +active_support/core_ext/string/conversions.rb+.
-
h5. +to_date+, +to_time+, +to_datetime+
The methods +to_date+, +to_time+, and +to_datetime+ are basically convenience wrappers around +Date._parse+:
@@ -1972,38 +1888,12 @@ The method +ordinalize+ returns the ordinal string corresponding to the receiver
NOTE: Defined in +active_support/core_ext/integer/inflections.rb+.
-h3. Extensions to +Float+
-
-h4. +round+
-
-The built-in method +Float#round+ rounds a float to the nearest integer. In Ruby 1.9 this method takes an optional argument to let you specify a precision. Active Support adds that functionality to +round+ in previous versions of Ruby:
-
-<ruby>
-Math::E.round(4) # => 2.7183
-</ruby>
-
-NOTE: Defined in +active_support/core_ext/float/rounding.rb+.
-
h3. Extensions to +BigDecimal+
...
h3. Extensions to +Enumerable+
-h4. +group_by+
-
-Active Support redefines +group_by+ in Ruby 1.8.7 so that it returns an ordered hash as in 1.9:
-
-<ruby>
-entries_by_surname_initial = address_book.group_by do |entry|
- entry.surname.at(0).upcase
-end
-</ruby>
-
-Distinct block return values are added to the hash as they come, so that's the resulting order.
-
-NOTE: Defined in +active_support/core_ext/enumerable.rb+.
-
h4. +sum+
The method +sum+ adds the elements of an enumerable:
@@ -2051,32 +1941,6 @@ end
NOTE: Defined in +active_support/core_ext/enumerable.rb+.
-h4. +each_with_object+
-
-The +inject+ method offers iteration with an accumulator:
-
-<ruby>
-[2, 3, 4].inject(1) {|product, i| product*i } # => 24
-</ruby>
-
-The block is expected to return the value for the accumulator in the next iteration, and this makes building mutable objects a bit cumbersome:
-
-<ruby>
-[1, 2].inject({}) {|h, i| h[i] = i**2; h} # => {1 => 1, 2 => 4}
-</ruby>
-
-See that spurious "+; h+"?
-
-Active Support backports +each_with_object+ from Ruby 1.9, which addresses that use case. It iterates over the collection, passes the accumulator, and returns the accumulator when done. You normally modify the accumulator in place. The example above would be written this way:
-
-<ruby>
-[1, 2].each_with_object({}) {|i, h| h[i] = i**2} # => {1 => 1, 2 => 4}
-</ruby>
-
-WARNING. Note that the item of the collection and the accumulator come in different order in +inject+ and +each_with_object+.
-
-NOTE: Defined in +active_support/core_ext/enumerable.rb+.
-
h4. +index_by+
The method +index_by+ generates a hash with the elements of an enumerable indexed by some key.
@@ -2148,20 +2012,6 @@ The methods +second+, +third+, +fourth+, and +fifth+ return the corresponding el
NOTE: Defined in +active_support/core_ext/array/access.rb+.
-h4. Random Access
-
-Active Support backports +sample+ from Ruby 1.9:
-
-<ruby>
-shape_type = [Circle, Square, Triangle].sample
-# => Square, for example
-
-shape_types = [Circle, Square, Triangle].sample(2)
-# => [Triangle, Circle], for example
-</ruby>
-
-NOTE: Defined in +active_support/core_ext/array/random_access.rb+.
-
h4. Adding Elements
h5. +prepend+
@@ -2914,14 +2764,6 @@ WARNING: The original +Range#include?+ is still the one aliased to +Range#===+.
NOTE: Defined in +active_support/core_ext/range/include_range.rb+.
-h4. +cover?+
-
-Ruby 1.9 provides +cover?+, and Active Support defines it for previous versions as an alias for +include?+.
-
-The method +include?+ in Ruby 1.9 is different from the one in 1.8 for non-numeric ranges: instead of being based on comparisons between the value and the range's endpoints, it walks the range with +succ+ looking for value. This works better for ranges with holes, but it has different complexity and may not finish in some other cases.
-
-In Ruby 1.9 the old behavior is still available in the new +cover?+, which Active Support backports for forward compatibility. For example, Rails uses +cover?+ for ranges in +validates_inclusion_of+.
-
h4. +overlaps?+
The method +Range#overlaps?+ says whether any two given ranges have non-void intersection:
@@ -3039,15 +2881,30 @@ Active Support defines these methods as well for Ruby 1.8.
h6. +beginning_of_week+, +end_of_week+
-The methods +beginning_of_week+ and +end_of_week+ return the dates for the beginning and end of week, assuming weeks start on Monday:
+The methods +beginning_of_week+ and +end_of_week+ return the dates for the
+beginning and end of the week, respectively. Weeks are assumed to start on
+Monday, but that can be changed passing an argument.
<ruby>
-d = Date.new(2010, 5, 8) # => Sat, 08 May 2010
-d.beginning_of_week # => Mon, 03 May 2010
-d.end_of_week # => Sun, 09 May 2010
+d = Date.new(2010, 5, 8) # => Sat, 08 May 2010
+d.beginning_of_week # => Mon, 03 May 2010
+d.beginning_of_week(:sunday) # => Sun, 02 May 2010
+d.end_of_week # => Sun, 09 May 2010
+d.end_of_week(:sunday) # => Sat, 08 May 2010
</ruby>
-+beginning_of_week+ is aliased to +monday+ and +at_beginning_of_week+. +end_of_week+ is aliased to +sunday+ and +at_end_of_week+.
++beginning_of_week+ is aliased to +at_beginning_of_week+ and +end_of_week+ is aliased to +at_end_of_week+.
+
+h6. +monday+, +sunday+
+
+The methods +monday+ and +sunday+ return the dates for the beginning and
+end of the week, respectively. Weeks are assumed to start on Monday.
+
+<ruby>
+d = Date.new(2010, 5, 8) # => Sat, 08 May 2010
+d.monday # => Mon, 03 May 2010
+d.sunday # => Sun, 09 May 2010
+</ruby>
h6. +prev_week+, +next_week+
@@ -3272,8 +3129,10 @@ The class +DateTime+ is a subclass of +Date+ so by loading +active_support/core_
<ruby>
yesterday
tomorrow
-beginning_of_week (monday, at_beginning_of_week)
-end_on_week (at_end_of_week)
+beginning_of_week (at_beginning_of_week)
+end_of_week (at_end_of_week)
+monday
+sunday
weeks_ago
prev_week
next_week
@@ -3446,8 +3305,10 @@ ago
since (in)
beginning_of_day (midnight, at_midnight, at_beginning_of_day)
end_of_day
-beginning_of_week (monday, at_beginning_of_week)
-end_on_week (at_end_of_week)
+beginning_of_week (at_beginning_of_week)
+end_of_week (at_end_of_week)
+monday
+sunday
weeks_ago
prev_week
next_week
@@ -3572,12 +3433,6 @@ Time.utc_time(1582, 10, 3) + 5.days
# => Mon Oct 18 00:00:00 UTC 1582
</ruby>
-h3. Extensions to +Process+
-
-h4. +daemon+
-
-Ruby 1.9 provides +Process.daemon+, and Active Support defines it for previous versions. It accepts the same two arguments, whether it should chdir to the root directory (default, true), and whether it should inherit the standard file descriptors from the parent (default, false).
-
h3. Extensions to +File+
h4. +atomic_write+
diff --git a/railties/guides/source/asset_pipeline.textile b/railties/guides/source/asset_pipeline.textile
index 6ff5e87b6d..f48f5afd54 100644
--- a/railties/guides/source/asset_pipeline.textile
+++ b/railties/guides/source/asset_pipeline.textile
@@ -369,10 +369,10 @@ It is important that this folder is shared between deployments so that remotely
NOTE. If you are precompiling your assets locally, you can use +bundle install --without assets+ on the server to avoid installing the assets gems (the gems in the assets group in the Gemfile).
-The default matcher for compiling files includes +application.js+, +application.css+ and all files that do not end in +js+ or +css+:
+The default matcher for compiling files includes +application.js+, +application.css+ and all non-JS/CSS files (ie. +.coffee+ and +.scss+ files are *not* automatically included as they compile to JS/CSS):
<ruby>
-[ /\w<plus>\.(?!js|css).<plus>/, /application.(css|js)$/ ]
+[ Proc.new{ |path| !File.extname(path).in?(['.js', '.css']) }, /application.(css|js)$/ ]
</ruby>
If you have other manifests or individual stylesheets and JavaScript files to include, you can add them to the +precompile+ array:
@@ -410,10 +410,6 @@ For Apache:
<plain>
<LocationMatch "^/assets/.*$">
- # Some browsers still send conditional-GET requests if there's a
- # Last-Modified header or an ETag header even if they haven't
- # reached the expiry date sent in the Expires header.
- Header unset Last-Modified
Header unset ETag
FileETag None
# RFC says only cache for 1 year
@@ -429,16 +425,12 @@ location ~ ^/assets/ {
expires 1y;
add_header Cache-Control public;
- # Some browsers still send conditional-GET requests if there's a
- # Last-Modified header or an ETag header even if they haven't
- # reached the expiry date sent in the Expires header.
- add_header Last-Modified "";
add_header ETag "";
break;
}
</plain>
-When files are precompiled, Sprockets also creates a "gzipped":http://en.wikipedia.org/wiki/Gzip (.gz) version of your assets. Web servers are typically configured to use a moderate compression ratio as a compromise, but since precompilation happens once Sprockets uses the maximum compression ratio, thus reducing the size of the data transfer to the minimum. On the other hand, web servers can be configured to serve compressed content directly from disk, rather than deflating non-compressed files themselves.
+When files are precompiled, Sprockets also creates a "gzipped":http://en.wikipedia.org/wiki/Gzip (.gz) version of your assets. Web servers are typically configured to use a moderate compression ratio as a compromise, but since precompilation happens once, Sprockets uses the maximum compression ratio, thus reducing the size of the data transfer to the minimum. On the other hand, web servers can be configured to serve compressed content directly from disk, rather than deflating non-compressed files themselves.
Nginx is able to do this automatically enabling +gzip_static+:
@@ -577,7 +569,7 @@ TODO: Registering gems on "Tilt":https://github.com/rtomayko/tilt enabling Sproc
h3. Upgrading from Old Versions of Rails
-There are two issues when upgrading. The first is moving the files to the new locations. See the section above for guidance on the correct locations for different file types.
+There are two issues when upgrading. The first is moving the files to the new locations. See "Asset Organization":#asset-organization above for guidance on the correct locations for different file types.
The second is updating the various environment files with the correct default options. The following changes reflect the defaults in version 3.1.0.
diff --git a/railties/guides/source/caching_with_rails.textile b/railties/guides/source/caching_with_rails.textile
index 0ef6f51190..6419d32c13 100644
--- a/railties/guides/source/caching_with_rails.textile
+++ b/railties/guides/source/caching_with_rails.textile
@@ -64,6 +64,28 @@ end
If you want a more complicated expiration scheme, you can use cache sweepers to expire cached objects when things change. This is covered in the section on Sweepers.
+By default, page caching automatically gzips files (for example, to +products.html.gz+ if user requests +/products+) to reduce the size of data transmitted (web servers are typically configured to use a moderate compression ratio as a compromise, but since precompilation happens once, compression ratio is maximum).
+
+Nginx is able to serve compressed content directly from disk by enabling +gzip_static+:
+
+<plain>
+location / {
+ gzip_static on; # to serve pre-gzipped version
+}
+</plain>
+
+You can disable gzipping by setting +:gzip+ option to false (for example, if action returns image):
+
+<ruby>
+caches_page :image, :gzip => false
+</ruby>
+
+Or, you can set custom gzip compression level (level names are taken from +Zlib+ constants):
+
+<ruby>
+caches_page :image, :gzip => :best_speed
+</ruby>
+
NOTE: Page caching ignores all parameters. For example +/products?page=1+ will be written out to the filesystem as +products.html+ with no reference to the +page+ parameter. Thus, if someone requests +/products?page=2+ later, they will get the cached first page. A workaround for this limitation is to include the parameters in the page's path, e.g. +/productions/page/1+.
INFO: Page caching runs in an after filter. Thus, invalid requests won't generate spurious cache entries as long as you halt them. Typically, a redirection in some before filter that checks request preconditions does the job.
@@ -332,6 +354,14 @@ caches_action :index, :expires_in => 60.seconds, :unless_exist => true
For more information about Ehcache, see "http://ehcache.org/":http://ehcache.org/ .
For more information about Ehcache for JRuby and Rails, see "http://ehcache.org/documentation/jruby.html":http://ehcache.org/documentation/jruby.html
+h4. ActiveSupport::Cache::NullStore
+
+This cache store implementation is meant to be used only in development or test environments and it never stores anything. This can be very useful in development when you have code that interacts directly with +Rails.cache+, but caching may interfere with being able to see the results of code changes. With this cache store, all +fetch+ and +read+ operations will result in a miss.
+
+<ruby>
+ActionController::Base.cache_store = :null
+</ruby>
+
h4. Custom Cache Stores
You can create your own custom cache store by simply extending +ActiveSupport::Cache::Store+ and implementing the appropriate methods. In this way, you can swap in any number of caching technologies into your Rails application.
diff --git a/railties/guides/source/command_line.textile b/railties/guides/source/command_line.textile
index 3f8643eca3..fa783edc58 100644
--- a/railties/guides/source/command_line.textile
+++ b/railties/guides/source/command_line.textile
@@ -36,7 +36,7 @@ WARNING: You can install the rails gem by typing +gem install rails+, if you don
<shell>
$ rails new commandsapp
create
- create README
+ create README.rdoc
create .gitignore
create Rakefile
create config.ru
@@ -81,6 +81,8 @@ The server can be run on a different port using the +-p+ option. The default dev
$ rails server -e production -p 4000
</shell>
+The +-b+ option binds Rails to the specified ip, by default it is 0.0.0.0. You can run a server as a daemon by passing a +-d+ option.
+
h4. +rails generate+
The +rails generate+ command uses templates to create a whole lot of things. Running +rails generate+ by itself gives a list of available generators:
@@ -379,17 +381,17 @@ h4. +about+
<shell>
$ rake about
About your application's environment
-Ruby version 1.8.7 (x86_64-linux)
+Ruby version 1.9.3 (x86_64-linux)
RubyGems version 1.3.6
Rack version 1.3
-Rails version 3.2.0.beta
+Rails version 4.0.0.beta
JavaScript Runtime Node.js (V8)
-Active Record version 3.2.0.beta
-Action Pack version 3.2.0.beta
-Active Resource version 3.2.0.beta
-Action Mailer version 3.2.0.beta
-Active Support version 3.2.0.beta
-Middleware ActionDispatch::Static, Rack::Lock, Rack::Runtime, Rack::MethodOverride, ActionDispatch::RequestId, Rails::Rack::Logger, ActionDispatch::ShowExceptions, ActionDispatch::RemoteIp, ActionDispatch::Reloader, ActionDispatch::Callbacks, ActiveRecord::ConnectionAdapters::ConnectionManagement, ActiveRecord::QueryCache, ActionDispatch::Cookies, ActionDispatch::Session::CookieStore, ActionDispatch::Flash, ActionDispatch::ParamsParser, ActionDispatch::Head, Rack::ConditionalGet, Rack::ETag, ActionDispatch::BestStandardsSupport
+Active Record version 4.0.0.beta
+Action Pack version 4.0.0.beta
+Active Resource version 4.0.0.beta
+Action Mailer version 4.0.0.beta
+Active Support version 4.0.0.beta
+Middleware ActionDispatch::Static, Rack::Lock, Rack::Runtime, Rack::MethodOverride, ActionDispatch::RequestId, Rails::Rack::Logger, ActionDispatch::ShowExceptions, ActionDispatch::DebugExceptions, ActionDispatch::RemoteIp, ActionDispatch::Reloader, ActionDispatch::Callbacks, ActiveRecord::ConnectionAdapters::ConnectionManagement, ActiveRecord::QueryCache, ActionDispatch::Cookies, ActionDispatch::Session::CookieStore, ActionDispatch::Flash, ActionDispatch::ParamsParser, ActionDispatch::Head, Rack::ConditionalGet, Rack::ETag, ActionDispatch::BestStandardsSupport
Application root /home/foobar/commandsapp
Environment development
Database adapter sqlite3
@@ -418,7 +420,7 @@ The +doc:+ namespace has the tools to generate documentation for your app, API d
h4. +notes+
-+rake notes+ will search through your code for comments beginning with FIXME, OPTIMIZE or TODO. The search is only done in files with extension +.builder+, +.rb+, +.rxml+, +.rhtml+ and +.erb+ for both default and custom annotations.
++rake notes+ will search through your code for comments beginning with FIXME, OPTIMIZE or TODO. The search is done in files with extension +.builder+, +.rb+, +.erb+, +.haml+ and +.slim+ for both default and custom annotations.
<shell>
$ rake notes
@@ -507,8 +509,8 @@ $ rails new . --git --database=postgresql
create tmp/pids
create Rakefile
add 'Rakefile'
- create README
-add 'README'
+ create README.rdoc
+add 'README.rdoc'
create app/controllers/application_controller.rb
add 'app/controllers/application_controller.rb'
create app/helpers/application_helper.rb
diff --git a/railties/guides/source/configuring.textile b/railties/guides/source/configuring.textile
index cd6e7d116e..09ef308665 100644
--- a/railties/guides/source/configuring.textile
+++ b/railties/guides/source/configuring.textile
@@ -82,12 +82,18 @@ NOTE. The +config.asset_path+ configuration is ignored if the asset pipeline is
* +config.encoding+ sets up the application-wide encoding. Defaults to UTF-8.
+* +config.exceptions_app+ sets the exceptions application invoked by the ShowException middleware when an exception happens. Defaults to +ActionDispatch::PublicExceptions.new(Rails.public_path)+.
+
+* +config.file_watcher+ the class used to detect file updates in the filesystem when +config.reload_classes_only_on_change+ is true. Must conform to +ActiveSupport::FileUpdateChecker+ API.
+
* +config.filter_parameters+ used for filtering out the parameters that you don't want shown in the logs, such as passwords or credit card numbers.
* +config.force_ssl+ forces all requests to be under HTTPS protocol by using +Rack::SSL+ middleware.
* +config.log_level+ defines the verbosity of the Rails logger. This option defaults to +:debug+ for all modes except production, where it defaults to +:info+.
+* +config.log_tags+ accepts a list of methods that respond to +request+ object. This makes it easy to tag log lines with debug information like subdomain and request id -- both very helpful in debugging multi-user production applications.
+
* +config.logger+ accepts a logger conforming to the interface of Log4r or the default Ruby +Logger+ class. Defaults to an instance of +ActiveSupport::BufferedLogger+, with auto flushing off in production mode.
* +config.middleware+ allows you to configure the application's middleware. This is covered in depth in the "Configuring Middleware":#configuring-middleware section below.
@@ -96,6 +102,8 @@ NOTE. The +config.asset_path+ configuration is ignored if the asset pipeline is
* +config.preload_frameworks+ enables or disables preloading all frameworks at startup. Enabled by +config.threadsafe!+. Defaults to +nil+, so is disabled.
+* +config.reload_classes_only_on_change+ enables or disables reloading of classes only when tracked files change. By default tracks everything on autoload paths and is set to true. If +config.cache_classes+ is true, this option is ignored.
+
* +config.reload_plugins+ enables or disables plugin reloading. Defaults to false.
* +config.secret_token+ used for specifying a key which allows sessions for the application to be verified against a known secure key to prevent tampering. Applications get +config.secret_token+ initialized to a random key in +config/initializers/secret_token.rb+.
@@ -188,6 +196,7 @@ Every Rails application comes with a standard set of middleware which it uses in
* +Rack::Runtime+ sets an +X-Runtime+ header, containing the time (in seconds) taken to execute the request.
* +Rails::Rack::Logger+ notifies the logs that the request has began. After request is complete, flushes all the logs.
* +ActionDispatch::ShowExceptions+ rescues any exception returned by the application and renders nice exception pages if the request is local or if +config.consider_all_requests_local+ is set to +true+. If +config.action_dispatch.show_exceptions+ is set to +false+, exceptions will be raised regardless.
+* +ActionDispatch::RequestId+ makes a unique X-Request-Id header available to the response and enables the +ActionDispatch::Request#uuid+ method.
* +ActionDispatch::RemoteIp+ checks for IP spoofing attacks. Configurable with the +config.action_dispatch.ip_spoofing_check+ and +config.action_dispatch.trusted_proxies+ settings.
* +Rack::Sendfile+ intercepts responses whose body is being served from a file and replaces it with a server specific X-Sendfile header. Configurable with +config.action_dispatch.x_sendfile_header+.
* +ActionDispatch::Callbacks+ runs the prepare callbacks before serving the request.
@@ -263,6 +272,10 @@ h4. Configuring Active Record
* +config.active_record.whitelist_attributes+ will create an empty whitelist of attributes available for mass-assignment security for all models in your app.
+* +config.active_record.identity_map+ controls whether the identity map is enabled, and is false by default.
+
+* +config.active_record.auto_explain_threshold_in_seconds+ configures the threshold for automatic EXPLAINs (+nil+ disables this feature). Queries exceeding the threshold get their query plan logged. Default is 0.5 in development mode.
+
The MySQL adapter adds one additional configuration option:
* +ActiveRecord::ConnectionAdapters::MysqlAdapter.emulate_booleans+ controls whether Active Record will consider all +tinyint(1)+ columns in a MySQL database to be booleans and is true by default.
diff --git a/railties/guides/source/contributing_to_ruby_on_rails.textile b/railties/guides/source/contributing_to_ruby_on_rails.textile
index 80c3cf6e1a..92cb0774de 100644
--- a/railties/guides/source/contributing_to_ruby_on_rails.textile
+++ b/railties/guides/source/contributing_to_ruby_on_rails.textile
@@ -215,7 +215,7 @@ TIP: You may want to "put your git branch name in your shell prompt":http://qugs
h3. Helping to Resolve Existing Issues
-As a next step beyond reporting issues, you can help the core team resolve existing issues. If you check the "Everyone's Issues":https://github.com/rails/rails/issues?sort=created&direction=desc&state=open&page=1 list in GitHub Issues, you'll find lots of issues already requiring attention. What can you do for these? Quite a bit, actually:
+As a next step beyond reporting issues, you can help the core team resolve existing issues. If you check the "Everyone's Issues":https://github.com/rails/rails/issues list in GitHub Issues, you'll find lots of issues already requiring attention. What can you do for these? Quite a bit, actually:
h4. Verifying Bug Reports
@@ -336,7 +336,7 @@ It’s pretty likely that other changes to master have happened while you were w
<shell>
$ git checkout master
-$ git pull
+$ git pull --rebase
</shell>
Now reapply your patch on top of the latest changes:
diff --git a/railties/guides/source/debugging_rails_applications.textile b/railties/guides/source/debugging_rails_applications.textile
index 3552c68418..57c7786636 100644
--- a/railties/guides/source/debugging_rails_applications.textile
+++ b/railties/guides/source/debugging_rails_applications.textile
@@ -465,7 +465,7 @@ Now you should know where you are in the running trace and be able to print the
Use +step+ (abbreviated +s+) to continue running your program until the next logical stopping point and return control to ruby-debug.
-TIP: You can also use +step+ _n_+ and +step- _n_+ to move forward or backward _n_ steps respectively.
+TIP: You can also use <tt>step<plus> n</tt> and <tt>step- n</tt> to move forward or backward +n+ steps respectively.
You may also use +next+ which is similar to step, but function or method calls that appear within the line of code are executed without stopping. As with step, you may use plus sign to move _n_ steps.
diff --git a/railties/guides/source/documents.yaml b/railties/guides/source/documents.yaml
new file mode 100644
index 0000000000..dccfefb4fb
--- /dev/null
+++ b/railties/guides/source/documents.yaml
@@ -0,0 +1,153 @@
+-
+ name: Start Here
+ documents:
+ -
+ name: Getting Started with Rails
+ url: getting_started.html
+ description: Everything you need to know to install Rails and create your first application.
+-
+ name: Models
+ documents:
+ -
+ name: Rails Database Migrations
+ url: migrations.html
+ description: This guide covers how you can use Active Record migrations to alter your database in a structured and organized manner.
+ -
+ name: Active Record Validations and Callbacks
+ url: active_record_validations_callbacks.html
+ description: This guide covers how you can use Active Record validations and callbacks.
+ -
+ name: Active Record Associations
+ url: association_basics.html
+ description: This guide covers all the associations provided by Active Record.
+ -
+ name: Active Record Query Interface
+ url: active_record_querying.html
+ description: This guide covers the database query interface provided by Active Record.
+-
+ name: Views
+ documents:
+ -
+ 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.
+ -
+ name: Action View Form Helpers
+ url: form_helpers.html
+ description: Guide to using built-in Form helpers.
+-
+ name: Controllers
+ documents:
+ -
+ name: Action Controller Overview
+ url: action_controller_overview.html
+ description: This guide covers how controllers work and how they fit into the request cycle in your application. It includes sessions, filters, and cookies, data streaming, and dealing with exceptions raised by a request, among other topics.
+ -
+ name: Rails Routing from the Outside In
+ url: routing.html
+ description: This guide covers the user-facing features of Rails routing. If you want to understand how to use routing in your own Rails applications, start here.
+-
+ name: Digging Deeper
+ documents:
+ -
+ name: Active Support Core Extensions
+ url: active_support_core_extensions.html
+ description: This guide documents the Ruby core extensions defined in Active Support.
+ -
+ name: Rails Internationalization API
+ url: i18n.html
+ description: This guide covers how to add internationalization to your applications. Your application will be able to translate content to different languages, change pluralization rules, use correct date formats for each country and so on.
+ -
+ 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
+ url: testing.html
+ work_in_progress: true
+ description: This is a rather comprehensive guide to doing both unit and functional tests in Rails. It covers everything from 'What is a test?' to the testing APIs. Enjoy.
+ -
+ name: Securing Rails Applications
+ url: security.html
+ description: This guide describes common security problems in web applications and how to avoid them with Rails.
+ -
+ name: Debugging Rails Applications
+ url: debugging_rails_applications.html
+ description: This guide describes how to debug Rails applications. It covers the different ways of achieving this and how to understand what is happening "behind the scenes" of your code.
+ -
+ name: Performance Testing Rails Applications
+ url: performance_testing.html
+ description: This guide covers the various ways of performance testing a Ruby on Rails application.
+ -
+ name: Configuring Rails Applications
+ url: configuring.html
+ description: This guide covers the basic configuration settings for a Rails application.
+ -
+ name: Rails Command Line Tools and Rake tasks
+ url: command_line.html
+ description: This guide covers the command line tools and rake tasks provided by Rails.
+ -
+ name: Caching with Rails
+ work_in_progress: true
+ url: caching_with_rails.html
+ description: Various caching techniques provided by Rails.
+ -
+ name: Asset Pipeline
+ url: asset_pipeline.html
+ description: This guide documents the asset pipeline.
+ -
+ name: The Rails Initialization Process
+ work_in_progress: true
+ url: initialization.html
+ description: This guide explains the internals of the Rails initialization process as of Rails 3.1
+-
+ name: Extending Rails
+ documents:
+ -
+ name: The Basics of Creating Rails Plugins
+ work_in_progress: true
+ url: plugins.html
+ description: This guide covers how to build a plugin to extend the functionality of Rails.
+ -
+ name: Rails on Rack
+ url: rails_on_rack.html
+ description: This guide covers Rails integration with Rack and interfacing with other Rack components.
+ -
+ name: Creating and Customizing Rails Generators
+ url: generators.html
+ description: This guide covers the process of adding a brand new generator to your extension or providing an alternative to an element of a built-in Rails generator (such as providing alternative test stubs for the scaffold generator).
+-
+ name: Contributing to Ruby on Rails
+ documents:
+ -
+ name: Contributing to Ruby on Rails
+ url: contributing_to_ruby_on_rails.html
+ description: Rails is not 'somebody else's framework.' This guide covers a variety of ways that you can get involved in the ongoing development of Rails.
+ -
+ name: API Documentation Guidelines
+ url: api_documentation_guidelines.html
+ description: This guide documents the Ruby on Rails API documentation guidelines.
+ -
+ name: Ruby on Rails Guides Guidelines
+ url: ruby_on_rails_guides_guidelines.html
+ description: This guide documents the Ruby on Rails guides guidelines.
+-
+ name: Release Notes
+ documents:
+ -
+ name: Ruby on Rails 3.1 Release Notes
+ url: 3_1_release_notes.html
+ description: Release notes for Rails 3.1.
+ -
+ name: Ruby on Rails 3.0 Release Notes
+ url: 3_0_release_notes.html
+ description: Release notes for Rails 3.0.
+ -
+ name: Ruby on Rails 2.3 Release Notes
+ url: 2_3_release_notes.html
+ description: Release notes for Rails 2.3.
+ -
+ name: Ruby on Rails 2.2 Release Notes
+ url: 2_2_release_notes.html
+ description: Release notes for Rails 2.2.
diff --git a/railties/guides/source/form_helpers.textile b/railties/guides/source/form_helpers.textile
index 821bb305f6..64eb2d8f36 100644
--- a/railties/guides/source/form_helpers.textile
+++ b/railties/guides/source/form_helpers.textile
@@ -229,7 +229,7 @@ The corresponding view +app/views/articles/new.html.erb+ using +form_for+ looks
There are a few things to note here:
# +@article+ is the actual object being edited.
-# There is a single hash of options. Routing options are passed in the +:url+ hash, HTML options are passed in the +:html+ hash.
+# There is a single hash of options. Routing options are passed in the +:url+ hash, HTML options are passed in the +:html+ hash. Also you can provide a +:namespace+ option for your form to ensure uniqueness of id attributes on form elements. The namespace attribute will be prefixed with underscore on the generated HTML id.
# The +form_for+ method yields a *form builder* object (the +f+ variable).
# Methods to create form controls are called *on* the form builder object +f+
diff --git a/railties/guides/source/generators.textile b/railties/guides/source/generators.textile
index 7a863ccbc7..d93dcf40bf 100644
--- a/railties/guides/source/generators.textile
+++ b/railties/guides/source/generators.textile
@@ -48,7 +48,7 @@ end
NOTE: +create_file+ is a method provided by +Thor::Actions+. Documentation for +create_file+ and other Thor methods can be found in "Thor's documentation":http://rdoc.info/github/wycats/thor/master/Thor/Actions.html
-Our new generator is quite simple: it inherits from +Rails::Generators::Base+ and has one method definition. Each public method in the generator is executed when a generator is invoked. Finally, we invoke the +create_file+ method that will create a file at the given destination with the given content. If you are familiar with the Rails Application Templates API, you'll feel right at home with the new generators API.
+Our new generator is quite simple: it inherits from +Rails::Generators::Base+ and has one method definition. When a generator is invoked, each public method in the generator is executed sequentially in the order that it is defined. Finally, we invoke the +create_file+ method that will create a file at the given destination with the given content. If you are familiar with the Rails Application Templates API, you'll feel right at home with the new generators API.
To invoke our new generator, we just need to do:
diff --git a/railties/guides/source/getting_started.textile b/railties/guides/source/getting_started.textile
index 8a0a70efad..54f3c74695 100644
--- a/railties/guides/source/getting_started.textile
+++ b/railties/guides/source/getting_started.textile
@@ -41,9 +41,6 @@ internet for learning Ruby, including:
* "Programming Ruby":http://www.ruby-doc.org/docs/ProgrammingRuby/
* "Why's (Poignant) Guide to Ruby":http://mislav.uniqpath.com/poignant-guide/
-Also, the example code for this guide is available in the rails github:https://github.com/rails/rails repository
-in rails/railties/guides/code/getting_started.
-
h3. What is Rails?
TIP: This section goes into the background and philosophy of the Rails framework
@@ -248,7 +245,7 @@ the following:
$ rails --version
</shell>
-If it says something like "Rails 3.1.1" you are ready to continue.
+If it says something like "Rails 3.1.3" you are ready to continue.
h4. Creating the Blog Application
@@ -289,7 +286,7 @@ rundown on the function of each of the files and folders that Rails created by d
|log/|Application log files.|
|public/|The only folder seen to the world as-is. Contains the static files and compiled assets.|
|Rakefile|This file locates and loads tasks that can be run from the command line. The task definitions are defined throughout the components of Rails. Rather than changing Rakefile, you should add your own tasks by adding files to the lib/tasks directory of your application.|
-|README|This is a brief instruction manual for your application. You should edit this file to tell others what your application does, how to set it up, and so on.|
+|README.rdoc|This is a brief instruction manual for your application. You should edit this file to tell others what your application does, how to set it up, and so on.|
|script/|Contains the rails script that starts your app and can contain other scripts you use to deploy or run your application.|
|test/|Unit tests, fixtures, and other test apparatus. These are covered in "Testing Rails Applications":testing.html|
|tmp/|Temporary files|
@@ -308,6 +305,14 @@ manually with the application.
* The +test+ environment is used when running automated tests.
* The +production+ environment is used when you deploy your application for the world to use.
+TIP: You don't have to update the database configurations manually. If you look at the
+options of the application generator, you will see that one of the options
+is named <tt>--database</tt>. This option allows you to choose an adapter from a
+list of the most used relational databases. You can even run the generator
+repeatedly: <tt>cd .. && rails new blog --database=mysql</tt>. When you confirm the overwriting
+ of the +config/database.yml+ file, your application will be configured for MySQL
+instead of SQLite. Detailed examples of the common database connections are below.
+
h5. Configuring an SQLite3 Database
Rails comes with built-in support for "SQLite3":http://www.sqlite.org, which is
@@ -411,14 +416,6 @@ development:
Change the username and password in the +development+ section as appropriate.
-TIP: You don't have to update the database configurations manually. If you look at the
-options of the application generator, you will see that one of the options
-is named <tt>--database</tt>. This option allows you to choose an adapter from a
-list of the most used relational databases. You can even run the generator
-repeatedly: <tt>cd .. && rails new blog --database=mysql</tt>. When you confirm the overwriting
- of the +config/database.yml+ file, your application will be configured for MySQL
-instead of SQLite.
-
h4. Creating the Database
Now that you have your database configured, it's time to have Rails create an
@@ -450,6 +447,8 @@ start a web server on your development machine. You can do this by running:
$ rails server
</shell>
+TIP: Compiling CoffeeScript to JavaScript requires a JavaScript runtime and the absence of a runtime will give you an +execjs+ error. Usually Mac OS X and Windows come with a JavaScript runtime installed. +therubyracer+ and +therubyrhino+ are the commonly used runtimes for Ruby and JRuby respectively. You can also investigate a list of runtimes at "ExecJS":https://github.com/sstephenson/execjs.
+
This will fire up an instance of the WEBrick web server by default (Rails can
also use several other web servers). To see your application in action, open a
browser window and navigate to "http://localhost:3000":http://localhost:3000.
diff --git a/railties/guides/source/i18n.textile b/railties/guides/source/i18n.textile
index 2d4cc13571..16ad35f345 100644
--- a/railties/guides/source/i18n.textile
+++ b/railties/guides/source/i18n.textile
@@ -231,7 +231,7 @@ end
Now, when you call the +books_path+ method you should get +"/en/books"+ (for the default locale). An URL like +http://localhost:3001/nl/books+ should load the Netherlands locale, then, and following calls to +books_path+ should return +"/nl/books"+ (because the locale changed).
-If you don't want to force the use of a locale in your routes you can use an optional path scope (donated by the use brackets) like so:
+If you don't want to force the use of a locale in your routes you can use an optional path scope (denoted by the parentheses) like so:
<ruby>
# config/routes.rb
@@ -825,7 +825,7 @@ h5. Active Record Methods
* +ActiveRecord::Errors#generate_message+ (which is used by Active Record validations but may also be used manually) uses +model_name.human+ and +human_attribute_name+ (see above). It also translates the error message and supports translations for inherited class names as explained above in "Error message scopes".
-*+ ActiveRecord::Errors#full_messages+ prepends the attribute name to the error message using a separator that will be looked up from "activerecord.errors.format.separator":https://github.com/rails/rails/blob/master/actionpack/lib/action_view/locale/en.yml#L91 (and which defaults to +'&nbsp;'+).
+* +ActiveRecord::Errors#full_messages+ prepends the attribute name to the error message using a separator that will be looked up from "activerecord.errors.format.separator":https://github.com/rails/rails/blob/master/actionpack/lib/action_view/locale/en.yml#L91 (and which defaults to +'&nbsp;'+).
h5. Active Support Methods
diff --git a/railties/guides/source/index.html.erb b/railties/guides/source/index.html.erb
index c9a8c4fa5c..5439459b42 100644
--- a/railties/guides/source/index.html.erb
+++ b/railties/guides/source/index.html.erb
@@ -3,189 +3,28 @@ Ruby on Rails Guides
<% end %>
<% content_for :header_section do %>
-<h2>Ruby on Rails Guides (<%= ENV['RAILS_VERSION'] || 'edge' %>)</h2>
-
-<% if @edge %>
-<p>
- These are <b>Edge Guides</b>, based on the current
- <a href="https://github.com/rails/rails/tree/master">master branch</a>.
-</p>
-<p>
- If you are looking for the ones for the stable version please check
- <a href="http://guides.rubyonrails.org">http://guides.rubyonrails.org</a> instead.
-</p>
-<% else %>
-<p>
- These are the new guides for Rails 3. The guides for Rails 2.3 are still available
- at <a href="http://guides.rubyonrails.org/v2.3.11/">http://guides.rubyonrails.org/v2.3.11/</a>.
-</p>
-<% end %>
-<p>
- These guides are designed to make you immediately productive with Rails,
- and to help you understand how all of the pieces fit together.
-</p>
-
+<%= render 'welcome' %>
<% end %>
<% content_for :index_section do %>
<div id="subCol">
<dl>
+ <dd class="kindle">Rails Guides are also available for the <%= link_to 'Kindle', 'https://kindle.amazon.com' %>
+and <%= link_to 'Free Kindle Reading Apps', 'http://www.amazon.com/gp/kindle/kcp' %> for the iPad,
+iPhone, Mac, Android, etc. Download them from <%= link_to 'here', @mobi %>.
+ </dd>
<dd class="work-in-progress">Guides marked with this icon are currently being worked on. While they might still be useful to you, they may contain incomplete information and even errors. You can help by reviewing them and posting your comments and corrections to the author.</dd>
</dl>
</div>
<% end %>
-<h3>Start Here</h3>
-
-<dl>
-<%= guide('Getting Started with Rails', 'getting_started.html') do %>
- <p>Everything you need to know to install Rails and create your first application.</p>
-<% end %>
-</dl>
-
-<h3>Models</h3>
-
-<dl>
-<%= guide("Rails Database Migrations", 'migrations.html') do %>
- <p>This guide covers how you can use Active Record migrations to alter your database in a structured and organized manner.</p>
-<% end %>
-
-<%= guide("Active Record Validations and Callbacks", 'active_record_validations_callbacks.html') do %>
- <p>This guide covers how you can use Active Record validations and callbacks.</p>
-<% end %>
-
-<%= guide("Active Record Associations", 'association_basics.html') do %>
- <p>This guide covers all the associations provided by Active Record.</p>
-<% end %>
-
-<%= guide("Active Record Query Interface", 'active_record_querying.html') do %>
- <p>This guide covers the database query interface provided by Active Record.</p>
-<% end %>
-</dl>
-
-<h3>Views</h3>
-
-<dl>
-<%= guide("Layouts and Rendering in Rails", 'layouts_and_rendering.html') do %>
- <p>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.</p>
-<% end %>
-
-<%= guide("Action View Form Helpers", 'form_helpers.html', :work_in_progress => true) do %>
- <p>Guide to using built-in Form helpers.</p>
-<% end %>
-</dl>
-
-<h3>Controllers</h3>
-
-<dl>
-<%= guide("Action Controller Overview", 'action_controller_overview.html') do %>
- <p>This guide covers how controllers work and how they fit into the request cycle in your application. It includes sessions, filters, and cookies, data streaming, and dealing with exceptions raised by a request, among other topics.</p>
-<% end %>
-
-<%= guide("Rails Routing from the Outside In", 'routing.html') do %>
- <p>This guide covers the user-facing features of Rails routing. If you want to understand how to use routing in your own Rails applications, start here.</p>
-<% end %>
-</dl>
-
-<h3>Digging Deeper</h3>
-
-<dl>
-
-<%= guide("Active Support Core Extensions", 'active_support_core_extensions.html') do %>
- <p>This guide documents the Ruby core extensions defined in Active Support.</p>
-<% end %>
-
-<%= guide("Rails Internationalization API", 'i18n.html') do %>
- <p>This guide covers how to add internationalization to your applications. Your application will be able to translate content to different languages, change pluralization rules, use correct date formats for each country and so on.</p>
-<% end %>
-
-<%= guide("Action Mailer Basics", 'action_mailer_basics.html', :work_in_progress => true) do %>
- <p>This guide describes how to use Action Mailer to send and receive emails.</p>
-<% end %>
-
-<%= guide("Testing Rails Applications", 'testing.html', :work_in_progress => true) do %>
- <p>This is a rather comprehensive guide to doing both unit and functional tests in Rails. It covers everything from &quot;What is a test?&quot; to the testing APIs. Enjoy.</p>
-<% end %>
-
-<%= guide("Securing Rails Applications", 'security.html') do %>
- <p>This guide describes common security problems in web applications and how to avoid them with Rails.</p>
-<% end %>
-
-<%= guide("Debugging Rails Applications", 'debugging_rails_applications.html') do %>
- <p>This guide describes how to debug Rails applications. It covers the different ways of achieving this and how to understand what is happening "behind the scenes" of your code.</p>
-<% end %>
-
-<%= guide("Performance Testing Rails Applications", 'performance_testing.html') do %>
- <p>This guide covers the various ways of performance testing a Ruby on Rails application.</p>
-<% end %>
-
-<%= guide("Configuring Rails Applications", 'configuring.html') do %>
- <p>This guide covers the basic configuration settings for a Rails application.</p>
-<% end %>
-
-<%= guide("Rails Command Line Tools and Rake tasks", 'command_line.html') do %>
- <p>This guide covers the command line tools and rake tasks provided by Rails.</p>
-<% end %>
-
-<%= guide("Caching with Rails", 'caching_with_rails.html', :work_in_progress => true) do %>
- <p>Various caching techniques provided by Rails.</p>
-<% end %>
-
-<%= guide('Asset Pipeline', 'asset_pipeline.html') do %>
- <p>This guide documents the asset pipeline.</p>
-<% end %>
-</dl>
-
-<h3>Extending Rails</h3>
-
-<dl>
- <%= guide("The Basics of Creating Rails Plugins", 'plugins.html', :work_in_progress => true) do %>
- <p>This guide covers how to build a plugin to extend the functionality of Rails.</p>
- <% end %>
-
- <%= guide("Rails on Rack", 'rails_on_rack.html') do %>
- <p>This guide covers Rails integration with Rack and interfacing with other Rack components.</p>
- <% end %>
-
- <%= guide("Creating and Customizing Rails Generators", 'generators.html') do %>
- <p>This guide covers the process of adding a brand new generator to your extension
- or providing an alternative to an element of a built-in Rails generator (such as
- providing alternative test stubs for the scaffold generator).</p>
- <% end %>
-</dl>
-
-<h3>Contributing to Ruby on Rails</h3>
-
-<dl>
- <%= guide("Contributing to Ruby on Rails", 'contributing_to_ruby_on_rails.html') do %>
- <p>Rails is not &quot;somebody else's framework.&quot; This guide covers a variety of ways that you can get involved in the ongoing development of Rails.</p>
- <% end %>
-
- <%= guide('API Documentation Guidelines', 'api_documentation_guidelines.html') do %>
- <p>This guide documents the Ruby on Rails API documentation guidelines.</p>
- <% end %>
-
- <%= guide('Ruby on Rails Guides Guidelines', 'ruby_on_rails_guides_guidelines.html') do %>
- <p>This guide documents the Ruby on Rails guides guidelines.</p>
- <% end %>
-</dl>
-
-<h3>Release Notes</h3>
-
-<dl>
-<%= guide("Ruby on Rails 3.1 Release Notes", '3_1_release_notes.html') do %>
- <p>Release notes for Rails 3.1.</p>
-<% end %>
-
-<%= guide("Ruby on Rails 3.0 Release Notes", '3_0_release_notes.html') do %>
- <p>Release notes for Rails 3.0.</p>
-<% end %>
-
-<%= guide("Ruby on Rails 2.3 Release Notes", '2_3_release_notes.html') do %>
- <p>Release notes for Rails 2.3.</p>
-<% end %>
-
-<%= guide("Ruby on Rails 2.2 Release Notes", '2_2_release_notes.html') do %>
- <p>Release notes for Rails 2.2.</p>
+<% documents_by_section.each do |section| %>
+ <h3><%= section['name'] %></h3>
+ <dl>
+ <% section['documents'].each do |document| %>
+ <%= guide(document['name'], document['url'], :work_in_progress => document['work_in_progress']) do %>
+ <p><%= document['description'] %></p>
+ <% end %>
+ <% end %>
+ </dl>
<% end %>
-</dl>
diff --git a/railties/guides/source/initialization.textile b/railties/guides/source/initialization.textile
index 036b356a37..5ae9cf0f2b 100644
--- a/railties/guides/source/initialization.textile
+++ b/railties/guides/source/initialization.textile
@@ -17,7 +17,7 @@ As of Rails 3, +script/server+ has become +rails server+. This was done to centr
h4. +bin/rails+
-The actual +rails+ command is kept in _bin/rails_ at the and goes like this:
+The actual +rails+ command is kept in _bin/rails_:
<ruby>
#!/usr/bin/env ruby
@@ -31,7 +31,7 @@ rescue LoadError
end
</ruby>
-This file will attempt to load +rails/cli+ and if it cannot find it then add the +railties/lib+ path to the load path (+$:+) and will then try to require it again.
+This file will attempt to load +rails/cli+. If it cannot find it then +railties/lib+ is added to the load path (+$:+) before retrying.
h4. +railties/lib/rails/cli.rb+
@@ -56,7 +56,7 @@ else
end
</ruby>
-The +rbconfig+ file here is out of Ruby's standard library and provides us with the +RbConfig+ class which contains useful information dependent on how Ruby was compiled. We'll see this in use in +railties/lib/rails/script_rails_loader+.
+The +rbconfig+ file from the Ruby standard library provides us with the +RbConfig+ class which contains detailed information about the Ruby environment, including how Ruby was compiled. We can see this in use in +railties/lib/rails/script_rails_loader+.
<ruby>
require 'pathname'
@@ -71,7 +71,7 @@ module Rails
end
</ruby>
-The +rails/script_rails_loader+ file uses +RbConfig::Config+ to gather up the +bin_dir+ and +ruby_install_name+ values for the configuration which will result in a path such as +/System/Library/Frameworks/Ruby.framework/Versions/1.8/usr/bin/ruby+, which is the default path on Mac OS X. If you're running Windows the path may be something such as +C:/Ruby192/bin/ruby+. Anyway, the path on your system may be different, but the point of this is that it will point at the known ruby executable location for your install. The +RbConfig::CONFIG["EXEEXT"]+ will suffix this path with ".exe" if the script is running on Windows. This constant is used later on in +exec_script_rails!+. As for the +SCRIPT_RAILS+ constant, we'll see that when we get to the +in_rails_application?+ method.
+The +rails/script_rails_loader+ file uses +RbConfig::Config+ to obtain the +bin_dir+ and +ruby_install_name+ values for the configuration which together form the path to the Ruby interpreter. The +RbConfig::CONFIG["EXEEXT"]+ will suffix this path with ".exe" if the script is running on Windows. This constant is used later on in +exec_script_rails!+. As for the +SCRIPT_RAILS+ constant, we'll see that when we get to the +in_rails_application?+ method.
Back in +rails/cli+, the next line is this:
@@ -79,7 +79,7 @@ Back in +rails/cli+, the next line is this:
Rails::ScriptRailsLoader.exec_script_rails!
</ruby>
-This method is defined in +rails/script_rails_loader+ like this:
+This method is defined in +rails/script_rails_loader+:
<ruby>
def self.exec_script_rails!
@@ -96,7 +96,7 @@ rescue SystemCallError
end
</ruby>
-This method will first check if the current working directory (+cwd+) is a Rails application or is a subdirectory of one. The way to determine this is defined in the +in_rails_application?+ method like this:
+This method will first check if the current working directory (+cwd+) is a Rails application or a subdirectory of one. This is determined by the +in_rails_application?+ method:
<ruby>
def self.in_rails_application?
@@ -104,7 +104,7 @@ def self.in_rails_application?
end
</ruby>
-The +SCRIPT_RAILS+ constant defined earlier is used here, with +File.exists?+ checking for its presence in the current directory. If this method returns +false+, then +in_rails_application_subdirectory?+ will be used:
+The +SCRIPT_RAILS+ constant defined earlier is used here, with +File.exists?+ checking for its presence in the current directory. If this method returns +false+ then +in_rails_application_subdirectory?+ will be used:
<ruby>
def self.in_rails_application_subdirectory?(path = Pathname.new(Dir.pwd))
@@ -112,17 +112,17 @@ def self.in_rails_application_subdirectory?(path = Pathname.new(Dir.pwd))
end
</ruby>
-This climbs the directory tree until it reaches a path which contains a +script/rails+ file. If a directory is reached which contains this file then this line will run:
+This climbs the directory tree until it reaches a path which contains a +script/rails+ file. If a directory containing this file is reached then this line will run:
<ruby>
exec RUBY, SCRIPT_RAILS, *ARGV if in_rails_application?
</ruby>
-This is effectively the same as doing +ruby script/rails [arguments]+. Where +[arguments]+ at this point in time is simply "server".
+This is effectively the same as running +ruby script/rails [arguments]+, where +[arguments]+ at this point in time is simply "server".
h4. +script/rails+
-This file looks like this:
+This file is as follows:
<ruby>
APP_PATH = File.expand_path('../../config/application', __FILE__)
@@ -130,7 +130,7 @@ require File.expand_path('../../config/boot', __FILE__)
require 'rails/commands'
</ruby>
-The +APP_PATH+ constant here will be used later in +rails/commands+. The +config/boot+ file that +script/rails+ references is the +config/boot.rb+ file in our application which is responsible for loading Bundler and setting it up.
+The +APP_PATH+ constant will be used later in +rails/commands+. The +config/boot+ file referenced here is the +config/boot.rb+ file in our application which is responsible for loading Bundler and setting it up.
h4. +config/boot.rb+
diff --git a/railties/guides/source/kindle/KINDLE.md b/railties/guides/source/kindle/KINDLE.md
new file mode 100644
index 0000000000..a7d9a4e4cf
--- /dev/null
+++ b/railties/guides/source/kindle/KINDLE.md
@@ -0,0 +1,26 @@
+# Rails Guides on the Kindle
+
+
+## Synopsis
+
+ 1. Obtain `kindlegen` from the link below and put the binary in your path
+ 2. Run `KINDLE=1 rake generate_guides` to generate the guides and compile the `.mobi` file
+ 3. Copy `output/kindle/rails_guides.mobi` to your Kindle
+
+## Resources
+
+ * [StackOverflow: Kindle Periodical Format](http://stackoverflow.com/questions/5379565/kindle-periodical-format)
+ * Example Periodical [.ncx](https://gist.github.com/808c971ed087b839d462) and [.opf](https://gist.github.com/d6349aa8488eca2ee6d0)
+ * [Kindle Publishing guidelines](http://kindlegen.s3.amazonaws.com/AmazonKindlePublishingGuidelines.pdf)
+ * [KindleGen & Kindle Previewer](http://www.amazon.com/gp/feature.html?ie=UTF8&docId=1000234621)
+
+## TODO
+
+### Post release
+
+ * Integrate generated Kindle document in to published HTML guides
+ * Tweak heading styles (most docs use h3/h4/h5, which end up being smaller than the text under it)
+ * Tweak table styles (smaller text? Many of the tables are unusable on a Kindle in portrait mode)
+ * Have the HTML/XML TOC 'drill down' into the TOCs of the individual guides
+ * `.epub` generation.
+
diff --git a/railties/guides/source/kindle/copyright.html.erb b/railties/guides/source/kindle/copyright.html.erb
new file mode 100644
index 0000000000..bd51d87383
--- /dev/null
+++ b/railties/guides/source/kindle/copyright.html.erb
@@ -0,0 +1 @@
+<%= render 'license' %> \ No newline at end of file
diff --git a/railties/guides/source/kindle/layout.html.erb b/railties/guides/source/kindle/layout.html.erb
new file mode 100644
index 0000000000..f0a286210b
--- /dev/null
+++ b/railties/guides/source/kindle/layout.html.erb
@@ -0,0 +1,27 @@
+<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
+
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
+<head>
+<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
+
+<title><%= yield(:page_title) || 'Ruby on Rails Guides' %></title>
+
+<link rel="stylesheet" type="text/css" href="stylesheets/kindle.css" />
+
+</head>
+<body class="guide">
+
+ <% if content_for? :header_section %>
+ <%= yield :header_section %>
+ <div class="pagebreak">
+ <% end %>
+
+ <% if content_for? :index_section %>
+ <%= yield :index_section %>
+ <div class="pagebreak">
+ <% end %>
+
+ <%= yield.html_safe %>
+</body>
+</html>
diff --git a/railties/guides/source/kindle/rails_guides.opf.erb b/railties/guides/source/kindle/rails_guides.opf.erb
new file mode 100644
index 0000000000..4e07664fd0
--- /dev/null
+++ b/railties/guides/source/kindle/rails_guides.opf.erb
@@ -0,0 +1,52 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<package xmlns="http://www.idpf.org/2007/opf" version="2.0" unique-identifier="RailsGuides">
+<metadata>
+ <meta name="cover" content="cover" />
+ <dc-metadata xmlns:dc="http://purl.org/dc/elements/1.1/">
+
+ <dc:title>Ruby on Rails Guides (<%= @version %>)</dc:title>
+
+ <dc:language>en-us</dc:language>
+ <dc:creator>Ruby on Rails</dc:creator>
+ <dc:publisher>Ruby on Rails</dc:publisher>
+ <dc:subject>Reference</dc:subject>
+ <dc:date><%= Time.now.strftime('%Y-%m-%d') %></dc:date>
+
+ <dc:description>These guides are designed to make you immediately productive with Rails, and to help you understand how all of the pieces fit together.</dc:description>
+ </dc-metadata>
+ <x-metadata>
+ <output content-type="application/x-mobipocket-subscription-magazine" encoding="utf-8"/>
+ </x-metadata>
+</metadata>
+
+<manifest>
+ <!-- HTML content files [mandatory] -->
+ <% documents_flat.each do |document| %>
+ <item id="<%= document['url'] %>" media-type="text/html" href="<%= document['url'] %>" />
+ <% end %>
+
+ <% %w{toc.html credits.html welcome.html copyright.html}.each do |url| %>
+ <item id="<%= url %>" media-type="text/html" href="<%= url %>" />
+ <% end %>
+
+ <item id="toc" media-type="application/x-dtbncx+xml" href="toc.ncx" />
+
+ <item id="cover" media-type="image/jpeg" href="images/rails_guides_kindle_cover.jpg"/>
+</manifest>
+
+<spine toc="toc">
+ <itemref idref="toc.html" />
+ <itemref idref="welcome.html" />
+ <itemref idref="credits.html" />
+ <itemref idref="copyright.html" />
+ <% documents_flat.each do |document| %>
+ <itemref idref="<%= document['url'] %>" />
+ <% end %>
+</spine>
+
+<guide>
+ <reference type="toc" title="Table of Contents" href="toc.html"></reference>
+</guide>
+
+</package>
diff --git a/railties/guides/source/kindle/toc.html.erb b/railties/guides/source/kindle/toc.html.erb
new file mode 100644
index 0000000000..e013797dee
--- /dev/null
+++ b/railties/guides/source/kindle/toc.html.erb
@@ -0,0 +1,24 @@
+<% content_for :page_title do %>
+Ruby on Rails Guides
+<% end %>
+
+<h1>Table of Contents</h1>
+<div id="toc">
+ <ul><li><a href="welcome.html">Welcome</a></li></ul>
+<% documents_by_section.each_with_index do |section, i| %>
+ <h3><%= "#{i + 1}." %> <%= section['name'] %></h3>
+ <ul>
+ <% section['documents'].each do |document| %>
+ <li>
+ <a href="<%= document['url'] %>"><%= document['name'] %></a>
+ <% if document['work_in_progress']%>(WIP)<% end %>
+ </li>
+ <% end %>
+ </ul>
+<% end %>
+<hr />
+<ul>
+ <li><a href="credits.html">Credits</a></li>
+ <li><a href="copyright.html">Copyright &amp; License</a></li>
+<ul>
+</div>
diff --git a/railties/guides/source/kindle/toc.ncx.erb b/railties/guides/source/kindle/toc.ncx.erb
new file mode 100644
index 0000000000..2c6d8e3bdf
--- /dev/null
+++ b/railties/guides/source/kindle/toc.ncx.erb
@@ -0,0 +1,64 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE ncx PUBLIC "-//NISO//DTD ncx 2005-1//EN"
+ "http://www.daisy.org/z3986/2005/ncx-2005-1.dtd">
+
+<ncx xmlns="http://www.daisy.org/z3986/2005/ncx/" version="2005-1" xml:lang="en-US">
+<head>
+ <meta name="dtb:uid" content="RailsGuides"/>
+ <meta name="dtb:depth" content="2"/>
+ <meta name="dtb:totalPageCount" content="0"/>
+ <meta name="dtb:maxPageNumber" content="0"/>
+</head>
+<docTitle><text>Ruby on Rails Guides</text></docTitle>
+<docAuthor><text>docrails</text></docAuthor>
+<navMap>
+ <navPoint playOrder="0" class="periodical" id="periodical">
+ <navLabel>
+ <text>Table of Contents</text>
+ </navLabel>
+ <content src="toc.html"/>
+
+ <navPoint class="section" id="welcome" playOrder="1">
+ <navLabel>
+ <text>Introduction</text>
+ </navLabel>
+ <content src="welcome.html"/>
+
+ <navPoint class="article" id="welcome" playOrder="2">
+ <navLabel>
+ <text>Welcome</text>
+ </navLabel>
+ <content src="welcome.html"/>
+ </navPoint>
+ <navPoint class="article" id="credits" playOrder="3">
+ <navLabel><text>Credits</text></navLabel>
+ <content src="credits.html">
+ </navPoint>
+ <navPoint class="article" id="copyright" playOrder="4">
+ <navLabel><text>Copyright &amp; License</text></navLabel>
+ <content src="copyright.html">
+ </navPoint>
+ </navPoint>
+
+ <% play_order = 4 %>
+ <% documents_by_section.each_with_index do |section, section_no| %>
+ <navPoint class="section" id="chapter_<%= section_no + 1 %>" playOrder="<% play_order +=1 %>">
+ <navLabel>
+ <text><%= section['name'] %></text>
+ </navLabel>
+ <content src="<%=section['documents'].first['url'] %>"/>
+
+ <% section['documents'].each_with_index do |document, document_no| %>
+ <navPoint class="article" id="_<%=section_no+1%>.<%=document_no+1%>" playOrder="<%=play_order +=1 %>">
+ <navLabel>
+ <text><%= document['name'] %></text>
+ </navLabel>
+ <content src="<%=document['url'] %>"/>
+ </navPoint>
+ <% end %>
+ </navPoint>
+ <% end %>
+
+ </navPoint>
+</navMap>
+</ncx>
diff --git a/railties/guides/source/kindle/welcome.html.erb b/railties/guides/source/kindle/welcome.html.erb
new file mode 100644
index 0000000000..e30704c4e6
--- /dev/null
+++ b/railties/guides/source/kindle/welcome.html.erb
@@ -0,0 +1,5 @@
+<%= render 'welcome' %>
+
+<h3>Kindle Edition</h3>
+
+The Kindle Edition of the Rails Guides should be considered a work in progress. Feedback is really welcome, please see the "Feedback" section at the end of each guide for instructions.
diff --git a/railties/guides/source/layout.html.erb b/railties/guides/source/layout.html.erb
index 4c979888b7..e69936b43a 100644
--- a/railties/guides/source/layout.html.erb
+++ b/railties/guides/source/layout.html.erb
@@ -143,8 +143,7 @@
<hr class="hide" />
<div id="footer">
<div class="wrapper">
- <p>This work is licensed under a <a href="http://creativecommons.org/licenses/by-sa/3.0/">Creative Commons Attribution-Share Alike 3.0</a> License</p>
- <p>"Rails", "Ruby on Rails", and the Rails logo are trademarks of David Heinemeier Hansson. All rights reserved.</p>
+ <%= render 'license' %>
</div>
</div>
diff --git a/railties/guides/source/layouts_and_rendering.textile b/railties/guides/source/layouts_and_rendering.textile
index df7b9b364c..5cff2d0893 100644
--- a/railties/guides/source/layouts_and_rendering.textile
+++ b/railties/guides/source/layouts_and_rendering.textile
@@ -495,7 +495,7 @@ def show
end
</ruby>
-Make sure to use +and return+ and not +&amp;&amp; return+, since +&amp;&amp; return+ will not work due to the operator precedence in the Ruby Language.
+Make sure to use +and return+ instead of +&amp;&amp; return+ because +&amp;&amp; return+ will not work due to the operator precedence in the Ruby Language.
Note that the implicit render done by ActionController detects if +render+ has been called, so the following will work without errors:
@@ -671,19 +671,33 @@ There are three tag options available for the +auto_discovery_link_tag+:
h5. Linking to JavaScript Files with the +javascript_include_tag+
-The +javascript_include_tag+ helper returns an HTML +script+ tag for each source provided. Rails looks in +public/javascripts+ for these files by default, but you can specify a full path relative to the document root, or a URL, if you prefer. For example, to include +public/javascripts/main.js+:
+The +javascript_include_tag+ helper returns an HTML +script+ tag for each source provided.
+
+If you are using Rails with the "Asset Pipeline":asset_pipeline.html enabled, this helper will generate a link to +/assets/javascripts/+ rather than +public/javascripts+ which was used in earlier versions of Rails. This link is then served by the Sprockets gem, which was introduced in Rails 3.1.
+
+A JavaScript file within a Rails application or Rails engine goes in one of three locations: +app/assets+, +lib/assets+ or +vendor/assets+. These locations are explained in detail in the "Asset Organization section in the Asset Pipeline Guide":asset_pipeline.html#asset-organization
+
+You can specify a full path relative to the document root, or a URL, if you prefer. For example, to link to a JavaScript file that is inside a directory called +javascripts+ inside of one of +app/assets+, +lib/assets+ or +vendor/assets+, you would do this:
<erb>
<%= javascript_include_tag "main" %>
</erb>
-To include +public/javascripts/main.js+ and +public/javascripts/columns.js+:
+Rails will then output a +script+ tag such as this:
+
+<html>
+<script src='/assets/main.js' type="text/javascript"></script>
+</html>
+
+The request to this asset is then served by the Sprockets gem.
+
+To include multiple files such as +app/assets/javascripts/main.js+ and +app/assets/javascripts/columns.js+ at the same time:
<erb>
<%= javascript_include_tag "main", "columns" %>
</erb>
-To include +public/javascripts/main.js+ and +public/photos/columns.js+:
+To include +app/assets/javascripts/main.js+ and +app/assets/javascripts/photos/columns.js+:
<erb>
<%= javascript_include_tag "main", "/photos/columns" %>
@@ -701,15 +715,38 @@ If the application does not use the asset pipeline, the +:defaults+ option loads
<%= javascript_include_tag :defaults %>
</erb>
-And you can in any case override the expansion in <tt>config/application.rb</tt>:
+Outputting +script+ tags such as this:
+
+<html>
+<script src="/javascripts/jquery.js" type="text/javascript"></script>
+<script src="/javascripts/jquery_ujs.js" type="text/javascript"></script>
+</html>
+
+These two files for jQuery, +jquery.js+ and +jquery_ujs.js+ must be placed inside +public/javascripts+ if the application doesn't use the asset pipeline. These files can be downloaded from the "jquery-rails repository on GitHub":https://github.com/indirect/jquery-rails/tree/master/vendor/assets/javascripts
+
+WARNING: If you are using the asset pipeline, this tag will render a +script+ tag for an asset called +defaults.js+, which would not exist in your application unless you've explicitly defined it to be.
+
+And you can in any case override the +:defaults+ expansion in <tt>config/application.rb</tt>:
<ruby>
config.action_view.javascript_expansions[:defaults] = %w(foo.js bar.js)
</ruby>
-When using <tt>:defaults</tt>, if an <tt>application.js</tt> file exists in <tt>public/javascripts</tt> it will be included as well at then end.
+You can also define new defaults:
+
+<ruby>
+config.action_view.javascript_expansions[:projects] = %w(projects.js tickets.js)
+</ruby>
+
+And use them by referencing them exactly like +:defaults+:
-Also, the +:all+ option loads every JavaScript file in +public/javascripts+:
+<erb>
+<%= javascript_include_tag :projects %>
+</erb>
+
+When using <tt>:defaults</tt>, if an <tt>application.js</tt> file exists in <tt>public/javascripts</tt> it will be included as well at the end.
+
+Also, if the asset pipeline is disabled, the +:all+ expansion loads every JavaScript file in +public/javascripts+:
<erb>
<%= javascript_include_tag :all %>
@@ -740,19 +777,23 @@ You can even use dynamic paths such as +cache/#{current_site}/main/display+.
h5. Linking to CSS Files with the +stylesheet_link_tag+
-The +stylesheet_link_tag+ helper returns an HTML +&lt;link&gt;+ tag for each source provided. Rails looks in +public/stylesheets+ for these files by default, but you can specify a full path relative to the document root, or a URL, if you prefer. For example, to include +public/stylesheets/main.css+:
+The +stylesheet_link_tag+ helper returns an HTML +&lt;link&gt;+ tag for each source provided.
+
+If you are using Rails with the "Asset Pipeline" enabled, this helper will generate a link to +/assets/stylesheets/+. This link is then processed by the Sprockets gem. A stylesheet file can be stored in one of three locations: +app/assets+, +lib/assets+ or +vendor/assets+.
+
+You can specify a full path relative to the document root, or a URL. For example, to link to a stylesheet file that is inside a directory called +stylesheets+ inside of one of +app/assets+, +lib/assets+ or +vendor/assets+, you would do this:
<erb>
<%= stylesheet_link_tag "main" %>
</erb>
-To include +public/stylesheets/main.css+ and +public/stylesheets/columns.css+:
+To include +app/assets/stylesheets/main.css+ and +app/assets/stylesheets/columns.css+:
<erb>
<%= stylesheet_link_tag "main", "columns" %>
</erb>
-To include +public/stylesheets/main.css+ and +public/photos/columns.css+:
+To include +app/assets/stylesheets/main.css+ and +app/assets/stylesheets/photos/columns.css+:
<erb>
<%= stylesheet_link_tag "main", "/photos/columns" %>
@@ -770,7 +811,7 @@ By default, the +stylesheet_link_tag+ creates links with +media="screen" rel="st
<%= stylesheet_link_tag "main_print", :media => "print" %>
</erb>
-The +all+ option links every CSS file in +public/stylesheets+:
+If the asset pipeline is disabled, the +all+ option links every CSS file in +public/stylesheets+:
<erb>
<%= stylesheet_link_tag :all %>
diff --git a/railties/guides/source/migrations.textile b/railties/guides/source/migrations.textile
index 23e36b39f9..66160f8b26 100644
--- a/railties/guides/source/migrations.textile
+++ b/railties/guides/source/migrations.textile
@@ -1,12 +1,24 @@
h2. Migrations
-Migrations are a convenient way for you to alter your database in a structured and organized manner. You could edit fragments of SQL by hand but you would then be responsible for telling other developers that they need to go and run them. You'd also have to keep track of which changes need to be run against the production machines next time you deploy.
-
-Active Record tracks which migrations have already been run so all you have to do is update your source and run +rake db:migrate+. Active Record will work out which migrations should be run. It will also update your +db/schema.rb+ file to match the structure of your database.
-
-Migrations also allow you to describe these transformations using Ruby. The great thing about this is that (like most of Active Record's functionality) it is database independent: you don't need to worry about the precise syntax of +CREATE TABLE+ any more than you worry about variations on +SELECT *+ (you can drop down to raw SQL for database specific features). For example you could use SQLite3 in development, but MySQL in production.
-
-You'll learn all about migrations including:
+Migrations are a convenient way for you to alter your database in a structured
+and organized manner. You could edit fragments of SQL by hand but you would then
+be responsible for telling other developers that they need to go and run them.
+You'd also have to keep track of which changes need to be run against the
+production machines next time you deploy.
+
+Active Record tracks which migrations have already been run so all you have to
+do is update your source and run +rake db:migrate+. Active Record will work out
+which migrations should be run. It will also update your +db/schema.rb+ file to
+match the structure of your database.
+
+Migrations also allow you to describe these transformations using Ruby. The
+great thing about this is that (like most of Active Record's functionality) it
+is database independent: you don't need to worry about the precise syntax of
++CREATE TABLE+ any more than you worry about variations on +SELECT *+ (you can
+drop down to raw SQL for database specific features). For example you could use
+SQLite3 in development, but MySQL in production.
+
+In this guide, you'll learn all about migrations including:
* The generators you can use to create them
* The methods Active Record provides to manipulate your database
@@ -17,7 +29,8 @@ endprologue.
h3. Anatomy of a Migration
-Before we dive into the details of a migration, here are a few examples of the sorts of things you can do:
+Before we dive into the details of a migration, here are a few examples of the
+sorts of things you can do:
<ruby>
class CreateProducts < ActiveRecord::Migration
@@ -36,9 +49,15 @@ class CreateProducts < ActiveRecord::Migration
end
</ruby>
-This migration adds a table called +products+ with a string column called +name+ and a text column called +description+. A primary key column called +id+ will also be added, however since this is the default we do not need to ask for this. The timestamp columns +created_at+ and +updated_at+ which Active Record populates automatically will also be added. Reversing this migration is as simple as dropping the table.
+This migration adds a table called +products+ with a string column called +name+
+and a text column called +description+. A primary key column called +id+ will
+also be added, however since this is the default we do not need to ask for this.
+The timestamp columns +created_at+ and +updated_at+ which Active Record
+populates automatically will also be added. Reversing this migration is as
+simple as dropping the table.
-Migrations are not limited to changing the schema. You can also use them to fix bad data in the database or populate new fields:
+Migrations are not limited to changing the schema. You can also use them to fix
+bad data in the database or populate new fields:
<ruby>
class AddReceiveNewsletterToUsers < ActiveRecord::Migration
@@ -55,12 +74,18 @@ class AddReceiveNewsletterToUsers < ActiveRecord::Migration
end
</ruby>
-NOTE: Some "caveats":#using-models-in-your-migrations apply to using models in your migrations.
+NOTE: Some "caveats":#using-models-in-your-migrations apply to using models in
+your migrations.
-This migration adds a +receive_newsletter+ column to the +users+ table. We want it to default to +false+ for new users, but existing users are considered
-to have already opted in, so we use the User model to set the flag to +true+ for existing users.
+This migration adds a +receive_newsletter+ column to the +users+ table. We want
+it to default to +false+ for new users, but existing users are considered to
+have already opted in, so we use the User model to set the flag to +true+ for
+existing users.
-Rails 3.1 makes migrations smarter by providing a new <tt>change</tt> method. This method is preferred for writing constructive migrations (adding columns or tables). The migration knows how to migrate your database and reverse it when the migration is rolled back without the need to write a separate +down+ method.
+Rails 3.1 makes migrations smarter by providing a new <tt>change</tt> method.
+This method is preferred for writing constructive migrations (adding columns or
+tables). The migration knows how to migrate your database and reverse it when
+the migration is rolled back without the need to write a separate +down+ method.
<ruby>
class CreateProducts < ActiveRecord::Migration
@@ -77,64 +102,111 @@ end
h4. Migrations are Classes
-A migration is a subclass of <tt>ActiveRecord::Migration</tt> that implements two methods: +up+ (perform the required transformations) and +down+ (revert them).
+A migration is a subclass of <tt>ActiveRecord::Migration</tt> that implements
+two methods: +up+ (perform the required transformations) and +down+ (revert
+them).
-Active Record provides methods that perform common data definition tasks in a database independent way (you'll read about them in detail later):
+Active Record provides methods that perform common data definition tasks in a
+database independent way (you'll read about them in detail later):
-* +create_table+
-* +change_table+
-* +drop_table+
* +add_column+
+* +add_index+
* +change_column+
-* +rename_column+
+* +change_table+
+* +create_table+
+* +drop_table+
* +remove_column+
-* +add_index+
* +remove_index+
+* +rename_column+
-If you need to perform tasks specific to your database (for example create a "foreign key":#active-record-and-referential-integrity constraint) then the +execute+ method allows you to execute arbitrary SQL. A migration is just a regular Ruby class so you're not limited to these functions. For example after adding a column you could write code to set the value of that column for existing records (if necessary using your models).
+If you need to perform tasks specific to your database (for example create a
+"foreign key":#active-record-and-referential-integrity constraint) then the
++execute+ method allows you to execute arbitrary SQL. A migration is just a
+regular Ruby class so you're not limited to these functions. For example after
+adding a column you could write code to set the value of that column for
+existing records (if necessary using your models).
-On databases that support transactions with statements that change the schema (such as PostgreSQL or SQLite3), migrations are wrapped in a transaction. If the database does not support this (for example MySQL) then when a migration fails the parts of it that succeeded will not be rolled back. You will have to unpick the changes that were made by hand.
+On databases that support transactions with statements that change the schema
+(such as PostgreSQL or SQLite3), migrations are wrapped in a transaction. If the
+database does not support this (for example MySQL) then when a migration fails
+the parts of it that succeeded will not be rolled back. You will have to rollback
+the changes that were made by hand.
h4. What's in a Name
-Migrations are stored in files in +db/migrate+, one for each migration class. The name of the file is of the form +YYYYMMDDHHMMSS_create_products.rb+, that is to say a UTC timestamp identifying the migration followed by an underscore followed by the name of the migration. The name of the migration class (CamelCased version) should match the latter part of the file name. For example +20080906120000_create_products.rb+ should define class +CreateProducts+ and +20080906120001_add_details_to_products.rb+ should define +AddDetailsToProducts+. If you do feel the need to change the file name then you <em>have to</em> update the name of the class inside or Rails will complain about a missing class.
-
-Internally Rails only uses the migration's number (the timestamp) to identify them. Prior to Rails 2.1 the migration number started at 1 and was incremented each time a migration was generated. With multiple developers it was easy for these to clash requiring you to rollback migrations and renumber them. With Rails 2.1 this is largely avoided by using the creation time of the migration to identify them. You can revert to the old numbering scheme by adding the following line to +config/application.rb+.
+Migrations are stored as files in the +db/migrate+ directory, one for each
+migration class. The name of the file is of the form
++YYYYMMDDHHMMSS_create_products.rb+, that is to say a UTC timestamp
+identifying the migration followed by an underscore followed by the name
+of the migration. The name of the migration class (CamelCased version)
+should match the latter part of the file name. For example
++20080906120000_create_products.rb+ should define class +CreateProducts+ and
++20080906120001_add_details_to_products.rb+ should define
++AddDetailsToProducts+. If you do feel the need to change the file name then you
+<em>have to</em> update the name of the class inside or Rails will complain
+about a missing class.
+
+Internally Rails only uses the migration's number (the timestamp) to identify
+them. Prior to Rails 2.1 the migration number started at 1 and was incremented
+each time a migration was generated. With multiple developers it was easy for
+these to clash requiring you to rollback migrations and renumber them. With
+Rails 2.1+ this is largely avoided by using the creation time of the migration
+to identify them. You can revert to the old numbering scheme by adding the
+following line to +config/application.rb+.
<ruby>
config.active_record.timestamped_migrations = false
</ruby>
-The combination of timestamps and recording which migrations have been run allows Rails to handle common situations that occur with multiple developers.
+The combination of timestamps and recording which migrations have been run
+allows Rails to handle common situations that occur with multiple developers.
-For example Alice adds migrations +20080906120000+ and +20080906123000+ and Bob adds +20080906124500+ and runs it. Alice finishes her changes and checks in her migrations and Bob pulls down the latest changes. Rails knows that it has not run Alice's two migrations so +rake db:migrate+ would run them (even though Bob's migration with a later timestamp has been run), and similarly migrating down would not run their +down+ methods.
+For example Alice adds migrations +20080906120000+ and +20080906123000+ and Bob
+adds +20080906124500+ and runs it. Alice finishes her changes and checks in her
+migrations and Bob pulls down the latest changes. When Bob runs +rake db:migrate+,
+Rails knows that it has not run Alice's two migrations so it executes the +up+ method for each migration.
-Of course this is no substitution for communication within the team. For example, if Alice's migration removed a table that Bob's migration assumed to exist, then trouble would certainly strike.
+Of course this is no substitution for communication within the team. For
+example, if Alice's migration removed a table that Bob's migration assumed to
+exist, then trouble would certainly strike.
h4. Changing Migrations
-Occasionally you will make a mistake when writing a migration. If you have already run the migration then you cannot just edit the migration and run the migration again: Rails thinks it has already run the migration and so will do nothing when you run +rake db:migrate+. You must rollback the migration (for example with +rake db:rollback+), edit your migration and then run +rake db:migrate+ to run the corrected version.
+Occasionally you will make a mistake when writing a migration. If you have
+already run the migration then you cannot just edit the migration and run the
+migration again: Rails thinks it has already run the migration and so will do
+nothing when you run +rake db:migrate+. You must rollback the migration (for
+example with +rake db:rollback+), edit your migration and then run +rake db:migrate+ to run the corrected version.
-In general editing existing migrations is not a good idea: you will be creating extra work for yourself and your co-workers and cause major headaches if the existing version of the migration has already been run on production machines. Instead, you should write a new migration that performs the changes you require. Editing a freshly generated migration that has not yet been committed to source control (or, more generally, which has not been propagated beyond your development machine) is relatively harmless.
+In general editing existing migrations is not a good idea: you will be creating
+extra work for yourself and your co-workers and cause major headaches if the
+existing version of the migration has already been run on production machines.
+Instead, you should write a new migration that performs the changes you require.
+Editing a freshly generated migration that has not yet been committed to source
+control (or, more generally, which has not been propagated beyond your
+development machine) is relatively harmless.
h4. Supported Types
-Active Record supports the following types:
+Active Record supports the following database column types:
+* +:binary+
+* +:boolean+
+* +:date+
+* +:datetime+
+* +:decimal+
+* +:float+
+* +:integer+
* +:primary_key+
* +:string+
* +:text+
-* +:integer+
-* +:float+
-* +:decimal+
-* +:datetime+
-* +:timestamp+
* +:time+
-* +:date+
-* +:binary+
-* +:boolean+
+* +:timestamp+
-These will be mapped onto an appropriate underlying database type. For example, with MySQL the type +:string+ is mapped to +VARCHAR(255)+. You can create columns of types not supported by Active Record when using the non-sexy syntax, for example
+These will be mapped onto an appropriate underlying database type. For example,
+with MySQL the type +:string+ is mapped to +VARCHAR(255)+. You can create
+columns of types not supported by Active Record when using the non-sexy syntax,
+for example
<ruby>
create_table :products do |t|
@@ -148,7 +220,10 @@ h3. Creating a Migration
h4. Creating a Model
-The model and scaffold generators will create migrations appropriate for adding a new model. This migration will already contain instructions for creating the relevant table. If you tell Rails what columns you want, then statements for adding these columns will also be created. For example, running
+The model and scaffold generators will create migrations appropriate for adding
+a new model. This migration will already contain instructions for creating the
+relevant table. If you tell Rails what columns you want, then statements for
+adding these columns will also be created. For example, running
<shell>
$ rails generate model Product name:string description:text
@@ -169,12 +244,15 @@ class CreateProducts < ActiveRecord::Migration
end
</ruby>
-You can append as many column name/type pairs as you want. By default +t.timestamps+ (which creates the +updated_at+ and +created_at+ columns that
-are automatically populated by Active Record) will be added for you.
+You can append as many column name/type pairs as you want. By default, the
+generated migration will include +t.timestamps+ (which creates the
++updated_at+ and +created_at+ columns that are automatically populated
+by Active Record).
h4. Creating a Standalone Migration
-If you are creating migrations for other purposes (for example to add a column to an existing table) then you can use the migration generator:
+If you are creating migrations for other purposes (for example to add a column
+to an existing table) then you can also use the migration generator:
<shell>
$ rails generate migration AddPartNumberToProducts
@@ -189,7 +267,9 @@ class AddPartNumberToProducts < ActiveRecord::Migration
end
</ruby>
-If the migration name is of the form "AddXXXToYYY" or "RemoveXXXFromYYY" and is followed by a list of column names and types then a migration containing the appropriate +add_column+ and +remove_column+ statements will be created.
+If the migration name is of the form "AddXXXToYYY" or "RemoveXXXFromYYY" and is
+followed by a list of column names and types then a migration containing the
+appropriate +add_column+ and +remove_column+ statements will be created.
<shell>
$ rails generate migration AddPartNumberToProducts part_number:string
@@ -242,17 +322,23 @@ class AddDetailsToProducts < ActiveRecord::Migration
end
</ruby>
-As always, what has been generated for you is just a starting point. You can add or remove from it as you see fit.
+As always, what has been generated for you is just a starting point. You can add
+or remove from it as you see fit by editing the
+db/migrate/YYYYMMDDHHMMSS_add_details_to_products.rb file.
-NOTE: The generated migration file for destructive migrations will still be old-style using the +up+ and +down+ methods. This is because Rails doesn't know the original data types defined when you made the original changes.
+NOTE: The generated migration file for destructive migrations will still be
+old-style using the +up+ and +down+ methods. This is because Rails needs to know
+the original data types defined when you made the original changes.
h3. Writing a Migration
-Once you have created your migration using one of the generators it's time to get to work!
+Once you have created your migration using one of the generators it's time to
+get to work!
h4. Creating a Table
-Migration method +create_table+ will be one of your workhorses. A typical use would be
+Migration method +create_table+ will be one of your workhorses. A typical use
+would be
<ruby>
create_table :products do |t|
@@ -260,9 +346,11 @@ create_table :products do |t|
end
</ruby>
-which creates a +products+ table with a column called +name+ (and as discussed below, an implicit +id+ column).
+which creates a +products+ table with a column called +name+ (and as discussed
+below, an implicit +id+ column).
-The object yielded to the block allows you to create columns on the table. There are two ways of doing it. The first (traditional) form looks like
+The object yielded to the block allows you to create columns on the table. There
+are two ways of doing it. The first (traditional) form looks like
<ruby>
create_table :products do |t|
@@ -270,7 +358,9 @@ create_table :products do |t|
end
</ruby>
-The second form, the so called "sexy" migration, drops the somewhat redundant +column+ method. Instead, the +string+, +integer+, etc. methods create a column of that type. Subsequent parameters are the same.
+The second form, the so called "sexy" migration, drops the somewhat redundant
++column+ method. Instead, the +string+, +integer+, etc. methods create a column
+of that type. Subsequent parameters are the same.
<ruby>
create_table :products do |t|
@@ -278,7 +368,12 @@ create_table :products do |t|
end
</ruby>
-By default, +create_table+ will create a primary key called +id+. You can change the name of the primary key with the +:primary_key+ option (don't forget to update the corresponding model) or, if you don't want a primary key at all (for example for a HABTM join table), you can pass the option +:id => false+. If you need to pass database specific options you can place an SQL fragment in the +:options+ option. For example,
+By default, +create_table+ will create a primary key called +id+. You can change
+the name of the primary key with the +:primary_key+ option (don't forget to
+update the corresponding model) or, if you don't want a primary key at all (for
+example for a HABTM join table), you can pass the option +:id => false+. If you
+need to pass database specific options you can place an SQL fragment in the
++:options+ option. For example,
<ruby>
create_table :products, :options => "ENGINE=BLACKHOLE" do |t|
@@ -286,11 +381,14 @@ create_table :products, :options => "ENGINE=BLACKHOLE" do |t|
end
</ruby>
-will append +ENGINE=BLACKHOLE+ to the SQL statement used to create the table (when using MySQL, the default is +ENGINE=InnoDB+).
+will append +ENGINE=BLACKHOLE+ to the SQL statement used to create the table
+(when using MySQL, the default is +ENGINE=InnoDB+).
h4. Changing Tables
-A close cousin of +create_table+ is +change_table+, used for changing existing tables. It is used in a similar fashion to +create_table+ but the object yielded to the block knows more tricks. For example
+A close cousin of +create_table+ is +change_table+, used for changing existing
+tables. It is used in a similar fashion to +create_table+ but the object yielded
+to the block knows more tricks. For example
<ruby>
change_table :products do |t|
@@ -301,28 +399,23 @@ change_table :products do |t|
end
</ruby>
-removes the +description+ and +name+ columns, creates a +part_number+ column and adds an index on it. Finally it renames the +upccode+ column. This is the same as doing
-
-<ruby>
-remove_column :products, :description
-remove_column :products, :name
-add_column :products, :part_number, :string
-add_index :products, :part_number
-rename_column :products, :upccode, :upc_code
-</ruby>
-
-You don't have to keep repeating the table name and it groups all the statements related to modifying one particular table. The individual transformation names are also shorter, for example +remove_column+ becomes just +remove+ and +add_index+ becomes just +index+.
+removes the +description+ and +name+ columns, creates a +part_number+ string
+column and adds an index on it. Finally it renames the +upccode+ column.
h4. Special Helpers
-Active Record provides some shortcuts for common functionality. It is for example very common to add both the +created_at+ and +updated_at+ columns and so there is a method that does exactly that:
+Active Record provides some shortcuts for common functionality. It is for
+example very common to add both the +created_at+ and +updated_at+ columns and so
+there is a method that does exactly that:
<ruby>
create_table :products do |t|
t.timestamps
end
</ruby>
-will create a new products table with those two columns (plus the +id+ column) whereas
+
+will create a new products table with those two columns (plus the +id+ column)
+whereas
<ruby>
change_table :products do |t|
@@ -331,7 +424,8 @@ end
</ruby>
adds those columns to an existing table.
-The other helper is called +references+ (also available as +belongs_to+). In its simplest form it just adds some readability
+Another helper is called +references+ (also available as +belongs_to+). In its
+simplest form it just adds some readability.
<ruby>
create_table :products do |t|
@@ -339,24 +433,42 @@ create_table :products do |t|
end
</ruby>
-will create a +category_id+ column of the appropriate type. Note that you pass the model name, not the column name. Active Record adds the +_id+ for you. If you have polymorphic +belongs_to+ associations then +references+ will add both of the columns required:
+will create a +category_id+ column of the appropriate type. Note that you pass
+the model name, not the column name. Active Record adds the +_id+ for you. If
+you have polymorphic +belongs_to+ associations then +references+ will add both
+of the columns required:
<ruby>
create_table :products do |t|
t.references :attachment, :polymorphic => {:default => 'Photo'}
end
</ruby>
-will add an +attachment_id+ column and a string +attachment_type+ column with a default value of 'Photo'.
-NOTE: The +references+ helper does not actually create foreign key constraints for you. You will need to use +execute+ or a plugin that adds "foreign key support":#active-record-and-referential-integrity.
+will add an +attachment_id+ column and a string +attachment_type+ column with
+a default value of 'Photo'.
+
+NOTE: The +references+ helper does not actually create foreign key constraints
+for you. You will need to use +execute+ or a plugin that adds "foreign key
+support":#active-record-and-referential-integrity.
-If the helpers provided by Active Record aren't enough you can use the +execute+ method to execute arbitrary SQL.
+If the helpers provided by Active Record aren't enough you can use the +execute+
+method to execute arbitrary SQL.
-For more details and examples of individual methods, check the API documentation, in particular the documentation for "<tt>ActiveRecord::ConnectionAdapters::SchemaStatements</tt>":http://api.rubyonrails.org/classes/ActiveRecord/ConnectionAdapters/SchemaStatements.html (which provides the methods available in the +up+ and +down+ methods), "<tt>ActiveRecord::ConnectionAdapters::TableDefinition</tt>":http://api.rubyonrails.org/classes/ActiveRecord/ConnectionAdapters/TableDefinition.html (which provides the methods available on the object yielded by +create_table+) and "<tt>ActiveRecord::ConnectionAdapters::Table</tt>":http://api.rubyonrails.org/classes/ActiveRecord/ConnectionAdapters/Table.html (which provides the methods available on the object yielded by +change_table+).
+For more details and examples of individual methods, check the API documentation,
+in particular the documentation for
+"<tt>ActiveRecord::ConnectionAdapters::SchemaStatements</tt>":http://api.rubyonrails.org/classes/ActiveRecord/ConnectionAdapters/SchemaStatements.html
+(which provides the methods available in the +up+ and +down+ methods),
+"<tt>ActiveRecord::ConnectionAdapters::TableDefinition</tt>":http://api.rubyonrails.org/classes/ActiveRecord/ConnectionAdapters/TableDefinition.html
+(which provides the methods available on the object yielded by +create_table+)
+and
+"<tt>ActiveRecord::ConnectionAdapters::Table</tt>":http://api.rubyonrails.org/classes/ActiveRecord/ConnectionAdapters/Table.html
+(which provides the methods available on the object yielded by +change_table+).
-h4. Writing Your +change+ Method
+h4. Using the +change+ Method
-The +change+ method removes the need to write both +up+ and +down+ methods in those cases that Rails know how to revert the changes automatically. Currently, the +change+ method supports only these migration definitions:
+The +change+ method removes the need to write both +up+ and +down+ methods in
+those cases that Rails know how to revert the changes automatically. Currently,
+the +change+ method supports only these migration definitions:
* +add_column+
* +add_index+
@@ -367,15 +479,20 @@ The +change+ method removes the need to write both +up+ and +down+ methods in th
* +rename_index+
* +rename_table+
-If you're going to use other methods, you'll have to write the +up+ and +down+ methods normally.
+If you're going to need to use any other methods, you'll have to write the
++up+ and +down+ methods instead of using the +change+ method.
-h4. Writing Your +down+ Method
+h4. Using the +up+/+down+ Methods
-The +down+ method of your migration should revert the transformations done by the +up+ method. In other words, the database schema should be unchanged if you do an +up+ followed by a +down+. For example, if you create a table in the +up+ method, you should drop it in the +down+ method. It is wise to reverse the transformations in precisely the reverse order they were made in the +up+ method. For example,
+The +down+ method of your migration should revert the transformations done by
+the +up+ method. In other words, the database schema should be unchanged if you
+do an +up+ followed by a +down+. For example, if you create a table in the +up+
+method, you should drop it in the +down+ method. It is wise to reverse the
+transformations in precisely the reverse order they were made in the +up+
+method. For example,
<ruby>
class ExampleMigration < ActiveRecord::Migration
-
def up
create_table :products do |t|
t.references :category
@@ -387,47 +504,69 @@ class ExampleMigration < ActiveRecord::Migration
FOREIGN KEY (category_id)
REFERENCES categories(id)
SQL
-
add_column :users, :home_page_url, :string
-
rename_column :users, :email, :email_address
end
def down
rename_column :users, :email_address, :email
remove_column :users, :home_page_url
- execute "ALTER TABLE products DROP FOREIGN KEY fk_products_categories"
+ execute <<-SQL
+ ALTER TABLE products
+ DROP FOREIGN KEY fk_products_categories
+ SQL
drop_table :products
end
end
</ruby>
-Sometimes your migration will do something which is just plain irreversible; for example, it might destroy some data. In such cases, you can raise +ActiveRecord::IrreversibleMigration+ from your +down+ method. If someone tries to revert your migration, an error message will be displayed saying that it can't be done.
+Sometimes your migration will do something which is just plain irreversible; for
+example, it might destroy some data. In such cases, you can raise
++ActiveRecord::IrreversibleMigration+ from your +down+ method. If someone tries
+to revert your migration, an error message will be displayed saying that it
+can't be done.
h3. Running Migrations
-Rails provides a set of rake tasks to work with migrations which boil down to running certain sets of migrations. The very first migration related rake task you will use will probably be +db:migrate+. In its most basic form it just runs the +up+ method for all the migrations that have not yet been run. If there are no such migrations, it exits.
+Rails provides a set of rake tasks to work with migrations which boil down to
+running certain sets of migrations.
+
+The very first migration related rake task you will use will probably be
++rake db:migrate+. In its most basic form it just runs the +up+ or +change+
+method for all the migrations that have not yet been run. If there are
+no such migrations, it exits. It will run these migrations in order based
+on the date of the migration.
-Note that running the +db:migrate+ also invokes the +db:schema:dump+ task, which will update your db/schema.rb file to match the structure of your database.
+Note that running the +db:migrate+ also invokes the +db:schema:dump+ task, which
+will update your db/schema.rb file to match the structure of your database.
-If you specify a target version, Active Record will run the required migrations (up or down) until it has reached the specified version. The
-version is the numerical prefix on the migration's filename. For example, to migrate to version 20080906120000 run
+If you specify a target version, Active Record will run the required migrations
+(up, down or change) until it has reached the specified version. The version
+is the numerical prefix on the migration's filename. For example, to migrate
+to version 20080906120000 run
<shell>
$ rake db:migrate VERSION=20080906120000
</shell>
-If version 20080906120000 is greater than the current version (i.e., it is migrating upwards), this will run the +up+ method on all migrations up to and including 20080906120000. If migrating downwards, this will run the +down+ method on all the migrations down to, but not including, 20080906120000.
+If version 20080906120000 is greater than the current version (i.e., it is
+migrating upwards), this will run the +up+ method on all migrations up to and
+including 20080906120000, and will not execute any later migrations. If
+migrating downwards, this will run the +down+ method on all the migrations
+down to, but not including, 20080906120000.
h4. Rolling Back
-A common task is to rollback the last migration, for example if you made a mistake in it and wish to correct it. Rather than tracking down the version number associated with the previous migration you can run
+A common task is to rollback the last migration, for example if you made a
+mistake in it and wish to correct it. Rather than tracking down the version
+number associated with the previous migration you can run
<shell>
$ rake db:rollback
</shell>
-This will run the +down+ method from the latest migration. If you need to undo several migrations you can provide a +STEP+ parameter:
+This will run the +down+ method from the latest migration. If you need to undo
+several migrations you can provide a +STEP+ parameter:
<shell>
$ rake db:rollback STEP=3
@@ -435,46 +574,65 @@ $ rake db:rollback STEP=3
will run the +down+ method from the last 3 migrations.
-The +db:migrate:redo+ task is a shortcut for doing a rollback and then migrating back up again. As with the +db:rollback+ task, you can use the +STEP+ parameter if you need to go more than one version back, for example
+The +db:migrate:redo+ task is a shortcut for doing a rollback and then migrating
+back up again. As with the +db:rollback+ task, you can use the +STEP+ parameter
+if you need to go more than one version back, for example
<shell>
$ rake db:migrate:redo STEP=3
</shell>
-Neither of these Rake tasks do anything you could not do with +db:migrate+. They are simply more convenient, since you do not need to explicitly specify the version to migrate to.
+Neither of these Rake tasks do anything you could not do with +db:migrate+. They
+are simply more convenient, since you do not need to explicitly specify the
+version to migrate to.
-Lastly, the +db:reset+ task will drop the database, recreate it and load the current schema into it.
+h4. Resetting the database
-NOTE: This is not the same as running all the migrations - see the section on "schema.rb":#schema-dumping-and-you.
+The +rake db:reset+ task will drop the database, recreate it and load the
+current schema into it.
-h4. Being Specific
+NOTE: This is not the same as running all the migrations - see the section on
+"schema.rb":#schema-dumping-and-you.
-If you need to run a specific migration up or down, the +db:migrate:up+ and +db:migrate:down+ tasks will do that. Just specify the appropriate version and the corresponding migration will have its +up+ or +down+ method invoked, for example,
+h4. Running specific migrations
+
+If you need to run a specific migration up or down, the +db:migrate:up+ and
++db:migrate:down+ tasks will do that. Just specify the appropriate version and
+the corresponding migration will have its +up+ or +down+ method invoked, for
+example,
<shell>
$ rake db:migrate:up VERSION=20080906120000
</shell>
-will run the +up+ method from the 20080906120000 migration. These tasks check whether the migration has already run, so for example +db:migrate:up VERSION=20080906120000+ will do nothing if Active Record believes that 20080906120000 has already been run.
+will run the +up+ method from the 20080906120000 migration. These tasks still
+check whether the migration has already run, so for example +db:migrate:up
+VERSION=20080906120000+ will do nothing if Active Record believes that
+20080906120000 has already been run.
-h4. Being Talkative
+h4. Changing the output of running migrations
-By default migrations tell you exactly what they're doing and how long it took. A migration creating a table and adding an index might produce output like this
+By default migrations tell you exactly what they're doing and how long it took.
+A migration creating a table and adding an index might produce output like this
<shell>
-20080906170109 CreateProducts: migrating
+== CreateProducts: migrating =================================================
-- create_table(:products)
- -> 0.0021s
--- add_index(:products, :name)
- -> 0.0026s
-20080906170109 CreateProducts: migrated (0.0059s)
+ -> 0.0028s
+== CreateProducts: migrated (0.0028s) ========================================
</shell>
-Several methods are provided that allow you to control all this:
+Several methods are provided in migrations that allow you to control all this:
-* +suppress_messages+ takes a block as an argument and suppresses any output generated by the block.
-* +say+ takes a message argument and outputs it as is. A second boolean argument can be passed to specify whether to indent or not.
-* +say_with_time+ outputs text along with how long it took to run its block. If the block returns an integer it assumes it is the number of rows affected.
+|_.Method |_.Purpose|
+|suppress_messages |Takes a block as an argument and suppresses any output
+ generated by the block.|
+|say |Takes a message argument and outputs it as is. A second
+ boolean argument can be passed to specify whether to
+ indent or not.|
+|say_with_time |Outputs text along with how long it took to run its
+ block. If the block returns an integer it assumes it
+ is the number of rows affected.|
For example, this migration
@@ -502,37 +660,46 @@ end
generates the following output
<shell>
-20080906170109 CreateProducts: migrating
- Created a table
+== CreateProducts: migrating =================================================
+-- Created a table
-> and an index!
- Waiting for a while
- -> 10.0001s
+-- Waiting for a while
+ -> 10.0013s
-> 250 rows
-20080906170109 CreateProducts: migrated (10.0097s)
+== CreateProducts: migrated (10.0054s) =======================================
</shell>
-If you just want Active Record to shut up, then running +rake db:migrate VERBOSE=false+ will suppress all output.
+If you want Active Record to not output anything, then running +rake db:migrate
+VERBOSE=false+ will suppress all output.
h3. Using Models in Your Migrations
-When creating or updating data in a migration it is often tempting to use one of your models. After all, they exist to provide easy access to the underlying data. This can be done, but some caution should be observed.
+When creating or updating data in a migration it is often tempting to use one of
+your models. After all, they exist to provide easy access to the underlying
+data. This can be done, but some caution should be observed.
-For example, problems occur when the model uses database columns which are (1) not currently in the database and (2) will be created by this or a subsequent migration.
+For example, problems occur when the model uses database columns which are (1)
+not currently in the database and (2) will be created by this or a subsequent
+migration.
-Consider this example, where Alice and Bob are working on the same code base which contains a +Product+ model:
+Consider this example, where Alice and Bob are working on the same code base
+which contains a +Product+ model:
Bob goes on vacation.
-Alice creates a migration for the +products+ table which adds a new column and initializes it.
-She also adds a validation to the +Product+ model for the new column.
+Alice creates a migration for the +products+ table which adds a new column and
+initializes it. She also adds a validation to the +Product+ model for the new
+column.
<ruby>
# db/migrate/20100513121110_add_flag_to_product.rb
class AddFlagToProduct < ActiveRecord::Migration
def change
- add_column :products, :flag, :int
- Product.all.each { |f| f.update_attributes!(:flag => 'false') }
+ add_column :products, :flag, :boolean
+ Product.all.each do |product|
+ product.update_attributes!(:flag => 'false')
+ end
end
end
</ruby>
@@ -545,7 +712,9 @@ class Product < ActiveRecord::Base
end
</ruby>
-Alice adds a second migration which adds and initializes another column to the +products+ table and also adds a validation to the +Product+ model for the new column.
+Alice adds a second migration which adds and initializes another column to the
++products+ table and also adds a validation to the +Product+ model for the new
+column.
<ruby>
# db/migrate/20100515121110_add_fuzz_to_product.rb
@@ -553,7 +722,9 @@ Alice adds a second migration which adds and initializes another column to the +
class AddFuzzToProduct < ActiveRecord::Migration
def change
add_column :products, :fuzz, :string
- Product.all.each { |f| f.update_attributes! :fuzz => 'fuzzy' }
+ Product.all.each do |product|
+ product.update_attributes! :fuzz => 'fuzzy'
+ end
end
end
</ruby>
@@ -570,10 +741,14 @@ Both migrations work for Alice.
Bob comes back from vacation and:
-# updates the source - which contains both migrations and the latests version of the Product model.
-# runs outstanding migrations with +rake db:migrate+, which includes the one that updates the +Product+ model.
+# Updates the source - which contains both migrations and the latests version of
+the Product model.
+# Runs outstanding migrations with +rake db:migrate+, which
+includes the one that updates the +Product+ model.
-The migration crashes because when the model attempts to save, it tries to validate the second added column, which is not in the database when the _first_ migration runs:
+The migration crashes because when the model attempts to save, it tries to
+validate the second added column, which is not in the database when the _first_
+migration runs:
<plain>
rake aborted!
@@ -582,9 +757,12 @@ An error has occurred, this and all later migrations canceled:
undefined method `fuzz' for #<Product:0x000001049b14a0>
</plain>
-A fix for this is to create a local model within the migration. This keeps rails from running the validations, so that the migrations run to completion.
+A fix for this is to create a local model within the migration. This keeps rails
+from running the validations, so that the migrations run to completion.
-When using a faux model, it's a good idea to call +Product.reset_column_information+ to refresh the +ActiveRecord+ cache for the +Product+ model prior to updating data in the database.
+When using a faux model, it's a good idea to call
++Product.reset_column_information+ to refresh the +ActiveRecord+ cache for the
++Product+ model prior to updating data in the database.
If Alice had done this instead, there would have been no problem:
@@ -596,9 +774,11 @@ class AddFlagToProduct < ActiveRecord::Migration
end
def change
- add_column :products, :flag, :int
+ add_column :products, :flag, :integer
Product.reset_column_information
- Product.all.each { |f| f.update_attributes!(:flag => false) }
+ Product.all.each do |product|
+ product.update_attributes!(:flag => false)
+ end
end
end
</ruby>
@@ -609,32 +789,50 @@ end
class AddFuzzToProduct < ActiveRecord::Migration
class Product < ActiveRecord::Base
end
+
def change
add_column :products, :fuzz, :string
Product.reset_column_information
- Product.all.each { |f| f.update_attributes! :fuzz => 'fuzzy' }
+ Product.all.each do |product|
+ product.update_attributes!(:fuzz => 'fuzzy')
+ end
end
end
</ruby>
-
h3. Schema Dumping and You
h4. What are Schema Files for?
-Migrations, mighty as they may be, are not the authoritative source for your database schema. That role falls to either +db/schema.rb+ or an SQL file which Active Record generates by examining the database. They are not designed to be edited, they just represent the current state of the database.
+Migrations, mighty as they may be, are not the authoritative source for your
+database schema. That role falls to either +db/schema.rb+ or an SQL file which
+Active Record generates by examining the database. They are not designed to be
+edited, they just represent the current state of the database.
-There is no need (and it is error prone) to deploy a new instance of an app by replaying the entire migration history. It is much simpler and faster to just load into the database a description of the current schema.
+There is no need (and it is error prone) to deploy a new instance of an app by
+replaying the entire migration history. It is much simpler and faster to just
+load into the database a description of the current schema.
-For example, this is how the test database is created: the current development database is dumped (either to +db/schema.rb+ or +db/development.sql+) and then loaded into the test database.
+For example, this is how the test database is created: the current development
+database is dumped (either to +db/schema.rb+ or +db/structure.sql+) and then
+loaded into the test database.
-Schema files are also useful if you want a quick look at what attributes an Active Record object has. This information is not in the model's code and is frequently spread across several migrations, but is summed up in the schema file. The "annotate_models":https://github.com/ctran/annotate_models gem automatically adds and updates comments at the top of each model summarizing the schema if you desire that functionality.
+Schema files are also useful if you want a quick look at what attributes an
+Active Record object has. This information is not in the model's code and is
+frequently spread across several migrations, but the information is nicely
+summed up in the schema file. The
+"annotate_models":https://github.com/ctran/annotate_models gem automatically
+adds and updates comments at the top of each model summarizing the schema if
+you desire that functionality.
h4. Types of Schema Dumps
-There are two ways to dump the schema. This is set in +config/application.rb+ by the +config.active_record.schema_format+ setting, which may be either +:sql+ or +:ruby+.
+There are two ways to dump the schema. This is set in +config/application.rb+ by
+the +config.active_record.schema_format+ setting, which may be either +:sql+ or
++:ruby+.
-If +:ruby+ is selected then the schema is stored in +db/schema.rb+. If you look at this file you'll find that it looks an awful lot like one very big migration:
+If +:ruby+ is selected then the schema is stored in +db/schema.rb+. If you look
+at this file you'll find that it looks an awful lot like one very big migration:
<ruby>
ActiveRecord::Schema.define(:version => 20080906171750) do
@@ -646,28 +844,57 @@ ActiveRecord::Schema.define(:version => 20080906171750) do
create_table "products", :force => true do |t|
t.string "name"
- t.text "description"
+ t.text "description"
t.datetime "created_at"
t.datetime "updated_at"
- t.string "part_number"
+ t.string "part_number"
end
end
</ruby>
-In many ways this is exactly what it is. This file is created by inspecting the database and expressing its structure using +create_table+, +add_index+, and so on. Because this is database-independent, it could be loaded into any database that Active Record supports. This could be very useful if you were to distribute an application that is able to run against multiple databases.
-
-There is however a trade-off: +db/schema.rb+ cannot express database specific items such as foreign key constraints, triggers, or stored procedures. While in a migration you can execute custom SQL statements, the schema dumper cannot reconstitute those statements from the database. If you are using features like this, then you should set the schema format to +:sql+.
-
-Instead of using Active Record's schema dumper, the database's structure will be dumped using a tool specific to the database (via the +db:structure:dump+ Rake task) into +db/#{Rails.env}_structure.sql+. For example, for the PostgreSQL RDBMS, the +pg_dump+ utility is used. For MySQL, this file will contain the output of +SHOW CREATE TABLE+ for the various tables. Loading these schemas is simply a question of executing the SQL statements they contain. By definition, this will create a perfect copy of the database's structure. Using the +:sql+ schema format will, however, prevent loading the schema into a RDBMS other than the one used to create it.
+In many ways this is exactly what it is. This file is created by inspecting the
+database and expressing its structure using +create_table+, +add_index+, and so
+on. Because this is database-independent, it could be loaded into any database
+that Active Record supports. This could be very useful if you were to distribute
+an application that is able to run against multiple databases.
+
+There is however a trade-off: +db/schema.rb+ cannot express database specific
+items such as foreign key constraints, triggers, or stored procedures. While in
+a migration you can execute custom SQL statements, the schema dumper cannot
+reconstitute those statements from the database. If you are using features like
+this, then you should set the schema format to +:sql+.
+
+Instead of using Active Record's schema dumper, the database's structure will be
+dumped using a tool specific to the database (via the +db:structure:dump+ Rake task)
+into +db/structure.sql+. For example, for the PostgreSQL RDBMS, the
++pg_dump+ utility is used. For MySQL, this file will contain the output of +SHOW
+CREATE TABLE+ for the various tables. Loading these schemas is simply a question
+of executing the SQL statements they contain. By definition, this will create a
+perfect copy of the database's structure. Using the +:sql+ schema format will,
+however, prevent loading the schema into a RDBMS other than the one used to
+create it.
h4. Schema Dumps and Source Control
-Because schema dumps are the authoritative source for your database schema, it is strongly recommended that you check them into source control.
+Because schema dumps are the authoritative source for your database schema, it
+is strongly recommended that you check them into source control.
h3. Active Record and Referential Integrity
-The Active Record way claims that intelligence belongs in your models, not in the database. As such, features such as triggers or foreign key constraints, which push some of that intelligence back into the database, are not heavily used.
-
-Validations such as +validates :foreign_key, :uniqueness => true+ are one way in which models can enforce data integrity. The +:dependent+ option on associations allows models to automatically destroy child objects when the parent is destroyed. Like anything which operates at the application level, these cannot guarantee referential integrity and so some people augment them with foreign key constraints.
-
-Although Active Record does not provide any tools for working directly with such features, the +execute+ method can be used to execute arbitrary SQL. There are also a number of plugins such as "foreign_key_migrations":https://github.com/harukizaemon/redhillonrails/tree/master/foreign_key_migrations/ which add foreign key support to Active Record (including support for dumping foreign keys in +db/schema.rb+).
+The Active Record way claims that intelligence belongs in your models, not in
+the database. As such, features such as triggers or foreign key constraints,
+which push some of that intelligence back into the database, are not heavily
+used.
+
+Validations such as +validates :foreign_key, :uniqueness => true+ are one way in
+which models can enforce data integrity. The +:dependent+ option on associations
+allows models to automatically destroy child objects when the parent is
+destroyed. Like anything which operates at the application level, these cannot
+guarantee referential integrity and so some people augment them with foreign key
+constraints in the database.
+
+Although Active Record does not provide any tools for working directly with such
+features, the +execute+ method can be used to execute arbitrary SQL. You could
+also use some plugin like "foreigner":https://github.com/matthuhiggins/foreigner
+which add foreign key support to Active Record (including support for dumping
+foreign keys in +db/schema.rb+).
diff --git a/railties/guides/source/performance_testing.textile b/railties/guides/source/performance_testing.textile
index 2440927542..958b13cd9e 100644
--- a/railties/guides/source/performance_testing.textile
+++ b/railties/guides/source/performance_testing.textile
@@ -151,7 +151,7 @@ Performance tests can be run in two modes: Benchmarking and Profiling.
h5. Benchmarking
-Benchmarking makes it easy to quickly gather a few metrics about each test tun. By default, each test case is run *4 times* in benchmarking mode.
+Benchmarking makes it easy to quickly gather a few metrics about each test run. By default, each test case is run *4 times* in benchmarking mode.
To run performance tests in benchmarking mode:
diff --git a/railties/guides/source/rails_on_rack.textile b/railties/guides/source/rails_on_rack.textile
index d6cbd84b1f..9526526bc7 100644
--- a/railties/guides/source/rails_on_rack.textile
+++ b/railties/guides/source/rails_on_rack.textile
@@ -95,6 +95,7 @@ use ActiveSupport::Cache::Strategy::LocalCache
use Rack::Runtime
use Rails::Rack::Logger
use ActionDispatch::ShowExceptions
+use ActionDispatch::DebugExceptions
use ActionDispatch::RemoteIp
use Rack::Sendfile
use ActionDispatch::Callbacks
diff --git a/railties/guides/source/routing.textile b/railties/guides/source/routing.textile
index 29c729592b..0823fb14e3 100644
--- a/railties/guides/source/routing.textile
+++ b/railties/guides/source/routing.textile
@@ -655,7 +655,7 @@ You can use the +:constraints+ option to specify a required format on the implic
resources :photos, :constraints => {:id => /[A-Z][A-Z][0-9]+/}
</ruby>
-This declaration constraints the +:id+ parameter to match the supplied regular expression. So, in this case, the router would no longer match +/photos/1+ to this route. Instead, +/photos/RR27+ would match.
+This declaration constrains the +:id+ parameter to match the supplied regular expression. So, in this case, the router would no longer match +/photos/1+ to this route. Instead, +/photos/RR27+ would match.
You can specify a single constraint to apply to a number of routes by using the block form:
diff --git a/railties/guides/source/testing.textile b/railties/guides/source/testing.textile
index 2341a3522c..5dbbe2c0f0 100644
--- a/railties/guides/source/testing.textile
+++ b/railties/guides/source/testing.textile
@@ -927,7 +927,7 @@ class UserControllerTest < ActionController::TestCase
assert_difference 'ActionMailer::Base.deliveries.size', +1 do
post :invite_friend, :email => 'friend@example.com'
end
- invite_email = ActionMailer::Base.deliveries.first
+ invite_email = ActionMailer::Base.deliveries.last
assert_equal "You have been invited by me@example.com", invite_email.subject
assert_equal 'friend@example.com', invite_email.to[0]