mirror of
https://github.com/rails/rails.git
synced 2022-11-09 12:12:34 -05:00
Merge commit 'mainstream/master'
This commit is contained in:
commit
63e8bcaeb3
12 changed files with 111 additions and 20 deletions
|
@ -524,11 +524,9 @@ module ActionController
|
|||
resource.member_methods.each do |method, actions|
|
||||
actions.each do |action|
|
||||
action_options = action_options_for(action, resource, method)
|
||||
action_path = action
|
||||
if resource.options[:path_names]
|
||||
action_path = resource.options[:path_names][action]
|
||||
action_path ||= Base.resources_path_names[action] || action
|
||||
end
|
||||
|
||||
action_path = resource.options[:path_names][action] if resource.options[:path_names].is_a?(Hash)
|
||||
action_path ||= Base.resources_path_names[action] || action
|
||||
|
||||
map.named_route("#{action}_#{resource.name_prefix}#{resource.singular}", "#{resource.member_path}#{resource.action_separator}#{action_path}", action_options)
|
||||
map.named_route("formatted_#{action}_#{resource.name_prefix}#{resource.singular}", "#{resource.member_path}#{resource.action_separator}#{action_path}.:format",action_options)
|
||||
|
|
|
@ -185,7 +185,7 @@ module ActionView #:nodoc:
|
|||
attr_internal :request
|
||||
|
||||
delegate :request_forgery_protection_token, :template, :params, :session, :cookies, :response, :headers,
|
||||
:flash, :logger, :to => :controller
|
||||
:flash, :logger, :action_name, :to => :controller
|
||||
|
||||
module CompiledTemplates #:nodoc:
|
||||
# holds compiled template code
|
||||
|
|
|
@ -246,6 +246,10 @@ class NewRenderTestController < ActionController::Base
|
|||
def accessing_logger_in_template
|
||||
render :inline => "<%= logger.class %>"
|
||||
end
|
||||
|
||||
def accessing_action_name_in_template
|
||||
render :inline => "<%= action_name %>"
|
||||
end
|
||||
|
||||
def accessing_params_in_template_with_layout
|
||||
render :layout => nil, :inline => "Hello: <%= params[:name] %>"
|
||||
|
@ -545,6 +549,11 @@ class NewRenderTest < Test::Unit::TestCase
|
|||
get :accessing_logger_in_template
|
||||
assert_equal "Logger", @response.body
|
||||
end
|
||||
|
||||
def test_access_to_action_name_in_view
|
||||
get :accessing_action_name_in_template
|
||||
assert_equal "accessing_action_name_in_template", @response.body
|
||||
end
|
||||
|
||||
def test_render_xml
|
||||
get :render_xml_hello
|
||||
|
|
|
@ -226,6 +226,28 @@ class ResourcesTest < Test::Unit::TestCase
|
|||
end
|
||||
end
|
||||
|
||||
def test_member_when_changed_default_restful_actions_and_path_names_not_specified
|
||||
default_path_names = ActionController::Base.resources_path_names
|
||||
ActionController::Base.resources_path_names = {:new => 'nuevo', :edit => 'editar'}
|
||||
|
||||
with_restful_routing :messages do
|
||||
new_options = { :action => 'new', :controller => 'messages' }
|
||||
new_path = "/messages/nuevo"
|
||||
edit_options = { :action => 'edit', :id => '1', :controller => 'messages' }
|
||||
edit_path = "/messages/1/editar"
|
||||
|
||||
assert_restful_routes_for :messages do |options|
|
||||
assert_recognizes(options.merge(new_options), :path => new_path, :method => :get)
|
||||
end
|
||||
|
||||
assert_restful_routes_for :messages do |options|
|
||||
assert_recognizes(options.merge(edit_options), :path => edit_path, :method => :get)
|
||||
end
|
||||
end
|
||||
ensure
|
||||
ActionController::Base.resources_path_names = default_path_names
|
||||
end
|
||||
|
||||
def test_with_two_member_actions_with_same_method
|
||||
[:put, :post].each do |method|
|
||||
with_restful_routing :messages, :member => { :mark => method, :unmark => method } do
|
||||
|
@ -691,11 +713,11 @@ class ResourcesTest < Test::Unit::TestCase
|
|||
options[:options] ||= {}
|
||||
options[:options][:controller] = options[:controller] || controller_name.to_s
|
||||
|
||||
new_action = "new"
|
||||
edit_action = "edit"
|
||||
new_action = ActionController::Base.resources_path_names[:new] || "new"
|
||||
edit_action = ActionController::Base.resources_path_names[:edit] || "edit"
|
||||
if options[:path_names]
|
||||
new_action = options[:path_names][:new] || "new"
|
||||
edit_action = options[:path_names][:edit] || "edit"
|
||||
new_action = options[:path_names][:new] if options[:path_names][:new]
|
||||
edit_action = options[:path_names][:edit] if options[:path_names][:edit]
|
||||
end
|
||||
|
||||
collection_path = "/#{options[:path_prefix]}#{options[:as] || controller_name}"
|
||||
|
|
|
@ -65,7 +65,13 @@ module ActiveRecord
|
|||
end
|
||||
|
||||
def set_association_single_records(id_to_record_map, reflection_name, associated_records, key)
|
||||
seen_keys = {}
|
||||
associated_records.each do |associated_record|
|
||||
#this is a has_one or belongs_to: there should only be one record.
|
||||
#Unfortunately we can't (in portable way) ask the database for 'all records where foo_id in (x,y,z), but please
|
||||
# only one row per distinct foo_id' so this where we enforce that
|
||||
next if seen_keys[associated_record[key].to_s]
|
||||
seen_keys[associated_record[key].to_s] = true
|
||||
mapped_records = id_to_record_map[associated_record[key].to_s]
|
||||
mapped_records.each do |mapped_record|
|
||||
mapped_record.send("set_#{reflection_name}_target", associated_record)
|
||||
|
@ -122,7 +128,6 @@ module ActiveRecord
|
|||
else
|
||||
records.each {|record| record.send("set_#{reflection.name}_target", nil)}
|
||||
|
||||
|
||||
set_association_single_records(id_to_record_map, reflection.name, find_associated_records(ids, reflection, preload_options), reflection.primary_key_name)
|
||||
end
|
||||
end
|
||||
|
|
25
activerecord/lib/active_record/associations.rb
Executable file → Normal file
25
activerecord/lib/active_record/associations.rb
Executable file → Normal file
|
@ -1446,6 +1446,12 @@ module ActiveRecord
|
|||
tables_from_conditions = conditions_tables(options)
|
||||
tables_from_order = order_tables(options)
|
||||
all_tables = tables_from_conditions + tables_from_order
|
||||
distinct_join_associations = all_tables.uniq.map{|table|
|
||||
join_dependency.joins_for_table_name(table)
|
||||
}.flatten.compact.uniq
|
||||
|
||||
|
||||
|
||||
|
||||
is_distinct = !options[:joins].blank? || include_eager_conditions?(options, tables_from_conditions) || include_eager_order?(options, tables_from_order)
|
||||
sql = "SELECT "
|
||||
|
@ -1457,7 +1463,7 @@ module ActiveRecord
|
|||
sql << " FROM #{connection.quote_table_name table_name} "
|
||||
|
||||
if is_distinct
|
||||
sql << join_dependency.join_associations.reject{ |ja| !all_tables.include?(ja.table_name) }.collect(&:association_join).join
|
||||
sql << distinct_join_associations.collect(&:association_join).join
|
||||
add_joins!(sql, options, scope)
|
||||
end
|
||||
|
||||
|
@ -1617,6 +1623,23 @@ module ActiveRecord
|
|||
end
|
||||
end
|
||||
|
||||
def join_for_table_name(table_name)
|
||||
@joins.select{|j|j.aliased_table_name == table_name.gsub(/^\"(.*)\"$/){$1} }.first rescue nil
|
||||
end
|
||||
|
||||
def joins_for_table_name(table_name)
|
||||
join = join_for_table_name(table_name)
|
||||
result = nil
|
||||
if join && join.is_a?(JoinAssociation)
|
||||
result = [join]
|
||||
if join.parent && join.parent.is_a?(JoinAssociation)
|
||||
result = joins_for_table_name(join.parent.aliased_table_name) +
|
||||
result
|
||||
end
|
||||
end
|
||||
result
|
||||
end
|
||||
|
||||
protected
|
||||
def build(associations, parent = nil)
|
||||
parent ||= @joins.last
|
||||
|
|
|
@ -29,6 +29,10 @@ class EagerAssociationTest < ActiveRecord::TestCase
|
|||
post = Post.find(:first, :include => :comments, :conditions => "posts.title = 'Welcome to the weblog'")
|
||||
assert_equal 2, post.comments.size
|
||||
assert post.comments.include?(comments(:greetings))
|
||||
|
||||
posts = Post.find(:all, :include => :last_comment)
|
||||
post = posts.find { |p| p.id == 1 }
|
||||
assert_equal Post.find(1).last_comment, post.last_comment
|
||||
end
|
||||
|
||||
def test_loading_conditions_with_or
|
||||
|
|
|
@ -8,6 +8,7 @@ require 'models/entrant'
|
|||
require 'models/developer'
|
||||
require 'models/post'
|
||||
require 'models/customer'
|
||||
require 'models/job'
|
||||
|
||||
class FinderTest < ActiveRecord::TestCase
|
||||
fixtures :companies, :topics, :entrants, :developers, :developers_projects, :posts, :comments, :accounts, :authors, :customers
|
||||
|
@ -857,6 +858,14 @@ class FinderTest < ActiveRecord::TestCase
|
|||
Company.connection.select_rows("SELECT id, name FROM companies WHERE id IN (1,2,3) ORDER BY id").map! {|i| i.map! {|j| j.to_s unless j.nil?}}
|
||||
end
|
||||
|
||||
def test_find_with_order_on_included_associations_with_construct_finder_sql_for_association_limiting_and_is_distinct
|
||||
assert_equal 2, Post.find(:all,:include=>{:authors=>:author_address},:order=>' author_addresses.id DESC ', :limit=>2).size
|
||||
|
||||
assert_equal 3, Post.find(:all,:include=>{:author=>:author_address,:authors=>:author_address},
|
||||
:order=>' author_addresses_authors.id DESC ', :limit=>3).size
|
||||
end
|
||||
|
||||
|
||||
protected
|
||||
def bind(statement, *vars)
|
||||
if vars.first.is_a?(Hash)
|
||||
|
|
|
@ -9,6 +9,8 @@ class Post < ActiveRecord::Base
|
|||
|
||||
belongs_to :author_with_posts, :class_name => "Author", :foreign_key => :author_id, :include => :posts
|
||||
|
||||
has_one :last_comment, :class_name => 'Comment', :order => 'id desc'
|
||||
|
||||
has_many :comments, :order => "body" do
|
||||
def find_most_recent
|
||||
find(:first, :order => "id DESC")
|
||||
|
|
|
@ -175,6 +175,20 @@ module ActiveSupport
|
|||
ActiveSupport::Deprecation.warn("#{@var} is deprecated! Call #{@method}.#{called} instead of #{@var}.#{called}. Args: #{args.inspect}", callstack)
|
||||
end
|
||||
end
|
||||
|
||||
class DeprecatedInstanceVariable < Delegator #:nodoc:
|
||||
def initialize(value, method)
|
||||
super(value)
|
||||
@method = method
|
||||
@value = value
|
||||
end
|
||||
|
||||
def __getobj__
|
||||
ActiveSupport::Deprecation.warn("Instance variable @#{@method} is deprecated! Call instance method #{@method} instead.")
|
||||
@value
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
|
||||
|
|
|
@ -149,3 +149,13 @@ class DeprecationTest < Test::Unit::TestCase
|
|||
assert_nil @last_message
|
||||
end
|
||||
end
|
||||
|
||||
class DeprecatedIvarTest < Test::Unit::TestCase
|
||||
|
||||
def test_deprecated_ivar
|
||||
@action = ActiveSupport::Deprecation::DeprecatedInstanceVariable.new("fubar", :foobar)
|
||||
|
||||
assert_deprecated(/Instance variable @foobar is deprecated! Call instance method foobar instead/) { assert_equal "fubar", @action }
|
||||
end
|
||||
|
||||
end
|
||||
|
|
|
@ -46,7 +46,7 @@ namespace :db do
|
|||
@encoding = config[:encoding] || ENV['CHARSET'] || 'utf8'
|
||||
begin
|
||||
ActiveRecord::Base.establish_connection(config.merge('database' => 'template1'))
|
||||
ActiveRecord::Base.connection.create_database(config['database'], :encoding => @encoding)
|
||||
ActiveRecord::Base.connection.create_database(config['database'], config.merge('encoding' => @encoding))
|
||||
ActiveRecord::Base.establish_connection(config)
|
||||
rescue
|
||||
$stderr.puts $!, *($!.backtrace)
|
||||
|
@ -314,14 +314,9 @@ namespace :db do
|
|||
ActiveRecord::Base.establish_connection(:test)
|
||||
ActiveRecord::Base.connection.recreate_database(abcs["test"]["database"])
|
||||
when "postgresql"
|
||||
ENV['PGHOST'] = abcs["test"]["host"] if abcs["test"]["host"]
|
||||
ENV['PGPORT'] = abcs["test"]["port"].to_s if abcs["test"]["port"]
|
||||
ENV['PGPASSWORD'] = abcs["test"]["password"].to_s if abcs["test"]["password"]
|
||||
enc_option = "-E #{abcs["test"]["encoding"]}" if abcs["test"]["encoding"]
|
||||
|
||||
ActiveRecord::Base.clear_active_connections!
|
||||
`dropdb -U "#{abcs["test"]["username"]}" #{abcs["test"]["database"]}`
|
||||
`createdb #{enc_option} -U "#{abcs["test"]["username"]}" #{abcs["test"]["database"]}`
|
||||
drop_database(abcs['test'])
|
||||
create_database(abcs['test'])
|
||||
when "sqlite","sqlite3"
|
||||
dbfile = abcs["test"]["database"] || abcs["test"]["dbfile"]
|
||||
File.delete(dbfile) if File.exist?(dbfile)
|
||||
|
|
Loading…
Reference in a new issue