From beca1af820fab74a6ea26cb906d6c5e0116b7f8c Mon Sep 17 00:00:00 2001 From: James Miller Date: Tue, 6 Apr 2010 16:36:43 -0700 Subject: [PATCH 01/22] ERB update for AC overview guide --- railties/guides/source/action_controller_overview.textile | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/railties/guides/source/action_controller_overview.textile b/railties/guides/source/action_controller_overview.textile index bedca59c127bd..e193c57935208 100644 --- a/railties/guides/source/action_controller_overview.textile +++ b/railties/guides/source/action_controller_overview.textile @@ -492,10 +492,10 @@ The way this is done is to add a non-guessable token which is only known to your If you generate a form like this: -<% form_for @user do |f| -%> +<%= form_for @user do |f| %> <%= f.text_field :username %> <%= f.text_field :password -%> -<% end -%> +<% end %> You will see how the token gets added as a hidden field: From b52b36e680713b04a541c4bf989a692975099e6c Mon Sep 17 00:00:00 2001 From: James Miller Date: Tue, 6 Apr 2010 16:52:39 -0700 Subject: [PATCH 02/22] More on the new ERB syntax in the guides --- .../source/action_controller_overview.textile | 10 ++++----- .../source/action_view_overview.textile | 22 +++++++++---------- ...activerecord_validations_callbacks.textile | 2 +- .../guides/source/getting_started.textile | 2 +- .../source/layouts_and_rendering.textile | 6 ++--- .../guides/source/nested_model_forms.textile | 6 ++--- railties/guides/source/testing.textile | 2 +- 7 files changed, 25 insertions(+), 25 deletions(-) diff --git a/railties/guides/source/action_controller_overview.textile b/railties/guides/source/action_controller_overview.textile index e193c57935208..caa7646b7f528 100644 --- a/railties/guides/source/action_controller_overview.textile +++ b/railties/guides/source/action_controller_overview.textile @@ -255,12 +255,12 @@ The +destroy+ action redirects to the application's +root_url+, where the messag - <% if flash[:notice] -%> + <% if flash[:notice] %>

<%= flash[:notice] %>

- <% end -%> - <% if flash[:error] -%> + <% end %> + <% if flash[:error] %>

<%= flash[:error] %>

- <% end -%> + <% end %> @@ -494,7 +494,7 @@ If you generate a form like this: <%= form_for @user do |f| %> <%= f.text_field :username %> - <%= f.text_field :password -%> + <%= f.text_field :password %> <% end %> diff --git a/railties/guides/source/action_view_overview.textile b/railties/guides/source/action_view_overview.textile index df8cf4dc29133..43ebe8787513d 100644 --- a/railties/guides/source/action_view_overview.textile +++ b/railties/guides/source/action_view_overview.textile @@ -135,7 +135,7 @@ The +post+ partial wraps the post's +body+ in a +div+ with the +id+ of the post *posts/_post.html.erb* -<% div_for(post) do %> +<%= div_for(post) do %>

<%= post.body %>

<% end %>
@@ -158,7 +158,7 @@ You can also render a block of code within a partial layout instead of calling + <% render(:layout => 'box', :locals => {:post => @post}) do %> - <% div_for(post) do %> + <%= div_for(post) do %>

<%= post.body %>

<% end %> <% end %> @@ -654,7 +654,7 @@ The core method of this helper, form_for, gives you the ability to create a form # Note: a @person variable will have been created in the controller (e.g. @person = Person.new) -<% form_for :person, @person, :url => { :action => "create" } do |f| %> +<%= form_for :person, @person, :url => { :action => "create" } do |f| %> <%= f.text_field :first_name %> <%= f.text_field :last_name %> <%= submit_tag 'Create' %> @@ -695,7 +695,7 @@ h5. fields_for Creates a scope around a specific model object like form_for, but doesn‘t create the form tags themselves. This makes fields_for suitable for specifying additional model objects in the same form: -<% form_for @person, :url => { :action => "update" } do |person_form| %> +<%= form_for @person, :url => { :action => "update" } do |person_form| %> First name: <%= person_form.text_field :first_name %> Last name : <%= person_form.text_field :last_name %> @@ -719,7 +719,7 @@ h5. form_for Creates a form and a scope around a specific model object that is used as a base for questioning about values for the fields. -<% form_for @post do |f| %> +<%= form_for @post do |f| %> <%= f.label :title, 'Title' %>: <%= f.text_field :title %>
<%= f.label :body, 'Body' %>: @@ -957,7 +957,7 @@ h5. field_set_tag Creates a field set for grouping HTML form elements. -<% field_set_tag do %> +<%= field_set_tag do %>

<%= text_field_tag 'name' %>

<% end %> # =>

@@ -970,10 +970,10 @@ Creates a file upload field. If you are using file uploads then you will also need to set the multipart option for the form tag: -<%= form_tag { :action => "post" }, { :multipart => true } %> +<%= form_tag { :action => "post" }, { :multipart => true } do %> <%= file_field_tag "file" %> <%= submit_tag %> -<%= end_form_tag %> +<% end %> Example output: @@ -988,9 +988,9 @@ h5. form_tag Starts a form tag that points the action to an url configured with +url_for_options+ just like +ActionController::Base#url_for+. -<% form_tag '/posts' do -%> +<%= form_tag '/posts' do %>
<%= submit_tag 'Save' %>
-<% end -%> +<% end %> # =>
@@ -1251,7 +1251,7 @@ h5. remote_form_for Creates a form that will submit using XMLHttpRequest in the background instead of the regular reloading POST arrangement and a scope around a specific resource that is used as a base for questioning about values for the fields. -<% remote_form_for(@post) do |f| %> +<%= remote_form_for(@post) do |f| %> ... <% end %> diff --git a/railties/guides/source/activerecord_validations_callbacks.textile b/railties/guides/source/activerecord_validations_callbacks.textile index 6575612bee6fa..126a6efff56c9 100644 --- a/railties/guides/source/activerecord_validations_callbacks.textile +++ b/railties/guides/source/activerecord_validations_callbacks.textile @@ -712,7 +712,7 @@ end
-<% form_for(@product) do |f| %> +<%= form_for(@product) do |f| %> <%= f.error_messages %>

<%= f.label :description %>
diff --git a/railties/guides/source/getting_started.textile b/railties/guides/source/getting_started.textile index 17279146a7bc3..2bbb4dc252cdd 100644 --- a/railties/guides/source/getting_started.textile +++ b/railties/guides/source/getting_started.textile @@ -974,7 +974,7 @@ Once we have made the new comment, we send the user back to the +post_path(@post <% end %>

Add a comment:

-<% form_for([@post, @post.comments.build]) do |f| %> +<%= form_for([@post, @post.comments.build]) do |f| %> <%= f.error_messages %>
diff --git a/railties/guides/source/layouts_and_rendering.textile b/railties/guides/source/layouts_and_rendering.textile index fad687466ebd8..92b36ab3e4997 100644 --- a/railties/guides/source/layouts_and_rendering.textile +++ b/railties/guides/source/layouts_and_rendering.textile @@ -1037,7 +1037,7 @@ You can also pass local variables into partials, making them even more powerful * +_form.html.erb+ -<% form_for(zone) do |f| %> +<%= form_for(zone) do |f| %>

Zone name
<%= f.text_field :name %> @@ -1181,11 +1181,11 @@ On pages generated by +NewsController+, you want to hide the top menu and add a <% content_for :stylesheets do %> #top_menu {display: none} #right_menu {float: right; background-color: yellow; color: black} -<% end -%> +<% end %> <% content_for :content do %>

Right menu items here
<%= yield(:news_content) or yield %> -<% end -%> +<% end %> <%= render :file => 'layouts/application' %>
diff --git a/railties/guides/source/nested_model_forms.textile b/railties/guides/source/nested_model_forms.textile index 4b685b214e2c7..4a79902232ebc 100644 --- a/railties/guides/source/nested_model_forms.textile +++ b/railties/guides/source/nested_model_forms.textile @@ -122,7 +122,7 @@ h5. Standard form Start out with a regular RESTful form: -<% form_for @person do |f| %> +<%= form_for @person do |f| %> <%= f.text_field :name %> <% end %> @@ -140,7 +140,7 @@ h5. Nested form for a single associated object Now add a nested form for the +address+ association: -<% form_for @person do |f| %> +<%= form_for @person do |f| %> <%= f.text_field :name %> <% f.fields_for :address do |af| %> @@ -181,7 +181,7 @@ h5. Nested form for a collection of associated objects The form code for an association collection is pretty similar to that of a single associated object: -<% form_for @person do |f| %> +<%= form_for @person do |f| %> <%= f.text_field :name %> <% f.fields_for :projects do |pf| %> diff --git a/railties/guides/source/testing.textile b/railties/guides/source/testing.textile index b291b541baa38..6e25515fed885 100644 --- a/railties/guides/source/testing.textile +++ b/railties/guides/source/testing.textile @@ -84,7 +84,7 @@ h5. ERb'in It Up ERb allows you embed ruby code within templates. Both the YAML and CSV fixture formats are pre-processed with ERb when you load fixtures. This allows you to use Ruby to help you generate some sample data. -<% earth_size = 20 -%> +<% earth_size = 20 %> mercury: size: <%= earth_size / 50 %> brightest_on: <%= 113.days.ago.to_s(:db) %> From 519efa637ba23fed62d549954de85eb2e1c384e6 Mon Sep 17 00:00:00 2001 From: Jaime Iniesta Date: Wed, 7 Apr 2010 17:56:51 +0200 Subject: [PATCH 03/22] Fixed duplicated IDs on associations_basics guide to validate XHTML 1.0 Strict --- .../guides/source/association_basics.textile | 163 +++++++++--------- 1 file changed, 82 insertions(+), 81 deletions(-) diff --git a/railties/guides/source/association_basics.textile b/railties/guides/source/association_basics.textile index 4256466becee6..f13f6db6ee7ed 100644 --- a/railties/guides/source/association_basics.textile +++ b/railties/guides/source/association_basics.textile @@ -603,11 +603,11 @@ The +belongs_to+ association supports these options: * +:touch+ * +:validate+ -h6. +:autosave+ +h6(#belongs_to-autosave). +:autosave+ If you set the +:autosave+ option to +true+, Rails will save any loaded members and destroy members that are marked for destruction whenever you save the parent object. -h6. +:class_name+ +h6(#belongs_to-class_name). +:class_name+ If the name of the other model cannot be derived from the association name, you can use the +:class_name+ option to supply the model name. For example, if an order belongs to a customer, but the actual name of the model containing customers is +Patron+, you'd set things up this way: @@ -617,7 +617,7 @@ class Order < ActiveRecord::Base end -h6. +:conditions+ +h6(#belongs_to-conditions). +:conditions+ The +:conditions+ option lets you specify the conditions that the associated object must meet (in the syntax used by a SQL +WHERE+ clause). @@ -666,13 +666,13 @@ end Counter cache columns are added to the containing model's list of read-only attributes through +attr_readonly+. -h6. +:dependent+ +h6(#belongs_to-dependent). +:dependent+ If you set the +:dependent+ option to +:destroy+, then deleting this object will call the +destroy+ method on the associated object to delete that object. If you set the +:dependent+ option to +:delete+, then deleting this object will delete the associated object _without_ calling its +destroy+ method. WARNING: You should not specify this option on a +belongs_to+ association that is connected with a +has_many+ association on the other class. Doing so can lead to orphaned records in your database. -h6. +:foreign_key+ +h6(#belongs_to-foreign_key). +:foreign_key+ By convention, Rails guesses that the column used to hold the foreign key on this model is the name of the association with the suffix +_id+ added. The +:foreign_key+ option lets you set the name of the foreign key directly: @@ -685,7 +685,7 @@ end TIP: In any case, Rails will not create foreign key columns for you. You need to explicitly define them as part of your migrations. -h6. +:include+ +h6(#belongs_to-includes). +:include+ You can use the +:include+ option to specify second-order associations that should be eager-loaded when this association is used. For example, consider these models: @@ -727,11 +727,11 @@ h6. +:polymorphic+ Passing +true+ to the +:polymorphic+ option indicates that this is a polymorphic association. Polymorphic associations were discussed in detail earlier in this guide. -h6. +:readonly+ +h6(#belongs_to-readonly). +:readonly+ If you set the +:readonly+ option to +true+, then the associated object will be read-only when retrieved via the association. -h6. +:select+ +h6(#belongs_to-select). +:select+ The +:select+ option lets you override the SQL +SELECT+ clause that is used to retrieve data about the associated object. By default, Rails retrieves all columns. @@ -759,11 +759,11 @@ class Order < ActiveRecord::Base end -h6. +:validate+ +h6(#belongs_to-validate). +:validate+ If you set the +:validate+ option to +true+, then associated objects will be validated whenever you save this object. By default, this is +false+: associated objects will not be validated when this object is saved. -h5. How To Know Whether There's an Associated Object? +h5(#belongs_to-how_to_know_whether_theres_an_associated_object). How To Know Whether There's an Associated Object? To know whether there's and associated object just check association.nil?: @@ -773,7 +773,7 @@ if @order.customer.nil? end -h5. When are Objects Saved? +h5(#belongs_to-when_are_objects_saved). When are Objects Saved? Assigning an object to a +belongs_to+ association does _not_ automatically save the object. It does not save the associated object either. @@ -869,15 +869,15 @@ The +has_one+ association supports these options: * +:through+ * +:validate+ -h6. +:as+ +h6(#has_one-as). +:as+ Setting the +:as+ option indicates that this is a polymorphic association. Polymorphic associations were discussed in detail earlier in this guide. -h6. +:autosave+ +h6(#has_one-autosave). +:autosave+ If you set the +:autosave+ option to +true+, Rails will save any loaded members and destroy members that are marked for destruction whenever you save the parent object. -h6. +:class_name+ +h6(#has_one-class_name). +:class_name+ If the name of the other model cannot be derived from the association name, you can use the +:class_name+ option to supply the model name. For example, if a supplier has an account, but the actual name of the model containing accounts is +Billing+, you'd set things up this way: @@ -887,7 +887,7 @@ class Supplier < ActiveRecord::Base end -h6. +:conditions+ +h6(#has_one-conditions). +:conditions+ The +:conditions+ option lets you specify the conditions that the associated object must meet (in the syntax used by a SQL +WHERE+ clause). @@ -897,11 +897,11 @@ class Supplier < ActiveRecord::Base end -h6. +:dependent+ +h6(#has_one-dependent). +:dependent+ If you set the +:dependent+ option to +:destroy+, then deleting this object will call the +destroy+ method on the associated object to delete that object. If you set the +:dependent+ option to +:delete+, then deleting this object will delete the associated object _without_ calling its +destroy+ method. If you set the +:dependent+ option to +:nullify+, then deleting this object will set the foreign key in the association object to +NULL+. -h6. +:foreign_key+ +h6(#has_one-foreign_key). +:foreign_key+ By convention, Rails guesses that the column used to hold the foreign key on the other model is the name of this model with the suffix +_id+ added. The +:foreign_key+ option lets you set the name of the foreign key directly: @@ -913,7 +913,7 @@ end TIP: In any case, Rails will not create foreign key columns for you. You need to explicitly define them as part of your migrations. -h6. +:include+ +h6(#has_one-include). +:include+ You can use the +:include+ option to specify second-order associations that should be eager-loaded when this association is used. For example, consider these models: @@ -949,39 +949,39 @@ class Representative < ActiveRecord::Base end -h6. +:order+ +h6(#has_one-order). +:order+ The +:order+ option dictates the order in which associated objects will be received (in the syntax used by a SQL +ORDER BY+ clause). Because a +has_one+ association will only retrieve a single associated object, this option should not be needed. -h6. +:primary_key+ +h6(#has_one-primary_key). +:primary_key+ By convention, Rails guesses that the column used to hold the primary key of this model is +id+. You can override this and explicitly specify the primary key with the +:primary_key+ option. -h6. +:readonly+ +h6(#has_one-readonly). +:readonly+ If you set the +:readonly+ option to +true+, then the associated object will be read-only when retrieved via the association. -h6. +:select+ +h6(#has_one-select). +:select+ The +:select+ option lets you override the SQL +SELECT+ clause that is used to retrieve data about the associated object. By default, Rails retrieves all columns. -h6. +:source+ +h6(#has_one-source). +:source+ The +:source+ option specifies the source association name for a +has_one :through+ association. -h6. +:source_type+ +h6(#has_one-source_type). +:source_type+ The +:source_type+ option specifies the source association type for a +has_one :through+ association that proceeds through a polymorphic association. -h6. +:through+ +h6(#has_one-through). +:through+ The +:through+ option specifies a join model through which to perform the query. +has_one :through+ associations were discussed in detail earlier in this guide. -h6. +:validate+ +h6(#has_one-validate). +:validate+ If you set the +:validate+ option to +true+, then associated objects will be validated whenever you save this object. By default, this is +false+: associated objects will not be validated when this object is saved. -h5. How To Know Whether There's an Associated Object? +h5(#has_one-how_to_know_whether_theres_an_associated_object). How To Know Whether There's an Associated Object? To know whether there's and associated object just check association.nil?: @@ -991,7 +991,7 @@ if @supplier.account.nil? end -h5. When are Objects Saved? +h5(#has_one-when_are_objects_saved). When are Objects Saved? When you assign an object to a +has_one+ association, that object is automatically saved (in order to update its foreign key). In addition, any object being replaced is also automatically saved, because its foreign key will change too. @@ -1005,7 +1005,7 @@ h4. +has_many+ Association Reference The +has_many+ association creates a one-to-many relationship with another model. In database terms, this association says that the other class will have a foreign key that refers to instances of this class. -h5. Methods Added +h5. Methods Added by +has_many+ When you declare a +has_many+ association, the declaring class automatically gains 13 methods related to the association: @@ -1049,7 +1049,7 @@ orders.build(attributes = {}, ...) orders.create(attributes = {}) -h6. collection(force_reload = false) +h6(#has_many-collection). collection(force_reload = false) The collection method returns an array of all of the associated objects. If there are no associated objects, it returns an empty array. @@ -1057,7 +1057,7 @@ The collection method returns an array of all of the associate @orders = @customer.orders -h6. collection<<(object, ...) +h6(#has_many-collection-lt_lt). collection<<(object, ...) The collection<< method adds one or more objects to the collection by setting their foreign keys to the primary key of the calling model. @@ -1065,7 +1065,7 @@ The collection<< method adds one or more objects to the collec @customer.orders << @order1 -h6. collection.delete(object, ...) +h6(#has_many-collection-delete). collection.delete(object, ...) The collection.delete method removes one or more objects from the collection by setting their foreign keys to +NULL+. @@ -1076,11 +1076,11 @@ The collection.delete method removes one or more objects from WARNING: Objects will be in addition destroyed if they're associated with +:dependent => :destroy+, and deleted if they're associated with +:dependent => :delete_all+. -h6. collection=objects +h6(#has_many-collection_equal). collection=objects The collection= method makes the collection contain only the supplied objects, by adding and deleting as appropriate. -h6. collection_singular_ids +h6(#has_many-collection_singular). collection_singular_ids The collection_singular_ids method returns an array of the ids of the objects in the collection. @@ -1088,11 +1088,11 @@ The collection_singular_ids method returns an array of the ids @order_ids = @customer.order_ids -h6. collection_singular_ids=ids +h6(#has_many-collection_singular_ids_ids). collection_singular_ids=ids The collection_singular_ids= method makes the collection contain only the objects identified by the supplied primary key values, by adding and deleting as appropriate. -h6. collection.clear +h6(#has_many-collection_clear). collection.clear The collection.clear method removes every object from the collection. This destroys the associated objects if they are associated with +:dependent => :destroy+, deletes them directly from the database if +:dependent => :delete_all+, and otherwise sets their foreign keys to +NULL+. @@ -1179,7 +1179,7 @@ The +has_many+ association supports these options: * +:uniq+ * +:validate+ -h6. +:as+ +h6(#has_many-as). +:as+ Setting the +:as+ option indicates that this is a polymorphic association, as discussed earlier in this guide. @@ -1187,7 +1187,7 @@ h6. +:autosave+ If you set the +:autosave+ option to +true+, Rails will save any loaded members and destroy members that are marked for destruction whenever you save the parent object. -h6. +:class_name+ +h6(#has_many-class_name). +:class_name+ If the name of the other model cannot be derived from the association name, you can use the +:class_name+ option to supply the model name. For example, if a customer has many orders, but the actual name of the model containing orders is +Transaction+, you'd set things up this way: @@ -1197,7 +1197,7 @@ class Customer < ActiveRecord::Base end -h6. +:conditions+ +h6(#has_many-conditions). +:conditions+ The +:conditions+ option lets you specify the conditions that the associated object must meet (in the syntax used by a SQL +WHERE+ clause). @@ -1230,27 +1230,27 @@ end Be sure to use single quotes. -h6. +:counter_sql+ +h6(#has_many-counter_sql). +:counter_sql+ Normally Rails automatically generates the proper SQL to count the association members. With the +:counter_sql+ option, you can specify a complete SQL statement to count them yourself. NOTE: If you specify +:finder_sql+ but not +:counter_sql+, then the counter SQL will be generated by substituting +SELECT COUNT(*) FROM+ for the +SELECT ... FROM+ clause of your +:finder_sql+ statement. -h6. +:dependent+ +h6(#has_many-dependent). +:dependent+ If you set the +:dependent+ option to +:destroy+, then deleting this object will call the +destroy+ method on the associated objects to delete those objects. If you set the +:dependent+ option to +:delete_all+, then deleting this object will delete the associated objects _without_ calling their +destroy+ method. If you set the +:dependent+ option to +:nullify+, then deleting this object will set the foreign key in the associated objects to +NULL+. NOTE: This option is ignored when you use the +:through+ option on the association. -h6. +:extend+ +h6(#has_many-extend). +:extend+ The +:extend+ option specifies a named module to extend the association proxy. Association extensions are discussed in detail later in this guide. -h6. +:finder_sql+ +h6(#has_many-finder_sql). +:finder_sql+ Normally Rails automatically generates the proper SQL to fetch the association members. With the +:finder_sql+ option, you can specify a complete SQL statement to fetch them yourself. If fetching objects requires complex multi-table SQL, this may be necessary. -h6. +:foreign_key+ +h6(#has_many-foreign_key). +:foreign_key+ By convention, Rails guesses that the column used to hold the foreign key on the other model is the name of this model with the suffix +_id+ added. The +:foreign_key+ option lets you set the name of the foreign key directly: @@ -1262,7 +1262,7 @@ end TIP: In any case, Rails will not create foreign key columns for you. You need to explicitly define them as part of your migrations. -h6. +:group+ +h6(:has_many-group). +:group+ The +:group+ option supplies an attribute name to group the result set by, using a +GROUP BY+ clause in the finder SQL. @@ -1272,7 +1272,7 @@ class Customer < ActiveRecord::Base end -h6. +:include+ +h6(#has_many-include). +:include+ You can use the +:include+ option to specify second-order associations that should be eager-loaded when this association is used. For example, consider these models: @@ -1308,7 +1308,7 @@ class LineItem < ActiveRecord::Base end -h6. +:limit+ +h6(#has_many-limit). +:limit+ The +:limit+ option lets you restrict the total number of objects that will be fetched through an association. @@ -1319,11 +1319,11 @@ class Customer < ActiveRecord::Base end -h6. +:offset+ +h6(#has_many-offset). +:offset+ The +:offset+ option lets you specify the starting offset for fetching objects via an association. For example, if you set +:offset => 11+, it will skip the first 11 records. -h6. +:order+ +h6(#has_many-order). +:order+ The +:order+ option dictates the order in which associated objects will be received (in the syntax used by a SQL +ORDER BY+ clause). @@ -1333,41 +1333,41 @@ class Customer < ActiveRecord::Base end -h6. +:primary_key+ +h6(#has_many-primary_key). +:primary_key+ By convention, Rails guesses that the column used to hold the primary key of the association is +id+. You can override this and explicitly specify the primary key with the +:primary_key+ option. -h6. +:readonly+ +h6(#has_many-readonly). +:readonly+ If you set the +:readonly+ option to +true+, then the associated objects will be read-only when retrieved via the association. -h6. +:select+ +h6(#has_many-select). +:select+ The +:select+ option lets you override the SQL +SELECT+ clause that is used to retrieve data about the associated objects. By default, Rails retrieves all columns. WARNING: If you specify your own +:select+, be sure to include the primary key and foreign key columns of the associated model. If you do not, Rails will throw an error. -h6. +:source+ +h6(#has_many-source). +:source+ The +:source+ option specifies the source association name for a +has_many :through+ association. You only need to use this option if the name of the source association cannot be automatically inferred from the association name. -h6. +:source_type+ +h6(#has_many-source_type). +:source_type+ The +:source_type+ option specifies the source association type for a +has_many :through+ association that proceeds through a polymorphic association. -h6. +:through+ +h6(#has_many-through). +:through+ The +:through+ option specifies a join model through which to perform the query. +has_many :through+ associations provide a way to implement many-to-many relationships, as discussed earlier in this guide. -h6. +:uniq+ +h6(#has_many-uniq). +:uniq+ Specify the +:uniq => true+ option to remove duplicates from the collection. This is most useful in conjunction with the +:through+ option. -h6. +:validate+ +h6(#has_many-validate). +:validate+ If you set the +:validate+ option to +false+, then associated objects will not be validated whenever you save this object. By default, this is +true+: associated objects will be validated when this object is saved. -h5. When are Objects Saved? +h5(#has_many-when_are_objects_saved). When are Objects Saved? When you assign an object to a +has_many+ association, that object is automatically saved (in order to update its foreign key). If you assign multiple objects in one statement, then they are all saved. @@ -1381,7 +1381,7 @@ h4. +has_and_belongs_to_many+ Association Reference The +has_and_belongs_to_many+ association creates a many-to-many relationship with another model. In database terms, this associates two classes via an intermediate join table that includes foreign keys referring to each of the classes. -h5. Methods Added +h5. Methods Added by +has_and_belongs_to_many+ When you declare a +has_and_belongs_to_many+ association, the declaring class automatically gains 13 methods related to the association: @@ -1478,7 +1478,7 @@ h6. collection.clear The collection.clear method removes every object from the collection by deleting the rows from the joining table. This does not destroy the associated objects. -h6. collection.empty? +h6(#has_and_belongs_to_many-collection-empty). collection.empty? The collection.empty? method returns +true+ if the collection does not contain any associated objects. @@ -1488,7 +1488,7 @@ The collection.empty? method returns +true+ if the collection <% end %> -h6. collection.size +h6(#has_and_belongs_to_many-collection-size). collection.size The collection.size method returns the number of objects in the collection. @@ -1496,7 +1496,7 @@ The collection.size method returns the number of objects in th @assembly_count = @part.assemblies.size -h6. collection.find(...) +h6(#has_and_belongs_to_many-collection-find). collection.find(...) The collection.find method finds objects within the collection. It uses the same syntax and options as +ActiveRecord::Base.find+. It also adds the additional condition that the object must be in the collection. @@ -1505,7 +1505,7 @@ The collection.find method finds objects within the collection :conditions => ["created_at > ?", 2.days.ago]) -h6. collection.exists?(...) +h6(#has_and_belongs_to_many-collection-exists). collection.exists?(...) The collection.exists? method checks whether an object meeting the supplied conditions exists in the collection. It uses the same syntax and options as +ActiveRecord::Base.exists?+. @@ -1518,7 +1518,7 @@ The collection.build method returns a new object of the associ {:assembly_name => "Transmission housing"}) -h6. collection.create(attributes = {}) +h6(#has_and_belongs_to_many-create-attributes). collection.create(attributes = {}) The collection.create method returns a new object of the associated type. This object will be instantiated from the passed attributes, the link through the join table will be created, and the associated object _will_ be saved (assuming that it passes any validations). @@ -1575,11 +1575,11 @@ class User < ActiveRecord::Base end -h6. +:autosave+ +h6(#has_and_belongs_to_many-autosave). +:autosave+ If you set the +:autosave+ option to +true+, Rails will save any loaded members and destroy members that are marked for destruction whenever you save the parent object. -h6. +:class_name+ +h6(#has_and_belongs_to_many-class_name). +:class_name+ If the name of the other model cannot be derived from the association name, you can use the +:class_name+ option to supply the model name. For example, if a part has many assemblies, but the actual name of the model containing assemblies is +Gadget+, you'd set things up this way: @@ -1589,7 +1589,7 @@ class Parts < ActiveRecord::Base end -h6. +:conditions+ +h6(#has_and_belongs_to_many-conditions). +:conditions+ The +:conditions+ option lets you specify the conditions that the associated object must meet (in the syntax used by a SQL +WHERE+ clause). @@ -1611,7 +1611,7 @@ end If you use a hash-style +:conditions+ option, then record creation via this association will be automatically scoped using the hash. In this case, using +@parts.assemblies.create+ or +@parts.assemblies.build+ will create orders where the +factory+ column has the value "Seattle". -h6. +:counter_sql+ +h6(#has_and_belongs_to_many-counter_sql). +:counter_sql+ Normally Rails automatically generates the proper SQL to count the association members. With the +:counter_sql+ option, you can specify a complete SQL statement to count them yourself. @@ -1621,15 +1621,15 @@ h6. +:delete_sql+ Normally Rails automatically generates the proper SQL to remove links between the associated classes. With the +:delete_sql+ option, you can specify a complete SQL statement to delete them yourself. -h6. +:extend+ +h6(#has_and_belongs_to_many-extend). +:extend+ The +:extend+ option specifies a named module to extend the association proxy. Association extensions are discussed in detail later in this guide. -h6. +:finder_sql+ +h6(#has_and_belongs_to_many-finder_sql). +:finder_sql+ Normally Rails automatically generates the proper SQL to fetch the association members. With the +:finder_sql+ option, you can specify a complete SQL statement to fetch them yourself. If fetching objects requires complex multi-table SQL, this may be necessary. -h6. +:foreign_key+ +h6(#has_and_belongs_to_many-foreign_key). +:foreign_key+ By convention, Rails guesses that the column in the join table used to hold the foreign key pointing to this model is the name of this model with the suffix +_id+ added. The +:foreign_key+ option lets you set the name of the foreign key directly: @@ -1641,7 +1641,7 @@ class User < ActiveRecord::Base end -h6. +:group+ +h6(#has_and_belongs_to_many-group). +:group+ The +:group+ option supplies an attribute name to group the result set by, using a +GROUP BY+ clause in the finder SQL. @@ -1651,7 +1651,7 @@ class Parts < ActiveRecord::Base end -h6. +:include+ +h6(#has_and_belongs_to_many-include). +:include+ You can use the +:include+ option to specify second-order associations that should be eager-loaded when this association is used. @@ -1663,7 +1663,7 @@ h6. +:join_table+ If the default name of the join table, based on lexical ordering, is not what you want, you can use the +:join_table+ option to override the default. -h6. +:limit+ +h6(#has_and_belongs_to_many-limit). +:limit+ The +:limit+ option lets you restrict the total number of objects that will be fetched through an association. @@ -1674,11 +1674,11 @@ class Parts < ActiveRecord::Base end -h6. +:offset+ +h6(#has_and_belongs_to_many-offset). +:offset+ The +:offset+ option lets you specify the starting offset for fetching objects via an association. For example, if you set +:offset => 11+, it will skip the first 11 records. -h6. +:order+ +h6(#has_and_belongs_to_many-order). +:order+ The +:order+ option dictates the order in which associated objects will be received (in the syntax used by a SQL +ORDER BY+ clause). @@ -1688,23 +1688,23 @@ class Parts < ActiveRecord::Base end -h6. +:readonly+ +h6(#has_and_belongs_to_many-readonly). +:readonly+ If you set the +:readonly+ option to +true+, then the associated objects will be read-only when retrieved via the association. -h6. +:select+ +h6(#has_and_belongs_to_many-select). +:select+ The +:select+ option lets you override the SQL +SELECT+ clause that is used to retrieve data about the associated objects. By default, Rails retrieves all columns. -h6. +:uniq+ +h6(#has_and_belongs_to_many-uniq). +:uniq+ Specify the +:uniq => true+ option to remove duplicates from the collection. -h6. +:validate+ +h6(#has_and_belongs_to_many-validate). +:validate+ If you set the +:validate+ option to +false+, then associated objects will not be validated whenever you save this object. By default, this is +true+: associated objects will be validated when this object is saved. -h5. When are Objects Saved? +h5(#has_and_belongs_to_many-when_are_objects_saved). When are Objects Saved? When you assign an object to a +has_and_belongs_to_many+ association, that object is automatically saved (in order to update the join table). If you assign multiple objects in one statement, then they are all saved. @@ -1809,6 +1809,7 @@ h3. Changelog "Lighthouse ticket":http://rails.lighthouseapp.com/projects/16213-rails-guides/tickets/11 +* April 7, 2010: Fixed document to validate XHTML 1.0 Strict. "Jaime Iniesta":http://jaimeiniesta.com * April 19, 2009: Added +:touch+ option to +belongs_to+ associations by "Mike Gunderloy":credits.html#mgunderloy * February 1, 2009: Added +:autosave+ option "Mike Gunderloy":credits.html#mgunderloy * September 28, 2008: Corrected +has_many :through+ diagram, added polymorphic diagram, some reorganization by "Mike Gunderloy":credits.html#mgunderloy . First release version. From 82526e8276e2630372dd423d882d75757f7bcd03 Mon Sep 17 00:00:00 2001 From: Jaime Iniesta Date: Wed, 7 Apr 2010 18:19:17 +0200 Subject: [PATCH 04/22] Fixed duplicated IDs on active_record_querying guide to validate XHTML 1.0 Strict --- railties/guides/source/active_record_querying.textile | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/railties/guides/source/active_record_querying.textile b/railties/guides/source/active_record_querying.textile index a993dad900756..edd8ea36407ab 100644 --- a/railties/guides/source/active_record_querying.textile +++ b/railties/guides/source/active_record_querying.textile @@ -274,7 +274,7 @@ Client.where( This makes for clearer readability if you have a large number of variable conditions. -h5. Range Conditions +h5(#array-range_conditions). Range Conditions If you're looking for a range inside of a table (for example, users created in a certain timeframe) you can use the conditions option coupled with the +IN+ SQL statement for this. If you had two dates coming in from a controller you could do something like this to look for a range: @@ -353,7 +353,7 @@ The field name does not have to be a symbol it can also be a string: Client.where({ 'locked' => true }) -h5. Range Conditions +h5(#hash-range_conditions). Range Conditions The good thing about this is that we can pass in a range for our fields without it generating a large query as shown in the preamble of this section. From 9364c70cd5c9d5c6fab08c77fd3ac0f580af09d4 Mon Sep 17 00:00:00 2001 From: Jaime Iniesta Date: Wed, 7 Apr 2010 18:21:31 +0200 Subject: [PATCH 05/22] update changelog --- railties/guides/source/active_record_querying.textile | 1 + 1 file changed, 1 insertion(+) diff --git a/railties/guides/source/active_record_querying.textile b/railties/guides/source/active_record_querying.textile index edd8ea36407ab..e47615f070aa1 100644 --- a/railties/guides/source/active_record_querying.textile +++ b/railties/guides/source/active_record_querying.textile @@ -934,6 +934,7 @@ h3. Changelog "Lighthouse ticket":http://rails.lighthouseapp.com/projects/16213-rails-guides/tickets/16 +* April 7, 2010: Fixed document to validate XHTML 1.0 Strict. "Jaime Iniesta":http://jaimeiniesta.com * February 3, 2010: Update to Rails 3 by "James Miller":credits.html#bensie * February 7, 2009: Second version by "Pratik":credits.html#lifo * December 29 2008: Initial version by "Ryan Bigg":credits.html#radar From f23fff6a6e2d4d22dae7e32dd54f6c9359ff3859 Mon Sep 17 00:00:00 2001 From: eparreno Date: Thu, 8 Apr 2010 16:19:26 +0200 Subject: [PATCH 06/22] fix font format in Command Line Basics section --- railties/guides/source/command_line.textile | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/railties/guides/source/command_line.textile b/railties/guides/source/command_line.textile index c8882126042a7..c0182f236bd24 100644 --- a/railties/guides/source/command_line.textile +++ b/railties/guides/source/command_line.textile @@ -18,12 +18,12 @@ h3. Command Line Basics There are a few commands that are absolutely critical to your everyday usage of Rails. In the order of how much you'll probably use them are: -* rails console -* rails server -* rake -* rails generate -* rails dbconsole -* rails app_name +* rails console +* rails server +* rake +* rails generate +* rails dbconsole +* rails app_name Let's create a simple Rails application to step through each of these commands in context. From e39950847c6f4a8e483f3dc44f50b6c0edc7b128 Mon Sep 17 00:00:00 2001 From: eparreno Date: Thu, 8 Apr 2010 16:38:26 +0200 Subject: [PATCH 07/22] CL guide: convert rails server to shell text --- railties/guides/source/command_line.textile | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/railties/guides/source/command_line.textile b/railties/guides/source/command_line.textile index c0182f236bd24..a8397a5b80eef 100644 --- a/railties/guides/source/command_line.textile +++ b/railties/guides/source/command_line.textile @@ -246,9 +246,13 @@ $ rake db:migrate INFO: Let's talk about unit tests. Unit tests are code that tests and makes assertions about code. In unit testing, we take a little part of code, say a method of a model, and test its inputs and outputs. Unit tests are your friend. The sooner you make peace with the fact that your quality of life will drastically increase when you unit test your code, the better. Seriously. We'll make one in a moment. -Let's see the interface Rails created for us. rails server; http://localhost:3000/high_scores +Let's see the interface Rails created for us. -We can create new high scores (55,160 on Space Invaders!) + +$ rails server + + +Go to your browser and open "http://localhost:3000/high_scores":http://localhost:3000/high_scores, now we can create new high scores (55,160 on Space Invaders!) h4. +rails console+ From 07b09bd404a39a9b2801d62fbce60416bba92ec8 Mon Sep 17 00:00:00 2001 From: eparreno Date: Thu, 8 Apr 2010 16:45:53 +0200 Subject: [PATCH 08/22] CL guide: fix font format in rails plugin section --- railties/guides/source/command_line.textile | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/railties/guides/source/command_line.textile b/railties/guides/source/command_line.textile index a8397a5b80eef..f2b53023a5e90 100644 --- a/railties/guides/source/command_line.textile +++ b/railties/guides/source/command_line.textile @@ -264,12 +264,12 @@ h4. +rails dbconsole+ h4. +rails plugin+ -The +rails plugin+ command simplifies plugin management; think a miniature version of the Gem utility. Let's walk through installing a plugin. You can call the sub-command *discover*, which sifts through repositories looking for plugins, or call *source* to add a specific repository of plugins, or you can specify the plugin location directly. +The +rails plugin+ command simplifies plugin management; think a miniature version of the Gem utility. Let's walk through installing a plugin. You can call the sub-command +discover+, which sifts through repositories looking for plugins, or call +source+ to add a specific repository of plugins, or you can specify the plugin location directly. -Let's say you're creating a website for a client who wants a small accounting system. Every event having to do with money must be logged, and must never be deleted. Wouldn't it be great if we could override the behavior of a model to never actually take its record out of the database, but *instead*, just set a field? +Let's say you're creating a website for a client who wants a small accounting system. Every event having to do with money must be logged, and must never be deleted. Wouldn't it be great if we could override the behavior of a model to never actually take its record out of the database, but instead, just set a field? + +There is such a thing! The plugin we're installing is called +acts_as_paranoid+, and it lets models implement a +deleted_at+ column that gets set when you call destroy. Later, when calling find, the plugin will tack on a database check to filter out "deleted" things. -There is such a thing! The plugin we're installing is called "acts_as_paranoid", and it lets models implement a "deleted_at" column that gets set when you call destroy. Later, when calling find, the plugin will tack on a database check to filter out "deleted" things. -================================================================================== $ rails plugin install http://svn.techno-weenie.net/projects/plugins/acts_as_paranoid + ./CHANGELOG From 7005e6db471ca9920ab680ce6c4fc5f0974e8cbb Mon Sep 17 00:00:00 2001 From: Ryan Bigg Date: Tue, 6 Apr 2010 08:46:57 +1000 Subject: [PATCH 09/22] Further expansion into how Bundler loads the gemfile. --- railties/guides/source/initialization.textile | 51 ++++++++++++++++++- 1 file changed, 49 insertions(+), 2 deletions(-) diff --git a/railties/guides/source/initialization.textile b/railties/guides/source/initialization.textile index 2d64510c2f4d4..1b76034f82018 100644 --- a/railties/guides/source/initialization.textile +++ b/railties/guides/source/initialization.textile @@ -2021,7 +2021,7 @@ This sets up a couple of important things initially. If you specify a gem like t gem 'rails', "2.3.4" -This sets +options+ to be an empty hash, but +version+ to be +"2.3.4"+. TODO: How does one pass options and versions? +This sets +options+ to be an empty hash, but +version+ to be +"2.3.4"+. TODO: How does one pass options and versions at the same time? In the Gemfile for a default Rails project, the first +gem+ line is: @@ -2054,7 +2054,54 @@ This line will check that +options+ contains no deprecated options by using the end -+_normalize_hash+ will convert all the keys in the +opts+ hash to strings. ++_normalize_hash+ will convert all the keys in the +opts+ hash to strings. There is neither a +git+ or a +path+ key in the +opts+ hash so the next couple of lines are ignored, then the +source+ and +group+ keys are set up. + +TODO: Maybe it is best to cover what would happen in the case these lines did exist? + +The next line goes about defining a dependency for this gem: + + + @dependencies << Dependency.new(name, version, options) + + +This class is defined like this: + + + module Bundler + class Dependency < Gem::Dependency + attr_reader :autorequire + attr_reader :groups + + def initialize(name, version, options = {}, &blk) + super(name, version) + + @autorequire = nil + @groups = Array(options["group"] || :default).map { |g| g.to_sym } + @source = options["source"] + + if options.key?('require') + @autorequire = Array(options['require'] || []) + end + end + end + end + + +The +initialize+ method in +Gem::Dependency+ is defined: + + + def initialize(name, version_requirements, type=:runtime) + @name = name + unless TYPES.include? type + raise ArgumentError, "Valid types are #{TYPES.inspect}, not #{@type.inspect}" + end + @type = type + @version_requirements = Gem::Requirement.create version_requirements + @version_requirement = nil # Avoid warnings. + end + + + From f4f24cc6412d5ded1ee3b149cb0a9967ada281f7 Mon Sep 17 00:00:00 2001 From: Ryan Bigg Date: Fri, 9 Apr 2010 06:45:49 +1000 Subject: [PATCH 10/22] Mention a way to turn off bundler and begin talking about version_requirements --- railties/guides/source/initialization.textile | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/railties/guides/source/initialization.textile b/railties/guides/source/initialization.textile index 1b76034f82018..9b6727b7408e7 100644 --- a/railties/guides/source/initialization.textile +++ b/railties/guides/source/initialization.textile @@ -1790,6 +1790,8 @@ Now that Rails has finished loading all the Railties by way of +require 'rails/a Bundler.require :default, Rails.env +NOTE: It is worth mentioning here that you are not tied to using Bundler with Rails 3, but it is (of course) advised that you do. To "turn off" Bundler, comment out or remove the corresponding lines in _config/application.rb_ and _config/boot.rb_. + Bundler was +require+'d back in _config/boot.rb_ and now we'll dive into the internals of Bundler to determine precisely what this line accomplishes. h4. +Bundler.require+ @@ -2101,6 +2103,8 @@ The +initialize+ method in +Gem::Dependency+ is defined: end +The +version_requirements+ that was passed in here + From ce30d0f2bbd331336ac36aa16549f1e747c5a411 Mon Sep 17 00:00:00 2001 From: Ryan Bigg Date: Fri, 9 Apr 2010 14:03:58 +1000 Subject: [PATCH 11/22] Further work on the bundler section. Almost there now. --- railties/guides/source/initialization.textile | 117 +++++++++++++++++- 1 file changed, 111 insertions(+), 6 deletions(-) diff --git a/railties/guides/source/initialization.textile b/railties/guides/source/initialization.textile index 9b6727b7408e7..e256503067041 100644 --- a/railties/guides/source/initialization.textile +++ b/railties/guides/source/initialization.textile @@ -1911,15 +1911,13 @@ The next method to be called here would be +definition+ and it is defined like end -We do not have +settings[:disabled_shared_gems]+ set to true so this will execute the code under the +else+. The +ENV["GEM_PATH"]+ will resemble +/usr/local/lib/ruby/gems/1.9.1:/home/you/.gem/ruby/1.9.1:/usr/local/lib/ruby/gems/1.9.1+ - -TODO: Why the duplicates? Added an issue: http://github.com/carlhuda/bundler/issues#issue/249 +We do not have +settings[:disabled_shared_gems]+ set to true so this will execute the code under the +else+. The +ENV["GEM_PATH"]+ will resemble +/usr/local/lib/ruby/gems/1.9.1:/home/you/.gem/ruby/1.9.1+ And +ENV["GEM_HOME"]+ will be the path to the gems installed into your home directory by Bundler, something resembling +/home/you/.bundle/ruby/1.9.1+. After +configure_gem_home_and_path+ is done the +definition+ method goes about creating a +Definition+ from either +Gemfile.lock+ if it exists, or the +gemfile+ previously located. +Gemfile.lock+ only exists if +bundle lock+ has been ran and so far it has not. -+Definition.from_lock+ is defined in _lib/definition.rb_: ++Definition.from_gemfile+ is defined in _lib/bundler/definition.rb_: def self.from_gemfile(gemfile) @@ -1933,7 +1931,7 @@ After +configure_gem_home_and_path+ is done the +definition+ method goes about c end -Now that the +gemfile+ is located +Dsl.evaluate+ goes about loading it. The code for this can be found in _lib/dsl.rb_: +Now that the +gemfile+ is located +Dsl.evaluate+ goes about loading it. The code for this can be found in _lib/bundler/dsl.rb_: def self.evaluate(gemfile) @@ -2103,11 +2101,118 @@ The +initialize+ method in +Gem::Dependency+ is defined: end -The +version_requirements+ that was passed in here +The +version_requirements+ that was passed in here will be inspected by +Gem::Requirement.create+ and return, for our +3.0.0beta2+ version string a +Gem::Requirement+ object: + + + #]]> + + +Going back to +Bundler::Dependency+, the next line simply sets +@autorequire+ to +nil+ and the next line is a little more interesting: + + + @autorequire = nil + @groups = Array(options["group"] || :default).map { |g| g.to_sym } + + +Here, bundler sets the +groups+ variable to be whatever +group+ we've set for this gem and also demonstrates through code that the +group+ option allows for multiple groups, so in the _Gemfile_ we can specify the same gem for multiple groups: + + + group :test, :cucumber do + gem 'faker' + end + + +The final lines in +initialize+ work on the +require+ option which is not passed: + + + if options.key?('require') + @autorequire = Array(options['require'] || []) + end + + +If it were to be used in the _Gemfile_, it would look like this: + + + gem 'thinking-sphinx', :require => "thinking_sphinx" + + +So far, this is what simply loading the _Gemfile_ does. + +h3. Bring forth the gems + +Now that the _Gemfile_ has finished being parsed, the next line is: + + + builder.to_definition + + +This method is defined in _lib/bundler/dsl.rb_ and does this: + + + def to_definition + Definition.new(@dependencies, @sources) + end + + +The +Bundler::Definition#initialize+ method is this: + + + def initialize(dependencies, sources) + @dependencies = dependencies + @sources = sources + end + + +Now Bundler has a +Bundler::Definition+ object to be passed back to the +load+ method from _lib/bundler.rb_: + + + def load(gemfile = default_gemfile) + root = Pathname.new(gemfile).dirname + Runtime.new root, definition(gemfile) + end + + +The +Bundler::Runtime+ class inherits from +Bundler::Environment+ and the reason this is pointed out is because +super+ is used in the +initialize+ method in +Bundler::Runtime+: + + + super + if locked? + write_rb_lock + end + + +Thankfully, the +Bundler::Environment#initialize+ method is nothing too complex: + + + def initialize(root, definition) + @root = root + @definition = definition + end + + +The +locked?+ method checks if the _Gemfile.lock_ or _.bundler/environment.rb_ files exist: + + def locked? + File.exist?("#{root}/Gemfile.lock") || File.exist?("#{root}/.bundle/environment.rb") + end + +And if they do will call +write_rb_lock+: + + def write_rb_lock + shared_helpers = File.read(File.expand_path("../shared_helpers.rb", __FILE__)) + template = File.read(File.expand_path("../templates/environment.erb", __FILE__)) + erb = ERB.new(template, nil, '-') + FileUtils.mkdir_p(rb_lock_file.dirname) + File.open(rb_lock_file, 'w') do |f| + f.puts erb.result(binding) + end + end + +This will write out to _.bundler/environment.rb_ the state of the current environment. h3. Firing it up! From 395dbd53ed87aa8c7e06ffeca9c80af6d50a9f18 Mon Sep 17 00:00:00 2001 From: Ryan Bigg Date: Fri, 9 Apr 2010 15:34:13 +1000 Subject: [PATCH 12/22] Continue expanding on Bundler. --- railties/guides/source/initialization.textile | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) diff --git a/railties/guides/source/initialization.textile b/railties/guides/source/initialization.textile index e256503067041..7013c3c3244ac 100644 --- a/railties/guides/source/initialization.textile +++ b/railties/guides/source/initialization.textile @@ -2214,6 +2214,25 @@ And if they do will call +write_rb_lock+: This will write out to _.bundler/environment.rb_ the state of the current environment. +Now a quick refresher. Bundler is still evaulating the code for the +require+ in _lib/bundler.rb_, and the +groups+ variable here is an +Array+ containing two elements: +:default+ and the current Rails environment: +development+: + + + def require(*groups) + gemfile = default_gemfile + load(gemfile).require(*groups) + end + + +The second +require+ method here: + + + load(gemfile).require(*groups) + + +Is defined on _bundler/runtime.rb_ + + + h3. Firing it up! From 11f838dc2e6a32a9e55e77f2c1114dbbfa6af6b2 Mon Sep 17 00:00:00 2001 From: Ryan Bigg Date: Fri, 9 Apr 2010 17:52:34 +1000 Subject: [PATCH 13/22] Expansion on require method from runtime.rb --- railties/guides/source/initialization.textile | 37 ++++++++++++++++++- 1 file changed, 36 insertions(+), 1 deletion(-) diff --git a/railties/guides/source/initialization.textile b/railties/guides/source/initialization.textile index 7013c3c3244ac..d8d119f6087e2 100644 --- a/railties/guides/source/initialization.textile +++ b/railties/guides/source/initialization.textile @@ -2229,9 +2229,44 @@ The second +require+ method here: load(gemfile).require(*groups) -Is defined on _bundler/runtime.rb_ +Is defined on _bundler/runtime.rb_: + + def require(*groups) + groups.map! { |g| g.to_sym } + groups = [:default] if groups.empty? + autorequires = autorequires_for_groups(*groups) + + groups.each do |group| + (autorequires[group] || [[]]).each do |path, explicit| + if explicit + Kernel.require(path) + else + begin + Kernel.require(path) + rescue LoadError + end + end + end + end + end + + +This method does TODO: Describe what magic this undertakes. +The first method to be called here is +autorequires_for_groups+: + + + def autorequires_for_groups(*groups) + groups.map! { |g| g.to_sym } + autorequires = Hash.new { |h,k| h[k] = [] } + + ordered_deps = [] + specs_for(*groups).each do |g| + dep = @definition.dependencies.find{|d| d.name == g.name } + ordered_deps << dep if dep && !ordered_deps.include?(dep) + end + h3. Firing it up! From ee8e9d548472fb8cb8792a569e579c6513be77d6 Mon Sep 17 00:00:00 2001 From: Xavier Noria Date: Fri, 9 Apr 2010 14:02:44 -0700 Subject: [PATCH 14/22] release notes: updates instructions for installing the current beta --- railties/guides/source/3_0_release_notes.textile | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/railties/guides/source/3_0_release_notes.textile b/railties/guides/source/3_0_release_notes.textile index 86d72db1253d7..024cb482882ac 100644 --- a/railties/guides/source/3_0_release_notes.textile +++ b/railties/guides/source/3_0_release_notes.textile @@ -20,14 +20,10 @@ endprologue. WARNING: Rails 3.0 is currently in beta. This means that there are probably bugs and that you should "report them":http://rails.lighthouseapp.com/projects/8994-ruby-on-rails/overview if you see them. You also may not want to run the NORAD nuclear launch application off a beta version. But if you're starting development on a new application and you don't mind getting wind in your hair, please do jump on board! -TIP: To install the Rails 3 prerelease beta using rubygems you have to install all the Rails dependencies first as these will not be installed for you by rubygems: +To install the last Rails 3 beta: # Use sudo if your setup requires it -gem install tzinfo builder i18n memcache-client rack \ - rake rack-test erubis mail text-format \ - thor bundler -gem install rack-mount -v=0.4 gem install rails --pre From a3e70ad57845bb24a85a00fbce5066b1cf367765 Mon Sep 17 00:00:00 2001 From: Rohit Arondekar Date: Sat, 10 Apr 2010 18:28:57 -0700 Subject: [PATCH 15/22] Fixed indentation of database.yml examples. --- .../guides/source/getting_started.textile | 26 +++++++++---------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/railties/guides/source/getting_started.textile b/railties/guides/source/getting_started.textile index 2bbb4dc252cdd..cbace177f9656 100644 --- a/railties/guides/source/getting_started.textile +++ b/railties/guides/source/getting_started.textile @@ -232,13 +232,13 @@ If you choose to use MySQL instead of the shipped Sqlite3 database, your +config development: -adapter: mysql -encoding: utf8 -database: blog_development -pool: 5 -username: root -password: -socket: /tmp/mysql.sock + adapter: mysql + encoding: utf8 + database: blog_development + pool: 5 + username: root + password: + socket: /tmp/mysql.sock If your development computer's MySQL installation includes a root user with an empty password, this configuration should work for you. Otherwise, change the username and password in the +development+ section as appropriate. @@ -249,12 +249,12 @@ Finally if you choose to use PostgreSQL, your +config/database.yml+ will be cust development: -adapter: postgresql -encoding: unicode -database: blog_development -pool: 5 -username: blog -password: + adapter: postgresql + encoding: unicode + database: blog_development + pool: 5 + username: blog + password: Change the username and password in the +development+ section as appropriate. From c7e2b6413df8b1c5609f6e5434a2557f2e178cd7 Mon Sep 17 00:00:00 2001 From: Rohit Arondekar Date: Sat, 10 Apr 2010 18:28:57 -0700 Subject: [PATCH 16/22] Fixed indentation of database.yml examples. --- .../guides/source/getting_started.textile | 26 +++++++++---------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/railties/guides/source/getting_started.textile b/railties/guides/source/getting_started.textile index 2bbb4dc252cdd..cbace177f9656 100644 --- a/railties/guides/source/getting_started.textile +++ b/railties/guides/source/getting_started.textile @@ -232,13 +232,13 @@ If you choose to use MySQL instead of the shipped Sqlite3 database, your +config development: -adapter: mysql -encoding: utf8 -database: blog_development -pool: 5 -username: root -password: -socket: /tmp/mysql.sock + adapter: mysql + encoding: utf8 + database: blog_development + pool: 5 + username: root + password: + socket: /tmp/mysql.sock If your development computer's MySQL installation includes a root user with an empty password, this configuration should work for you. Otherwise, change the username and password in the +development+ section as appropriate. @@ -249,12 +249,12 @@ Finally if you choose to use PostgreSQL, your +config/database.yml+ will be cust development: -adapter: postgresql -encoding: unicode -database: blog_development -pool: 5 -username: blog -password: + adapter: postgresql + encoding: unicode + database: blog_development + pool: 5 + username: blog + password: Change the username and password in the +development+ section as appropriate. From 41bcf06d3289e2292fcc3819c8f104252af36adc Mon Sep 17 00:00:00 2001 From: Malcolm Locke Date: Mon, 12 Apr 2010 23:47:33 +1200 Subject: [PATCH 17/22] low and behold => lo and behold! --- railties/guides/source/testing.textile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/railties/guides/source/testing.textile b/railties/guides/source/testing.textile index 6e25515fed885..c4f7ff8e92f4a 100644 --- a/railties/guides/source/testing.textile +++ b/railties/guides/source/testing.textile @@ -65,7 +65,7 @@ YAML-formatted fixtures are a very human-friendly way to describe your sample da Here's a sample YAML fixture file: -# low & behold! I am a YAML comment! +# lo & behold! I am a YAML comment! david: name: David Heinemeier Hansson birthday: 1979-10-15 From 84e46437fa50782dd38b96b8df00ca8b017c892e Mon Sep 17 00:00:00 2001 From: Anil Wadghule Date: Mon, 12 Apr 2010 22:20:55 +0530 Subject: [PATCH 18/22] Replace 'RAILS_ROOT' to 'Rails.root' and 'RAILS_ENV' to 'Rails.env' in significant places. --- actionpack/lib/action_controller/caching/pages.rb | 2 +- railties/guides/source/3_0_release_notes.textile | 2 +- railties/guides/source/command_line.textile | 2 +- railties/guides/source/configuring.textile | 2 +- railties/guides/source/debugging_rails_applications.textile | 2 +- railties/guides/source/i18n.textile | 6 +++--- railties/guides/source/migrations.textile | 2 +- railties/guides/source/rails_application_templates.textile | 2 +- railties/guides/source/rails_on_rack.textile | 6 +++--- railties/lib/rails/application/configuration.rb | 2 +- railties/lib/rails/webrick_server.rb | 4 ++-- 11 files changed, 16 insertions(+), 16 deletions(-) diff --git a/actionpack/lib/action_controller/caching/pages.rb b/actionpack/lib/action_controller/caching/pages.rb index 2a0a1107eba84..21a424e6f04bf 100644 --- a/actionpack/lib/action_controller/caching/pages.rb +++ b/actionpack/lib/action_controller/caching/pages.rb @@ -41,7 +41,7 @@ module Pages ## # :singleton-method: # The cache directory should be the document root for the web server and is set using Base.page_cache_directory = "/document/root". - # For Rails, this directory has already been set to Rails.public_path (which is usually set to RAILS_ROOT + "/public"). Changing + # For Rails, this directory has already been set to Rails.public_path (which is usually set to Rails.root + "/public"). Changing # this setting can be useful to avoid naming conflicts with files in public/, but doing so will likely require configuring your # web server to look in the new location for cached files. @@page_cache_directory = '' diff --git a/railties/guides/source/3_0_release_notes.textile b/railties/guides/source/3_0_release_notes.textile index 024cb482882ac..da69ada7b4ba4 100644 --- a/railties/guides/source/3_0_release_notes.textile +++ b/railties/guides/source/3_0_release_notes.textile @@ -183,7 +183,7 @@ Railties generators got a huge amount of attention in Rails 3.0, basically: * Rails templates API and generators API were merged (they are the same as the former). * Generators are no longer loaded from special paths anymore, they are just found in the Ruby load path, so calling rails generate foo will look for generators/foo_generator. * New generators provide hooks, so any template engine, ORM, test framework can easily hook in. -* New generators allow you to override the templates by placing a copy at RAILS_ROOT/lib/templates. +* New generators allow you to override the templates by placing a copy at Rails.root/lib/templates. * Rails::Generators::TestCase is also supplied so you can create your own generators and test them. Also, the views generated by Railties generators had some overhaul: diff --git a/railties/guides/source/command_line.textile b/railties/guides/source/command_line.textile index f2b53023a5e90..ebae320ebce7d 100644 --- a/railties/guides/source/command_line.textile +++ b/railties/guides/source/command_line.textile @@ -530,7 +530,7 @@ You can get a list of Rake tasks available to you, which will often depend on yo rake db:abort_if_pending_migrations # Raises an error if there are pending migrations rake db:charset # Retrieves the charset for the current environment's database rake db:collation # Retrieves the collation for the current environment's database -rake db:create # Create the database defined in config/database.yml for the current RAILS_ENV +rake db:create # Create the database defined in config/database.yml for the current Rails.env ... ... rake tmp:pids:clear # Clears all files in tmp/pids diff --git a/railties/guides/source/configuring.textile b/railties/guides/source/configuring.textile index 03d2519ee7ec7..bd2289890ab12 100644 --- a/railties/guides/source/configuring.textile +++ b/railties/guides/source/configuring.textile @@ -163,7 +163,7 @@ WARNING: Threadsafe operation in incompatible with the normal workings of develo The caching code adds two additional settings: -* +ActionController::Base.page_cache_directory+ sets the directory where Rails will create cached pages for your web server. The default is +Rails.public_path+ (which is usually set to +RAILS_ROOT + "/public"+). +* +ActionController::Base.page_cache_directory+ sets the directory where Rails will create cached pages for your web server. The default is +Rails.public_path+ (which is usually set to +Rails.root + "/public"+). * +ActionController::Base.page_cache_extension+ sets the extension to be used when generating pages for the cache (this is ignored if the incoming request already has an extension). The default is +.html+. diff --git a/railties/guides/source/debugging_rails_applications.textile b/railties/guides/source/debugging_rails_applications.textile index 8f502bac997b3..0fb7542995d1d 100644 --- a/railties/guides/source/debugging_rails_applications.textile +++ b/railties/guides/source/debugging_rails_applications.textile @@ -136,7 +136,7 @@ config.logger = Logger.new(STDOUT) config.logger = Log4r::Logger.new("Application Log") -TIP: By default, each log is created under +RAILS_ROOT/log/+ and the log file name is +environment_name.log+. +TIP: By default, each log is created under +Rails.root/log/+ and the log file name is +environment_name.log+. h4. Log Levels diff --git a/railties/guides/source/i18n.textile b/railties/guides/source/i18n.textile index ec69f770ee7ee..9e882bc0a19e2 100644 --- a/railties/guides/source/i18n.textile +++ b/railties/guides/source/i18n.textile @@ -103,7 +103,7 @@ The default +environment.rb+ files has instructions on how to add locales from a # The internationalization framework can be changed # to have another default locale (standard is :en) or more load paths. # All files from config/locales/*.rb,yml are added automatically. -# config.i18n.load_path << Dir[File.join(RAILS_ROOT, 'my', 'locales', '*.{rb,yml}')] +# config.i18n.load_path << Dir[File.join(Rails.root, 'my', 'locales', '*.{rb,yml}')] # config.i18n.default_locale = :de @@ -117,7 +117,7 @@ To tell the I18n library where it can find your custom translation files you can # in config/initializers/locale.rb # tell the I18n library where to find your translations -I18n.load_path << Dir[ File.join(RAILS_ROOT, 'lib', 'locale', +I18n.load_path << Dir[ File.join(Rails.root, 'lib', 'locale', '*.{rb,yml}') ] # set default locale to something other than :en @@ -423,7 +423,7 @@ NOTE: The default locale loading mechanism in Rails does not load locale files i # config/environment.rb - config.i18n.load_path += Dir[File.join(RAILS_ROOT, 'config', 'locales', '**', '*.{rb,yml}')] + config.i18n.load_path += Dir[File.join(Rails.root, 'config', 'locales', '**', '*.{rb,yml}')] Do check the "Rails i18n Wiki":http://rails-i18n.org/wiki for list of tools available for managing translations. diff --git a/railties/guides/source/migrations.textile b/railties/guides/source/migrations.textile index 558cbb47713f1..6f88ed6b3fc28 100644 --- a/railties/guides/source/migrations.textile +++ b/railties/guides/source/migrations.textile @@ -568,7 +568,7 @@ In many ways this is exactly what it is. This file is created by inspecting the 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 that database (via the +db:structure:dump+ Rake task) into +db/#{RAILS_ENV}_structure.sql+. For example for PostgreSQL the +pg_dump+ utility is used and for MySQL this file will contain the output of +SHOW CREATE TABLE+ for the various tables. Loading this schema is simply a question of executing the SQL statements contained inside. +Instead of using Active Record's schema dumper the database's structure will be dumped using a tool specific to that database (via the +db:structure:dump+ Rake task) into +db/#{Rails.env}_structure.sql+. For example for PostgreSQL the +pg_dump+ utility is used and for MySQL this file will contain the output of +SHOW CREATE TABLE+ for the various tables. Loading this schema is simply a question of executing the SQL statements contained inside. By definition this will be a perfect copy of the database's structure but this will usually prevent loading the schema into a database other than the one used to create it. diff --git a/railties/guides/source/rails_application_templates.textile b/railties/guides/source/rails_application_templates.textile index 579b1a553832d..baaa3d6d6605b 100644 --- a/railties/guides/source/rails_application_templates.textile +++ b/railties/guides/source/rails_application_templates.textile @@ -113,7 +113,7 @@ CODE Similarly +lib()+ creates a file in the +lib/+ directory and +vendor()+ creates a file in the +vendor/+ directory. -There is even +file()+, which accepts a relative path from +RAILS_ROOT+ and creates all the directories/file needed : +There is even +file()+, which accepts a relative path from +Rails.root+ and creates all the directories/file needed : file 'app/components/foo.rb', <<-CODE diff --git a/railties/guides/source/rails_on_rack.textile b/railties/guides/source/rails_on_rack.textile index 320ce137bbc13..d0d86e99f240f 100644 --- a/railties/guides/source/rails_on_rack.textile +++ b/railties/guides/source/rails_on_rack.textile @@ -49,7 +49,7 @@ Middlewares used in the code above are primarily useful only in the development |_.Middleware|_.Purpose| |+Rails::Rack::LogTailer+|Appends log file output to console| -|+ActionDispatch::Static+|Serves static files inside +RAILS_ROOT/public+ directory| +|+ActionDispatch::Static+|Serves static files inside +Rails.root/public+ directory| |+Rails::Rack::Debugger+|Starts Debugger| h4. +rackup+ @@ -57,7 +57,7 @@ h4. +rackup+ To use +rackup+ instead of Rails' +rails server+, you can put the following inside +config.ru+ of your Rails application's root directory: -# RAILS_ROOT/config.ru +# Rails.root/config.ru require "config/environment" use Rails::Rack::LogTailer @@ -214,7 +214,7 @@ config.middleware.clear
-Add a +config.ru+ file to +RAILS_ROOT+ +Add a +config.ru+ file to +Rails.root+ # config.ru diff --git a/railties/lib/rails/application/configuration.rb b/railties/lib/rails/application/configuration.rb index 7ce3494fa675f..11bf6a6e726df 100644 --- a/railties/lib/rails/application/configuration.rb +++ b/railties/lib/rails/application/configuration.rb @@ -53,7 +53,7 @@ def paths paths.vendor.plugins "vendor/plugins" if File.exists?("#{root}/test/mocks/#{Rails.env}") - ActiveSupport::Deprecation.warn "\"RAILS_ROOT/test/mocks/#{Rails.env}\" won't be added " << + ActiveSupport::Deprecation.warn "\"Rails.root/test/mocks/#{Rails.env}\" won't be added " << "automatically to load paths anymore in future releases" paths.mocks_path "test/mocks", :load_path => true, :glob => Rails.env end diff --git a/railties/lib/rails/webrick_server.rb b/railties/lib/rails/webrick_server.rb index 2f60151b22275..f3b74c28d30fc 100644 --- a/railties/lib/rails/webrick_server.rb +++ b/railties/lib/rails/webrick_server.rb @@ -63,8 +63,8 @@ def self.dispatch(options = {}) def initialize(server, options) #:nodoc: @server_options = options @file_handler = WEBrick::HTTPServlet::FileHandler.new(server, options[:server_root]) - # Change to the RAILS_ROOT, since Webrick::Daemon.start does a Dir::cwd("/") - # OPTIONS['working_directory'] is an absolute path of the RAILS_ROOT, set in railties/lib/commands/servers/webrick.rb + # Change to the Rails.root, since Webrick::Daemon.start does a Dir::cwd("/") + # OPTIONS['working_directory'] is an absolute path of the Rails.root, set in railties/lib/commands/servers/webrick.rb Dir.chdir(OPTIONS['working_directory']) if defined?(OPTIONS) && File.directory?(OPTIONS['working_directory']) super end From 3f0097c7157e4a328f87cdf80ab6330c39b6d90f Mon Sep 17 00:00:00 2001 From: Anil Wadghule Date: Tue, 13 Apr 2010 00:56:34 +0530 Subject: [PATCH 19/22] Updated guide to use 'Rails.root.join' to construct path --- railties/guides/source/i18n.textile | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/railties/guides/source/i18n.textile b/railties/guides/source/i18n.textile index 9e882bc0a19e2..cfaa573fa0cc5 100644 --- a/railties/guides/source/i18n.textile +++ b/railties/guides/source/i18n.textile @@ -103,7 +103,7 @@ The default +environment.rb+ files has instructions on how to add locales from a # The internationalization framework can be changed # to have another default locale (standard is :en) or more load paths. # All files from config/locales/*.rb,yml are added automatically. -# config.i18n.load_path << Dir[File.join(Rails.root, 'my', 'locales', '*.{rb,yml}')] +# config.i18n.load_path += Dir[Rails.root.join('my', 'locales', '*.{rb,yml}')] # config.i18n.default_locale = :de @@ -117,8 +117,7 @@ To tell the I18n library where it can find your custom translation files you can # in config/initializers/locale.rb # tell the I18n library where to find your translations -I18n.load_path << Dir[ File.join(Rails.root, 'lib', 'locale', - '*.{rb,yml}') ] +I18n.load_path << Dir[Rails.root.join('lib', 'locale', '*.{rb,yml}')] # set default locale to something other than :en I18n.default_locale = :pt @@ -423,7 +422,8 @@ NOTE: The default locale loading mechanism in Rails does not load locale files i # config/environment.rb - config.i18n.load_path += Dir[File.join(Rails.root, 'config', 'locales', '**', '*.{rb,yml}')] + config.i18n.load_path += Dir[Rails.root.join('config', 'locales', '**', '*.{rb,yml}')] + Do check the "Rails i18n Wiki":http://rails-i18n.org/wiki for list of tools available for managing translations. From fe0b52befb99e247c5cb98aceaa660dce34cfc47 Mon Sep 17 00:00:00 2001 From: Anil Wadghule Date: Tue, 13 Apr 2010 12:25:44 +0530 Subject: [PATCH 20/22] Changes in guide as per Rails 3 features --- railties/guides/source/i18n.textile | 30 ++++++++++++++--------------- 1 file changed, 15 insertions(+), 15 deletions(-) diff --git a/railties/guides/source/i18n.textile b/railties/guides/source/i18n.textile index cfaa573fa0cc5..01e3380ee45d4 100644 --- a/railties/guides/source/i18n.textile +++ b/railties/guides/source/i18n.textile @@ -97,19 +97,17 @@ The *translations load path* (+I18n.load_path+) is just a Ruby Array of paths to NOTE: The backend will lazy-load these translations when a translation is looked up for the first time. This makes it possible to just swap the backend with something else even after translations have already been announced. -The default +environment.rb+ files has instructions on how to add locales from another directory and how to set a different default locale. Just uncomment and edit the specific lines. +The default +application.rb+ files has instructions on how to add locales from another directory and how to set a different default locale. Just uncomment and edit the specific lines. -# The internationalization framework can be changed -# to have another default locale (standard is :en) or more load paths. -# All files from config/locales/*.rb,yml are added automatically. -# config.i18n.load_path += Dir[Rails.root.join('my', 'locales', '*.{rb,yml}')] +# The default locale is :en and all translations from config/locales/*.rb,yml are auto loaded. +# config.i18n.load_path += Dir[Rails.root.join('my', 'locales', '*.{rb,yml}').to_s] # config.i18n.default_locale = :de h4. Optional: Custom I18n Configuration Setup -For the sake of completeness, let's mention that if you do not want to use the +environment.rb+ file for some reason, you can always wire up things manually, too. +For the sake of completeness, let's mention that if you do not want to use the +application.rb+ file for some reason, you can always wire up things manually, too. To tell the I18n library where it can find your custom translation files you can specify the load path anywhere in your application - just make sure it gets run before any translations are actually looked up. You might also want to change the default locale. The simplest thing possible is to put the following into an initializer: @@ -117,7 +115,7 @@ To tell the I18n library where it can find your custom translation files you can # in config/initializers/locale.rb # tell the I18n library where to find your translations -I18n.load_path << Dir[Rails.root.join('lib', 'locale', '*.{rb,yml}')] +I18n.load_path += Dir[Rails.root.join('lib', 'locale', '*.{rb,yml}')] # set default locale to something other than :en I18n.default_locale = :pt @@ -125,7 +123,7 @@ I18n.default_locale = :pt h4. Setting and Passing the Locale -If you want to translate your Rails application to a *single language other than English* (the default locale), you can set I18n.default_locale to your locale in +environment.rb+ or an initializer as shown above, and it will persist through the requests. +If you want to translate your Rails application to a *single language other than English* (the default locale), you can set I18n.default_locale to your locale in +application.rb+ or an initializer as shown above, and it will persist through the requests. However, you would probably like to *provide support for more locales* in your application. In such case, you need to set and pass the locale between requests. @@ -226,21 +224,23 @@ You probably want URLs to look like this: +www.example.com/en/books+ (which load # config/routes.rb -map.resources :books, :path_prefix => '/:locale' +scope "/:locale" do + resources :books +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). -Of course, you need to take special care of the root URL (usually "homepage" or "dashboard") of your application. An URL like +http://localhost:3001/nl+ will not work automatically, because the +map.root :controller => "dashboard"+ declaration in your +routes.rb+ doesn't take locale into account. (And rightly so: there's only one "root" URL.) +Of course, you need to take special care of the root URL (usually "homepage" or "dashboard") of your application. An URL like +http://localhost:3001/nl+ will not work automatically, because the +root :to => "books#index"+ declaration in your +routes.rb+ doesn't take locale into account. (And rightly so: there's only one "root" URL.) You would probably need to map URLs like these: # config/routes.rb -map.dashboard '/:locale', :controller => "dashboard" +match '/:locale' => 'dashboard#index' -Do take special care about the *order of your routes*, so this route declaration does not "eat" other ones. (You may want to add it directly before the +map.root+ declaration.) +Do take special care about the *order of your routes*, so this route declaration does not "eat" other ones. (You may want to add it directly before the +root :to+ declaration.) IMPORTANT: This solution has currently one rather big *downside*. Due to the _default_url_options_ implementation, you have to pass the +:id+ option explicitly, like this: +link_to 'Show', book_url(:id => book)+ and not depend on Rails' magic in code like +link_to 'Show', book+. If this should be a problem, have a look at two plugins which simplify work with routes in this way: Sven Fuchs's "routing_filter":http://github.com/svenfuchs/routing-filter/tree/master and Raul Murciano's "translate_routes":http://github.com/raul/translate_routes/tree/master. See also the page "How to encode the current locale in the URL":http://rails-i18n.org/wiki/wikipages/how-to-encode-the-current-locale-in-the-url in the Rails i18n Wiki. @@ -287,8 +287,8 @@ You most probably have something like this in one of your applications: # config/routes.rb -ActionController::Routing::Routes.draw do |map| - map.root :controller => 'home', :action => 'index' +Yourapp::Application.routes.draw do |map| + root :to => "home#index" end # app/controllers/home_controller.rb @@ -421,7 +421,7 @@ This way, you can separate model and model attribute names from text inside view NOTE: The default locale loading mechanism in Rails does not load locale files in nested dictionaries, like we have here. So, for this to work, we must explicitly tell Rails to look further: - # config/environment.rb + # config/application.rb config.i18n.load_path += Dir[Rails.root.join('config', 'locales', '**', '*.{rb,yml}')] From d45cacc8370776b9b9609fce1d287f68ba6b2e16 Mon Sep 17 00:00:00 2001 From: Ryan Bigg Date: Sun, 11 Apr 2010 07:43:59 +1000 Subject: [PATCH 21/22] Use instead of --- railties/guides/source/initialization.textile | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-) diff --git a/railties/guides/source/initialization.textile b/railties/guides/source/initialization.textile index d8d119f6087e2..fea0185c4c395 100644 --- a/railties/guides/source/initialization.textile +++ b/railties/guides/source/initialization.textile @@ -844,7 +844,7 @@ The ActiveRecord Railtie takes care of hooking ActiveRecord into Rails. This dep TODO: Quotify. - + Active Record connects business objects and database tables to create a persistable domain model where logic and data are presented in one wrapping. It's an implementation of the object-relational mapping (ORM) pattern by the same name as described by Martin Fowler: "An object that wraps a row in a database table or view, encapsulates @@ -854,7 +854,7 @@ TODO: Quotify. lack of associations and inheritance. By adding a simple domain language-like set of macros to describe the former and integrating the Single Table Inheritance pattern for the latter, Active Record narrows the gap of functionality between the data mapper and active record approach. - + h5. +require "active_record/railtie"+ @@ -989,13 +989,13 @@ This Railtie is +require+'d by ActiveRecord's Railtie. From the ActiveModel readme: - + Prior to Rails 3.0, if a plugin or gem developer wanted to be able to have an object interact with Action Pack helpers, it was required to either copy chunks of code from Rails, or monkey patch entire helpers to make them handle objects that did not look like Active Record. This generated code duplication and fragile applications that broke on upgrades. Active Model is a solution for this problem. Active Model provides a known set of interfaces that your objects can implement to then present a common interface to the Action Pack helpers. - + h5. +require "active_model/railtie"+ @@ -1249,9 +1249,9 @@ In _encoding.rb_ it's used to define a constant that's now been deprecated: Now when you reference +ActiveSupport::JSON::CircularReferenceError+ you'll receive a warning: - + ActiveSupport::JSON::CircularReferenceError is deprecated! Use Encoding::CircularReferenceError instead. - + h5. +require "active_support/deprecation"+ @@ -2268,6 +2268,12 @@ The first method to be called here is +autorequires_for_groups+: end +The +specs_for+ method here: + + + + + h3. Firing it up! From e090898c5e98e853828208343b3911a229563b62 Mon Sep 17 00:00:00 2001 From: Diego Carrion Date: Tue, 13 Apr 2010 18:23:41 -0300 Subject: [PATCH 22/22] fixed typo in RUNNING_UNIT_TESTS --- activerecord/RUNNING_UNIT_TESTS | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/activerecord/RUNNING_UNIT_TESTS b/activerecord/RUNNING_UNIT_TESTS index 39fc86759fa5b..8559d72647f2b 100644 --- a/activerecord/RUNNING_UNIT_TESTS +++ b/activerecord/RUNNING_UNIT_TESTS @@ -14,7 +14,7 @@ connection.rb otherwise (on Postgres, at least) tests for default values will fa The easiest way to run the unit tests is through Rake. The default task runs the entire test suite for all the adapters. You can also run the suite on just -one adapter by using the tasks test_mysql, test_sqlite, test_postgresql or any +one adapter by using the tasks test_mysql, test_sqlite3, test_postgresql or any of the other test_ tasks. For more information, checkout the full array of rake tasks with "rake -T"