mirror of
https://github.com/github/rails.git
synced 2026-04-26 03:00:59 -04:00
merge forward to current rails/master
This commit is contained in:
@@ -65,6 +65,12 @@ class AdapterTest < ActiveRecord::TestCase
|
||||
end
|
||||
end
|
||||
|
||||
if current_adapter?(:PostgreSQLAdapter)
|
||||
def test_encoding
|
||||
assert_not_nil @connection.encoding
|
||||
end
|
||||
end
|
||||
|
||||
def test_table_alias
|
||||
def @connection.test_table_alias_length() 10; end
|
||||
class << @connection
|
||||
|
||||
@@ -681,4 +681,10 @@ class HasAndBelongsToManyAssociationsTest < ActiveRecord::TestCase
|
||||
assert_equal developer, project.developers.find(:first)
|
||||
assert_equal project, developer.projects.find(:first)
|
||||
end
|
||||
|
||||
def test_dynamic_find_should_respect_association_include
|
||||
# SQL error in sort clause if :include is not included
|
||||
# due to Unknown column 'authors.id'
|
||||
assert Category.find(1).posts_with_authors_sorted_by_author_id.find_by_title('Welcome to the weblog')
|
||||
end
|
||||
end
|
||||
|
||||
@@ -129,6 +129,10 @@ class HasManyAssociationsTest < ActiveRecord::TestCase
|
||||
assert_equal "Microsoft", Firm.find(:first).clients_like_ms_with_hash_conditions.first.name
|
||||
end
|
||||
|
||||
def test_finding_using_primary_key
|
||||
assert_equal "Summit", Firm.find(:first).clients_using_primary_key.first.name
|
||||
end
|
||||
|
||||
def test_finding_using_sql
|
||||
firm = Firm.find(:first)
|
||||
first_client = firm.clients_using_sql.first
|
||||
@@ -345,7 +349,7 @@ class HasManyAssociationsTest < ActiveRecord::TestCase
|
||||
def test_invalid_adding_with_validate_false
|
||||
firm = Firm.find(:first)
|
||||
client = Client.new
|
||||
firm.unvalidated_clients_of_firm << Client.new
|
||||
firm.unvalidated_clients_of_firm << client
|
||||
|
||||
assert firm.valid?
|
||||
assert !client.valid?
|
||||
@@ -353,6 +357,23 @@ class HasManyAssociationsTest < ActiveRecord::TestCase
|
||||
assert client.new_record?
|
||||
end
|
||||
|
||||
def test_valid_adding_with_validate_false
|
||||
no_of_clients = Client.count
|
||||
|
||||
firm = Firm.find(:first)
|
||||
client = Client.new("name" => "Apple")
|
||||
|
||||
assert firm.valid?
|
||||
assert client.valid?
|
||||
assert client.new_record?
|
||||
|
||||
firm.unvalidated_clients_of_firm << client
|
||||
|
||||
assert firm.save
|
||||
assert !client.new_record?
|
||||
assert_equal no_of_clients+1, Client.count
|
||||
end
|
||||
|
||||
def test_build
|
||||
company = companies(:first_firm)
|
||||
new_client = assert_no_queries { company.clients_of_firm.build("name" => "Another Client") }
|
||||
@@ -367,6 +388,13 @@ class HasManyAssociationsTest < ActiveRecord::TestCase
|
||||
assert_equal 2, company.clients_of_firm(true).size
|
||||
end
|
||||
|
||||
def test_collection_size_after_building
|
||||
company = companies(:first_firm) # company already has one client
|
||||
company.clients_of_firm.build("name" => "Another Client")
|
||||
company.clients_of_firm.build("name" => "Yet Another Client")
|
||||
assert_equal 3, company.clients_of_firm.size
|
||||
end
|
||||
|
||||
def test_build_many
|
||||
company = companies(:first_firm)
|
||||
new_clients = assert_no_queries { company.clients_of_firm.build([{"name" => "Another Client"}, {"name" => "Another Client II"}]) }
|
||||
@@ -397,6 +425,37 @@ class HasManyAssociationsTest < ActiveRecord::TestCase
|
||||
assert_equal 2, first_topic.replies.to_ary.size
|
||||
end
|
||||
|
||||
def test_build_via_block
|
||||
company = companies(:first_firm)
|
||||
new_client = assert_no_queries { company.clients_of_firm.build {|client| client.name = "Another Client" } }
|
||||
assert !company.clients_of_firm.loaded?
|
||||
|
||||
assert_equal "Another Client", new_client.name
|
||||
assert new_client.new_record?
|
||||
assert_equal new_client, company.clients_of_firm.last
|
||||
company.name += '-changed'
|
||||
assert_queries(2) { assert company.save }
|
||||
assert !new_client.new_record?
|
||||
assert_equal 2, company.clients_of_firm(true).size
|
||||
end
|
||||
|
||||
def test_build_many_via_block
|
||||
company = companies(:first_firm)
|
||||
new_clients = assert_no_queries do
|
||||
company.clients_of_firm.build([{"name" => "Another Client"}, {"name" => "Another Client II"}]) do |client|
|
||||
client.name = "changed"
|
||||
end
|
||||
end
|
||||
|
||||
assert_equal 2, new_clients.size
|
||||
assert_equal "changed", new_clients.first.name
|
||||
assert_equal "changed", new_clients.last.name
|
||||
|
||||
company.name += '-changed'
|
||||
assert_queries(3) { assert company.save }
|
||||
assert_equal 3, company.clients_of_firm(true).size
|
||||
end
|
||||
|
||||
def test_create_without_loading_association
|
||||
first_firm = companies(:first_firm)
|
||||
Firm.column_names
|
||||
|
||||
@@ -187,4 +187,10 @@ class HasManyThroughAssociationsTest < ActiveRecord::TestCase
|
||||
post.people_with_callbacks.clear
|
||||
assert_equal (%w(Michael David Julian Roger) * 2).sort, log.last(8).collect(&:last).sort
|
||||
end
|
||||
|
||||
def test_dynamic_find_should_respect_association_include
|
||||
# SQL error in sort clause if :include is not included
|
||||
# due to Unknown column 'comments.id'
|
||||
assert Person.find(1).posts_with_comments_sorted_by_comment_id.find_by_title('Welcome to the weblog')
|
||||
end
|
||||
end
|
||||
|
||||
@@ -29,6 +29,13 @@ class HasOneAssociationsTest < ActiveRecord::TestCase
|
||||
assert_equal Firm.find(1, :include => :account_with_select).account_with_select.attributes.size, 2
|
||||
end
|
||||
|
||||
def test_finding_using_primary_key
|
||||
firm = companies(:first_firm)
|
||||
assert_equal Account.find_by_firm_id(firm.id), firm.account
|
||||
firm.firm_id = companies(:rails_core).id
|
||||
assert_equal accounts(:rails_core_account), firm.account_using_primary_key
|
||||
end
|
||||
|
||||
def test_can_marshal_has_one_association_with_nil_target
|
||||
firm = Firm.new
|
||||
assert_nothing_raised do
|
||||
|
||||
@@ -189,6 +189,114 @@ class AssociationProxyTest < ActiveRecord::TestCase
|
||||
end
|
||||
end
|
||||
|
||||
def test_belongs_to_mass_assignment
|
||||
post_attributes = { :title => 'Associations', :body => 'Are They Accessible?' }
|
||||
author_attributes = { :name => 'David Dollar' }
|
||||
|
||||
assert_no_difference 'Author.count' do
|
||||
assert_raise(ActiveRecord::AssociationTypeMismatch) do
|
||||
Post.create(post_attributes.merge({:author => author_attributes}))
|
||||
end
|
||||
end
|
||||
|
||||
assert_difference 'Author.count' do
|
||||
post = Post.create(post_attributes.merge({:creatable_author => author_attributes}))
|
||||
assert_equal post.creatable_author.name, author_attributes[:name]
|
||||
end
|
||||
end
|
||||
|
||||
def test_has_one_mass_assignment
|
||||
post_attributes = { :title => 'Associations', :body => 'Are They Accessible?' }
|
||||
comment_attributes = { :body => 'Setter Takes Hash' }
|
||||
|
||||
assert_no_difference 'Comment.count' do
|
||||
assert_raise(ActiveRecord::AssociationTypeMismatch) do
|
||||
Post.create(post_attributes.merge({:uncreatable_comment => comment_attributes}))
|
||||
end
|
||||
end
|
||||
|
||||
assert_difference 'Comment.count' do
|
||||
post = Post.create(post_attributes.merge({:creatable_comment => comment_attributes}))
|
||||
assert_equal post.creatable_comment.body, comment_attributes[:body]
|
||||
end
|
||||
end
|
||||
|
||||
def test_has_many_mass_assignment
|
||||
post = posts(:welcome)
|
||||
post_attributes = { :title => 'Associations', :body => 'Are They Accessible?' }
|
||||
comment_attributes = { :body => 'Setter Takes Hash' }
|
||||
|
||||
assert_no_difference 'Comment.count' do
|
||||
assert_raise(ActiveRecord::AssociationTypeMismatch) do
|
||||
Post.create(post_attributes.merge({:comments => [comment_attributes]}))
|
||||
end
|
||||
assert_raise(ActiveRecord::AssociationTypeMismatch) do
|
||||
post.comments << comment_attributes
|
||||
end
|
||||
end
|
||||
|
||||
assert_difference 'Comment.count' do
|
||||
post = Post.create(post_attributes.merge({:creatable_comments => [comment_attributes]}))
|
||||
assert_equal post.creatable_comments.last.body, comment_attributes[:body]
|
||||
end
|
||||
|
||||
assert_difference 'Comment.count' do
|
||||
post.creatable_comments << comment_attributes
|
||||
assert_equal post.comments.last.body, comment_attributes[:body]
|
||||
end
|
||||
|
||||
post.creatable_comments = [comment_attributes, comment_attributes]
|
||||
assert_equal post.creatable_comments.count, 2
|
||||
end
|
||||
|
||||
def test_has_and_belongs_to_many_mass_assignment
|
||||
post = posts(:welcome)
|
||||
post_attributes = { :title => 'Associations', :body => 'Are They Accessible?' }
|
||||
category_attributes = { :name => 'Accessible Association', :type => 'Category' }
|
||||
|
||||
assert_no_difference 'Category.count' do
|
||||
assert_raise(ActiveRecord::AssociationTypeMismatch) do
|
||||
Post.create(post_attributes.merge({:categories => [category_attributes]}))
|
||||
end
|
||||
assert_raise(ActiveRecord::AssociationTypeMismatch) do
|
||||
post.categories << category_attributes
|
||||
end
|
||||
end
|
||||
|
||||
assert_difference 'Category.count' do
|
||||
post = Post.create(post_attributes.merge({:creatable_categories => [category_attributes]}))
|
||||
assert_equal post.creatable_categories.last.name, category_attributes[:name]
|
||||
end
|
||||
|
||||
assert_difference 'Category.count' do
|
||||
post.creatable_categories << category_attributes
|
||||
assert_equal post.creatable_categories.last.name, category_attributes[:name]
|
||||
end
|
||||
|
||||
post.creatable_categories = [category_attributes, category_attributes]
|
||||
assert_equal post.creatable_categories.count, 2
|
||||
end
|
||||
|
||||
def test_association_proxy_setter_can_take_hash
|
||||
special_comment_attributes = { :body => 'Setter Takes Hash' }
|
||||
|
||||
post = posts(:welcome)
|
||||
post.creatable_comment = { :body => 'Setter Takes Hash' }
|
||||
|
||||
assert_equal post.creatable_comment.body, special_comment_attributes[:body]
|
||||
end
|
||||
|
||||
def test_association_collection_can_take_hash
|
||||
post_attributes = { :title => 'Setter Takes', :body => 'Hash' }
|
||||
david = authors(:david)
|
||||
|
||||
post = (david.posts << post_attributes).last
|
||||
assert_equal post.title, post_attributes[:title]
|
||||
|
||||
david.posts = [post_attributes, post_attributes]
|
||||
assert_equal david.posts.count, 2
|
||||
end
|
||||
|
||||
def setup_dangling_association
|
||||
josh = Author.create(:name => "Josh")
|
||||
p = Post.create(:title => "New on Edge", :body => "More cool stuff!", :author => josh)
|
||||
|
||||
@@ -19,6 +19,7 @@ require 'models/warehouse_thing'
|
||||
require 'rexml/document'
|
||||
|
||||
class Category < ActiveRecord::Base; end
|
||||
class Categorization < ActiveRecord::Base; end
|
||||
class Smarts < ActiveRecord::Base; end
|
||||
class CreditCard < ActiveRecord::Base
|
||||
class PinNumber < ActiveRecord::Base
|
||||
@@ -75,7 +76,7 @@ class TopicWithProtectedContentAndAccessibleAuthorName < ActiveRecord::Base
|
||||
end
|
||||
|
||||
class BasicsTest < ActiveRecord::TestCase
|
||||
fixtures :topics, :companies, :developers, :projects, :computers, :accounts, :minimalistics, 'warehouse-things', :authors
|
||||
fixtures :topics, :companies, :developers, :projects, :computers, :accounts, :minimalistics, 'warehouse-things', :authors, :categorizations
|
||||
|
||||
def test_table_exists
|
||||
assert !NonExistentTable.table_exists?
|
||||
@@ -130,7 +131,7 @@ class BasicsTest < ActiveRecord::TestCase
|
||||
|
||||
def test_read_attributes_before_type_cast
|
||||
category = Category.new({:name=>"Test categoty", :type => nil})
|
||||
category_attrs = {"name"=>"Test categoty", "type" => nil}
|
||||
category_attrs = {"name"=>"Test categoty", "type" => nil, "categorizations_count" => nil}
|
||||
assert_equal category_attrs , category.attributes_before_type_cast
|
||||
end
|
||||
|
||||
@@ -614,6 +615,22 @@ class BasicsTest < ActiveRecord::TestCase
|
||||
assert_equal -2, Topic.find(2).replies_count
|
||||
end
|
||||
|
||||
def test_update_counter
|
||||
category = Category.first
|
||||
assert_nil category.categorizations_count
|
||||
assert_equal 2, category.categorizations.count
|
||||
|
||||
Category.update_counters(category.id, "categorizations_count" => category.categorizations.count)
|
||||
category.reload
|
||||
assert_not_nil category.categorizations_count
|
||||
assert_equal 2, category.categorizations_count
|
||||
|
||||
Category.update_counters(category.id, "categorizations_count" => category.categorizations.count)
|
||||
category.reload
|
||||
assert_not_nil category.categorizations_count
|
||||
assert_equal 4, category.categorizations_count
|
||||
end
|
||||
|
||||
def test_update_all
|
||||
assert_equal Topic.count, Topic.update_all("content = 'bulk updated!'")
|
||||
assert_equal "bulk updated!", Topic.find(1).content
|
||||
|
||||
36
activerecord/test/cases/column_definition_test.rb
Normal file
36
activerecord/test/cases/column_definition_test.rb
Normal file
@@ -0,0 +1,36 @@
|
||||
require "cases/helper"
|
||||
|
||||
class ColumnDefinitionTest < ActiveRecord::TestCase
|
||||
def setup
|
||||
@adapter = ActiveRecord::ConnectionAdapters::AbstractAdapter.new(nil)
|
||||
def @adapter.native_database_types
|
||||
{:string => "varchar"}
|
||||
end
|
||||
end
|
||||
|
||||
# Avoid column definitions in create table statements like:
|
||||
# `title` varchar(255) DEFAULT NULL NULL
|
||||
def test_should_not_include_default_clause_when_default_is_null
|
||||
column = ActiveRecord::ConnectionAdapters::Column.new("title", nil, "varchar(20)")
|
||||
column_def = ActiveRecord::ConnectionAdapters::ColumnDefinition.new(
|
||||
@adapter, column.name, "string",
|
||||
column.limit, column.precision, column.scale, column.default, column.null)
|
||||
assert_equal "title varchar(20) NULL", column_def.to_sql
|
||||
end
|
||||
|
||||
def test_should_include_default_clause_when_default_is_present
|
||||
column = ActiveRecord::ConnectionAdapters::Column.new("title", "Hello", "varchar(20)")
|
||||
column_def = ActiveRecord::ConnectionAdapters::ColumnDefinition.new(
|
||||
@adapter, column.name, "string",
|
||||
column.limit, column.precision, column.scale, column.default, column.null)
|
||||
assert_equal %Q{title varchar(20) DEFAULT 'Hello' NULL}, column_def.to_sql
|
||||
end
|
||||
|
||||
def test_should_specify_not_null_if_null_option_is_false
|
||||
column = ActiveRecord::ConnectionAdapters::Column.new("title", "Hello", "varchar(20)", false)
|
||||
column_def = ActiveRecord::ConnectionAdapters::ColumnDefinition.new(
|
||||
@adapter, column.name, "string",
|
||||
column.limit, column.precision, column.scale, column.default, column.null)
|
||||
assert_equal %Q{title varchar(20) DEFAULT 'Hello' NOT NULL}, column_def.to_sql
|
||||
end
|
||||
end
|
||||
@@ -2,6 +2,7 @@ require 'cases/helper'
|
||||
require 'models/topic' # For booleans
|
||||
require 'models/pirate' # For timestamps
|
||||
require 'models/parrot'
|
||||
require 'models/person' # For optimistic locking
|
||||
|
||||
class Pirate # Just reopening it, not defining it
|
||||
attr_accessor :detected_changes_in_after_update # Boolean for if changes are detected
|
||||
@@ -54,6 +55,33 @@ class DirtyTest < ActiveRecord::TestCase
|
||||
end
|
||||
end
|
||||
|
||||
def test_zero_to_blank_marked_as_changed
|
||||
pirate = Pirate.new
|
||||
pirate.catchphrase = "Yarrrr, me hearties"
|
||||
pirate.parrot_id = 1
|
||||
pirate.save
|
||||
|
||||
# check the change from 1 to ''
|
||||
pirate = Pirate.find_by_catchphrase("Yarrrr, me hearties")
|
||||
pirate.parrot_id = ''
|
||||
assert pirate.parrot_id_changed?
|
||||
assert_equal([1, nil], pirate.parrot_id_change)
|
||||
pirate.save
|
||||
|
||||
# check the change from nil to 0
|
||||
pirate = Pirate.find_by_catchphrase("Yarrrr, me hearties")
|
||||
pirate.parrot_id = 0
|
||||
assert pirate.parrot_id_changed?
|
||||
assert_equal([nil, 0], pirate.parrot_id_change)
|
||||
pirate.save
|
||||
|
||||
# check the change from 0 to ''
|
||||
pirate = Pirate.find_by_catchphrase("Yarrrr, me hearties")
|
||||
pirate.parrot_id = ''
|
||||
assert pirate.parrot_id_changed?
|
||||
assert_equal([0, nil], pirate.parrot_id_change)
|
||||
end
|
||||
|
||||
def test_object_should_be_changed_if_any_attribute_is_changed
|
||||
pirate = Pirate.new
|
||||
assert !pirate.changed?
|
||||
@@ -125,6 +153,24 @@ class DirtyTest < ActiveRecord::TestCase
|
||||
end
|
||||
end
|
||||
|
||||
def test_partial_update_with_optimistic_locking
|
||||
person = Person.new(:first_name => 'foo')
|
||||
old_lock_version = 1
|
||||
|
||||
with_partial_updates Person, false do
|
||||
assert_queries(2) { 2.times { person.save! } }
|
||||
Person.update_all({ :first_name => 'baz' }, :id => person.id)
|
||||
end
|
||||
|
||||
with_partial_updates Person, true do
|
||||
assert_queries(0) { 2.times { person.save! } }
|
||||
assert_equal old_lock_version, person.reload.lock_version
|
||||
|
||||
assert_queries(1) { person.first_name = 'bar'; person.save! }
|
||||
assert_not_equal old_lock_version, person.reload.lock_version
|
||||
end
|
||||
end
|
||||
|
||||
def test_changed_attributes_should_be_preserved_if_save_failure
|
||||
pirate = Pirate.new
|
||||
pirate.parrot_id = 1
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
require "cases/helper"
|
||||
require 'models/author'
|
||||
require 'models/categorization'
|
||||
require 'models/comment'
|
||||
require 'models/company'
|
||||
require 'models/topic'
|
||||
@@ -199,6 +200,23 @@ class FinderTest < ActiveRecord::TestCase
|
||||
assert_raises(ActiveRecord::RecordNotFound) { Topic.find(1, :conditions => { 'topics.approved' => true }) }
|
||||
end
|
||||
|
||||
def test_find_on_hash_conditions_with_hashed_table_name
|
||||
assert Topic.find(1, :conditions => {:topics => { :approved => false }})
|
||||
assert_raises(ActiveRecord::RecordNotFound) { Topic.find(1, :conditions => {:topics => { :approved => true }}) }
|
||||
end
|
||||
|
||||
def test_find_with_hash_conditions_on_joined_table
|
||||
firms = Firm.all :joins => :account, :conditions => {:accounts => { :credit_limit => 50 }}
|
||||
assert_equal 1, firms.size
|
||||
assert_equal companies(:first_firm), firms.first
|
||||
end
|
||||
|
||||
def test_find_with_hash_conditions_on_joined_table_and_with_range
|
||||
firms = DependentFirm.all :joins => :account, :conditions => {:name => 'RailsCore', :accounts => { :credit_limit => 55..60 }}
|
||||
assert_equal 1, firms.size
|
||||
assert_equal companies(:rails_core), firms.first
|
||||
end
|
||||
|
||||
def test_find_on_hash_conditions_with_explicit_table_name_and_aggregate
|
||||
david = customers(:david)
|
||||
assert Customer.find(david.id, :conditions => { 'customers.name' => david.name, :address => david.address })
|
||||
@@ -394,6 +412,12 @@ class FinderTest < ActiveRecord::TestCase
|
||||
assert_equal '1,1,1', bind('?', os)
|
||||
end
|
||||
|
||||
def test_named_bind_with_postgresql_type_casts
|
||||
l = Proc.new { bind(":a::integer '2009-01-01'::date", :a => '10') }
|
||||
assert_nothing_raised(&l)
|
||||
assert_equal "#{ActiveRecord::Base.quote_value('10')}::integer '2009-01-01'::date", l.call
|
||||
end
|
||||
|
||||
def test_string_sanitation
|
||||
assert_not_equal "#{ActiveRecord::Base.connection.quoted_string_prefix}'something ' 1=1'", ActiveRecord::Base.sanitize("something ' 1=1")
|
||||
assert_equal "#{ActiveRecord::Base.connection.quoted_string_prefix}'something; select table'", ActiveRecord::Base.sanitize("something; select table")
|
||||
|
||||
@@ -15,6 +15,7 @@ require 'models/pirate'
|
||||
require 'models/treasure'
|
||||
require 'models/matey'
|
||||
require 'models/ship'
|
||||
require 'models/book'
|
||||
|
||||
class FixturesTest < ActiveRecord::TestCase
|
||||
self.use_instantiated_fixtures = true
|
||||
@@ -373,6 +374,34 @@ class CheckSetTableNameFixturesTest < ActiveRecord::TestCase
|
||||
end
|
||||
end
|
||||
|
||||
class FixtureNameIsNotTableNameFixturesTest < ActiveRecord::TestCase
|
||||
set_fixture_class :items => Book
|
||||
fixtures :items
|
||||
# Set to false to blow away fixtures cache and ensure our fixtures are loaded
|
||||
# and thus takes into account our set_fixture_class
|
||||
self.use_transactional_fixtures = false
|
||||
|
||||
def test_named_accessor
|
||||
assert_kind_of Book, items(:dvd)
|
||||
end
|
||||
end
|
||||
|
||||
class FixtureNameIsNotTableNameMultipleFixturesTest < ActiveRecord::TestCase
|
||||
set_fixture_class :items => Book, :funny_jokes => Joke
|
||||
fixtures :items, :funny_jokes
|
||||
# Set to false to blow away fixtures cache and ensure our fixtures are loaded
|
||||
# and thus takes into account our set_fixture_class
|
||||
self.use_transactional_fixtures = false
|
||||
|
||||
def test_named_accessor_of_differently_named_fixture
|
||||
assert_kind_of Book, items(:dvd)
|
||||
end
|
||||
|
||||
def test_named_accessor_of_same_named_fixture
|
||||
assert_kind_of Joke, funny_jokes(:a_joke)
|
||||
end
|
||||
end
|
||||
|
||||
class CustomConnectionFixturesTest < ActiveRecord::TestCase
|
||||
set_fixture_class :courses => Course
|
||||
fixtures :courses
|
||||
@@ -432,11 +461,11 @@ class FixturesBrokenRollbackTest < ActiveRecord::TestCase
|
||||
alias_method :teardown, :blank_teardown
|
||||
|
||||
def test_no_rollback_in_teardown_unless_transaction_active
|
||||
assert_equal 0, Thread.current['open_transactions']
|
||||
assert_equal 0, ActiveRecord::Base.connection.open_transactions
|
||||
assert_raise(RuntimeError) { ar_setup_fixtures }
|
||||
assert_equal 0, Thread.current['open_transactions']
|
||||
assert_equal 0, ActiveRecord::Base.connection.open_transactions
|
||||
assert_nothing_raised { ar_teardown_fixtures }
|
||||
assert_equal 0, Thread.current['open_transactions']
|
||||
assert_equal 0, ActiveRecord::Base.connection.open_transactions
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
@@ -32,13 +32,13 @@ end
|
||||
ActiveRecord::Base.connection.class.class_eval do
|
||||
IGNORED_SQL = [/^PRAGMA/, /^SELECT currval/, /^SELECT CAST/, /^SELECT @@IDENTITY/, /^SELECT @@ROWCOUNT/]
|
||||
|
||||
def execute_with_counting(sql, name = nil, &block)
|
||||
$query_count ||= 0
|
||||
$query_count += 1 unless IGNORED_SQL.any? { |r| sql =~ r }
|
||||
execute_without_counting(sql, name, &block)
|
||||
def execute_with_query_record(sql, name = nil, &block)
|
||||
$queries_executed ||= []
|
||||
$queries_executed << sql unless IGNORED_SQL.any? { |r| sql =~ r }
|
||||
execute_without_query_record(sql, name, &block)
|
||||
end
|
||||
|
||||
alias_method_chain :execute, :counting
|
||||
alias_method_chain :execute, :query_record
|
||||
end
|
||||
|
||||
# Make with_scope public for tests
|
||||
|
||||
@@ -191,6 +191,13 @@ class InheritanceTest < ActiveRecord::TestCase
|
||||
assert_not_nil account.instance_variable_get("@firm"), "nil proves eager load failed"
|
||||
end
|
||||
|
||||
def test_eager_load_belongs_to_primary_key_quoting
|
||||
con = Account.connection
|
||||
assert_sql(/\(#{con.quote_table_name('companies')}.#{con.quote_column_name('id')} IN \(1\)\)/) do
|
||||
Account.find(1, :include => :firm)
|
||||
end
|
||||
end
|
||||
|
||||
def test_alt_eager_loading
|
||||
switch_to_alt_inheritance_column
|
||||
test_eager_load_belongs_to_something_inherited
|
||||
|
||||
@@ -143,12 +143,20 @@ class LifecycleTest < ActiveRecord::TestCase
|
||||
assert_equal developer.name, multi_observer.record.name
|
||||
end
|
||||
|
||||
def test_observing_after_find_when_not_defined_on_the_model
|
||||
def test_after_find_cannot_be_observed_when_its_not_defined_on_the_model
|
||||
observer = MinimalisticObserver.instance
|
||||
assert_equal Minimalistic, MinimalisticObserver.observed_class
|
||||
|
||||
minimalistic = Minimalistic.find(1)
|
||||
assert_equal minimalistic, observer.minimalistic
|
||||
assert_nil observer.minimalistic
|
||||
end
|
||||
|
||||
def test_after_find_can_be_observed_when_its_defined_on_the_model
|
||||
observer = TopicObserver.instance
|
||||
assert_equal Topic, TopicObserver.observed_class
|
||||
|
||||
topic = Topic.find(1)
|
||||
assert_equal topic, observer.topic
|
||||
end
|
||||
|
||||
def test_invalid_observer
|
||||
|
||||
@@ -29,10 +29,12 @@ class OptimisticLockingTest < ActiveRecord::TestCase
|
||||
assert_equal 0, p1.lock_version
|
||||
assert_equal 0, p2.lock_version
|
||||
|
||||
p1.first_name = 'stu'
|
||||
p1.save!
|
||||
assert_equal 1, p1.lock_version
|
||||
assert_equal 0, p2.lock_version
|
||||
|
||||
p2.first_name = 'sue'
|
||||
assert_raises(ActiveRecord::StaleObjectError) { p2.save! }
|
||||
end
|
||||
|
||||
@@ -42,11 +44,14 @@ class OptimisticLockingTest < ActiveRecord::TestCase
|
||||
assert_equal 0, p1.lock_version
|
||||
assert_equal 0, p2.lock_version
|
||||
|
||||
p1.first_name = 'stu'
|
||||
p1.save!
|
||||
assert_equal 1, p1.lock_version
|
||||
assert_equal 0, p2.lock_version
|
||||
|
||||
p2.first_name = 'sue'
|
||||
assert_raises(ActiveRecord::StaleObjectError) { p2.save! }
|
||||
p2.first_name = 'sue2'
|
||||
assert_raises(ActiveRecord::StaleObjectError) { p2.save! }
|
||||
end
|
||||
|
||||
@@ -54,15 +59,18 @@ class OptimisticLockingTest < ActiveRecord::TestCase
|
||||
p1 = Person.new(:first_name => 'anika')
|
||||
assert_equal 0, p1.lock_version
|
||||
|
||||
p1.first_name = 'anika2'
|
||||
p1.save!
|
||||
p2 = Person.find(p1.id)
|
||||
assert_equal 0, p1.lock_version
|
||||
assert_equal 0, p2.lock_version
|
||||
|
||||
p1.first_name = 'anika3'
|
||||
p1.save!
|
||||
assert_equal 1, p1.lock_version
|
||||
assert_equal 0, p2.lock_version
|
||||
|
||||
p2.first_name = 'sue'
|
||||
assert_raises(ActiveRecord::StaleObjectError) { p2.save! }
|
||||
end
|
||||
|
||||
@@ -81,10 +89,12 @@ class OptimisticLockingTest < ActiveRecord::TestCase
|
||||
assert_equal 0, t1.version
|
||||
assert_equal 0, t2.version
|
||||
|
||||
t1.tps_report_number = 700
|
||||
t1.save!
|
||||
assert_equal 1, t1.version
|
||||
assert_equal 0, t2.version
|
||||
|
||||
t2.tps_report_number = 800
|
||||
assert_raises(ActiveRecord::StaleObjectError) { t2.save! }
|
||||
end
|
||||
|
||||
@@ -93,6 +103,7 @@ class OptimisticLockingTest < ActiveRecord::TestCase
|
||||
assert_equal 0, p1.lock_version
|
||||
assert_equal p1.lock_version, Person.new(p1.attributes).lock_version
|
||||
|
||||
p1.first_name = 'bianca2'
|
||||
p1.save!
|
||||
assert_equal 1, p1.lock_version
|
||||
assert_equal p1.lock_version, Person.new(p1.attributes).lock_version
|
||||
@@ -146,6 +157,15 @@ class OptimisticLockingTest < ActiveRecord::TestCase
|
||||
assert ref.save
|
||||
end
|
||||
|
||||
# Useful for partial updates, don't only update the lock_version if there
|
||||
# is nothing else being updated.
|
||||
def test_update_without_attributes_does_not_only_update_lock_version
|
||||
assert_nothing_raised do
|
||||
p1 = Person.new(:first_name => 'anika')
|
||||
p1.send(:update_with_lock, [])
|
||||
end
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def add_counter_column_to(model)
|
||||
|
||||
@@ -87,6 +87,16 @@ class MethodScopingTest < ActiveRecord::TestCase
|
||||
assert_equal 1, scoped_developers.size
|
||||
end
|
||||
|
||||
def test_scoped_find_joins
|
||||
scoped_developers = Developer.with_scope(:find => { :joins => 'JOIN developers_projects ON id = developer_id' } ) do
|
||||
Developer.find(:all, :conditions => 'developers_projects.project_id = 2')
|
||||
end
|
||||
assert scoped_developers.include?(developers(:david))
|
||||
assert !scoped_developers.include?(developers(:jamis))
|
||||
assert_equal 1, scoped_developers.size
|
||||
assert_equal developers(:david).attributes, scoped_developers.first.attributes
|
||||
end
|
||||
|
||||
def test_scoped_count_include
|
||||
# with the include, will retrieve only developers for the given project
|
||||
Developer.with_scope(:find => { :include => :projects }) do
|
||||
|
||||
@@ -3,6 +3,7 @@ require 'bigdecimal/util'
|
||||
|
||||
require 'models/person'
|
||||
require 'models/topic'
|
||||
require 'models/developer'
|
||||
|
||||
require MIGRATIONS_ROOT + "/valid/1_people_have_last_names"
|
||||
require MIGRATIONS_ROOT + "/valid/2_we_need_reminders"
|
||||
@@ -153,9 +154,10 @@ if ActiveRecord::Base.connection.supports_migrations?
|
||||
|
||||
t.column :default_int, :integer
|
||||
|
||||
t.column :one_int, :integer, :limit => 1
|
||||
t.column :four_int, :integer, :limit => 4
|
||||
t.column :eight_int, :integer, :limit => 8
|
||||
t.column :one_int, :integer, :limit => 1
|
||||
t.column :four_int, :integer, :limit => 4
|
||||
t.column :eight_int, :integer, :limit => 8
|
||||
t.column :eleven_int, :integer, :limit => 11
|
||||
end
|
||||
end
|
||||
|
||||
@@ -167,12 +169,20 @@ if ActiveRecord::Base.connection.supports_migrations?
|
||||
one = columns.detect { |c| c.name == "one_int" }
|
||||
four = columns.detect { |c| c.name == "four_int" }
|
||||
eight = columns.detect { |c| c.name == "eight_int" }
|
||||
eleven = columns.detect { |c| c.name == "eleven_int" }
|
||||
|
||||
if current_adapter?(:PostgreSQLAdapter)
|
||||
assert_equal 'integer', default.sql_type
|
||||
assert_equal 'smallint', one.sql_type
|
||||
assert_equal 'integer', four.sql_type
|
||||
assert_equal 'bigint', eight.sql_type
|
||||
assert_equal 'integer', eleven.sql_type
|
||||
elsif current_adapter?(:MysqlAdapter)
|
||||
assert_match 'int(11)', default.sql_type
|
||||
assert_match 'tinyint', one.sql_type
|
||||
assert_match 'int', four.sql_type
|
||||
assert_match 'bigint', eight.sql_type
|
||||
assert_match 'int(11)', eleven.sql_type
|
||||
elsif current_adapter?(:OracleAdapter)
|
||||
assert_equal 'NUMBER(38)', default.sql_type
|
||||
assert_equal 'NUMBER(1)', one.sql_type
|
||||
@@ -483,6 +493,37 @@ if ActiveRecord::Base.connection.supports_migrations?
|
||||
end
|
||||
end
|
||||
|
||||
def test_rename_column_preserves_default_value_not_null
|
||||
begin
|
||||
default_before = Developer.connection.columns("developers").find { |c| c.name == "salary" }.default
|
||||
assert_equal 70000, default_before
|
||||
Developer.connection.rename_column "developers", "salary", "anual_salary"
|
||||
Developer.reset_column_information
|
||||
assert Developer.column_names.include?("anual_salary")
|
||||
default_after = Developer.connection.columns("developers").find { |c| c.name == "anual_salary" }.default
|
||||
assert_equal 70000, default_after
|
||||
ensure
|
||||
Developer.connection.rename_column "developers", "anual_salary", "salary"
|
||||
Developer.reset_column_information
|
||||
end
|
||||
end
|
||||
|
||||
def test_rename_nonexistent_column
|
||||
ActiveRecord::Base.connection.create_table(:hats) do |table|
|
||||
table.column :hat_name, :string, :default => nil
|
||||
end
|
||||
exception = if current_adapter?(:PostgreSQLAdapter)
|
||||
ActiveRecord::StatementInvalid
|
||||
else
|
||||
ActiveRecord::ActiveRecordError
|
||||
end
|
||||
assert_raises(exception) do
|
||||
Person.connection.rename_column "hats", "nonexistent", "should_fail"
|
||||
end
|
||||
ensure
|
||||
ActiveRecord::Base.connection.drop_table(:hats)
|
||||
end
|
||||
|
||||
def test_rename_column_with_sql_reserved_word
|
||||
begin
|
||||
assert_nothing_raised { Person.connection.rename_column "people", "first_name", "group" }
|
||||
@@ -662,6 +703,55 @@ if ActiveRecord::Base.connection.supports_migrations?
|
||||
Person.connection.drop_table :testings rescue nil
|
||||
end
|
||||
|
||||
def test_keeping_default_and_notnull_constaint_on_change
|
||||
Person.connection.create_table :testings do |t|
|
||||
t.column :title, :string
|
||||
end
|
||||
person_klass = Class.new(Person)
|
||||
person_klass.set_table_name 'testings'
|
||||
|
||||
person_klass.connection.add_column "testings", "wealth", :integer, :null => false, :default => 99
|
||||
person_klass.reset_column_information
|
||||
assert_equal 99, person_klass.columns_hash["wealth"].default
|
||||
assert_equal false, person_klass.columns_hash["wealth"].null
|
||||
assert_nothing_raised {person_klass.connection.execute("insert into testings (title) values ('tester')")}
|
||||
|
||||
# change column default to see that column doesn't lose its not null definition
|
||||
person_klass.connection.change_column_default "testings", "wealth", 100
|
||||
person_klass.reset_column_information
|
||||
assert_equal 100, person_klass.columns_hash["wealth"].default
|
||||
assert_equal false, person_klass.columns_hash["wealth"].null
|
||||
|
||||
# rename column to see that column doesn't lose its not null and/or default definition
|
||||
person_klass.connection.rename_column "testings", "wealth", "money"
|
||||
person_klass.reset_column_information
|
||||
assert_nil person_klass.columns_hash["wealth"]
|
||||
assert_equal 100, person_klass.columns_hash["money"].default
|
||||
assert_equal false, person_klass.columns_hash["money"].null
|
||||
|
||||
# change column
|
||||
person_klass.connection.change_column "testings", "money", :integer, :null => false, :default => 1000
|
||||
person_klass.reset_column_information
|
||||
assert_equal 1000, person_klass.columns_hash["money"].default
|
||||
assert_equal false, person_klass.columns_hash["money"].null
|
||||
|
||||
# change column, make it nullable and clear default
|
||||
person_klass.connection.change_column "testings", "money", :integer, :null => true, :default => nil
|
||||
person_klass.reset_column_information
|
||||
assert_nil person_klass.columns_hash["money"].default
|
||||
assert_equal true, person_klass.columns_hash["money"].null
|
||||
|
||||
# change_column_null, make it not nullable and set null values to a default value
|
||||
person_klass.connection.execute('UPDATE testings SET money = NULL')
|
||||
person_klass.connection.change_column_null "testings", "money", false, 2000
|
||||
person_klass.reset_column_information
|
||||
assert_nil person_klass.columns_hash["money"].default
|
||||
assert_equal false, person_klass.columns_hash["money"].null
|
||||
assert_equal [2000], Person.connection.select_values("SELECT money FROM testings").map { |s| s.to_i }.sort
|
||||
ensure
|
||||
Person.connection.drop_table :testings rescue nil
|
||||
end
|
||||
|
||||
def test_change_column_default_to_null
|
||||
Person.connection.change_column_default "people", "first_name", nil
|
||||
Person.reset_column_information
|
||||
@@ -799,6 +889,21 @@ if ActiveRecord::Base.connection.supports_migrations?
|
||||
assert !Reminder.table_exists?
|
||||
end
|
||||
|
||||
def test_migrator_double_up
|
||||
assert_equal(0, ActiveRecord::Migrator.current_version)
|
||||
ActiveRecord::Migrator.run(:up, MIGRATIONS_ROOT + "/valid", 1)
|
||||
assert_nothing_raised { ActiveRecord::Migrator.run(:up, MIGRATIONS_ROOT + "/valid", 1) }
|
||||
assert_equal(1, ActiveRecord::Migrator.current_version)
|
||||
end
|
||||
|
||||
def test_migrator_double_down
|
||||
assert_equal(0, ActiveRecord::Migrator.current_version)
|
||||
ActiveRecord::Migrator.run(:up, MIGRATIONS_ROOT + "/valid", 1)
|
||||
ActiveRecord::Migrator.run(:down, MIGRATIONS_ROOT + "/valid", 1)
|
||||
assert_nothing_raised { ActiveRecord::Migrator.run(:down, MIGRATIONS_ROOT + "/valid", 1) }
|
||||
assert_equal(0, ActiveRecord::Migrator.current_version)
|
||||
end
|
||||
|
||||
def test_finds_migrations
|
||||
migrations = ActiveRecord::Migrator.new(:up, MIGRATIONS_ROOT + "/valid").migrations
|
||||
[['1', 'people_have_last_names'],
|
||||
@@ -888,16 +993,6 @@ if ActiveRecord::Base.connection.supports_migrations?
|
||||
ActiveRecord::Migrator.rollback(MIGRATIONS_ROOT + "/valid")
|
||||
assert_equal(0, ActiveRecord::Migrator.current_version)
|
||||
end
|
||||
|
||||
def test_migrator_run
|
||||
assert_equal(0, ActiveRecord::Migrator.current_version)
|
||||
ActiveRecord::Migrator.run(:up, MIGRATIONS_ROOT + "/valid", 3)
|
||||
assert_equal(0, ActiveRecord::Migrator.current_version)
|
||||
|
||||
assert_equal(0, ActiveRecord::Migrator.current_version)
|
||||
ActiveRecord::Migrator.run(:down, MIGRATIONS_ROOT + "/valid", 3)
|
||||
assert_equal(0, ActiveRecord::Migrator.current_version)
|
||||
end
|
||||
|
||||
def test_schema_migrations_table_name
|
||||
ActiveRecord::Base.table_name_prefix = "prefix_"
|
||||
@@ -1206,10 +1301,10 @@ if ActiveRecord::Base.connection.supports_migrations?
|
||||
end
|
||||
|
||||
def integer_column
|
||||
if current_adapter?(:SQLite3Adapter) || current_adapter?(:SQLiteAdapter) || current_adapter?(:PostgreSQLAdapter)
|
||||
"integer"
|
||||
else
|
||||
if current_adapter?(:MysqlAdapter)
|
||||
'int(11)'
|
||||
else
|
||||
'integer'
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
@@ -57,4 +57,29 @@ class MultipleDbTest < ActiveRecord::TestCase
|
||||
|
||||
assert Course.connection
|
||||
end
|
||||
|
||||
def test_transactions_across_databases
|
||||
c1 = Course.find(1)
|
||||
e1 = Entrant.find(1)
|
||||
|
||||
begin
|
||||
Course.transaction do
|
||||
Entrant.transaction do
|
||||
c1.name = "Typo"
|
||||
e1.name = "Typo"
|
||||
c1.save
|
||||
e1.save
|
||||
raise "No I messed up."
|
||||
end
|
||||
end
|
||||
rescue
|
||||
# Yup caught it
|
||||
end
|
||||
|
||||
assert_equal "Typo", c1.name
|
||||
assert_equal "Typo", e1.name
|
||||
|
||||
assert_equal "Ruby Development", Course.find(1).name
|
||||
assert_equal "Ruby Developer", Entrant.find(1).name
|
||||
end
|
||||
end
|
||||
|
||||
@@ -6,7 +6,7 @@ require 'models/reply'
|
||||
require 'models/author'
|
||||
|
||||
class NamedScopeTest < ActiveRecord::TestCase
|
||||
fixtures :posts, :authors, :topics, :comments
|
||||
fixtures :posts, :authors, :topics, :comments, :author_addresses
|
||||
|
||||
def test_implements_enumerable
|
||||
assert !Topic.find(:all).empty?
|
||||
@@ -59,6 +59,16 @@ class NamedScopeTest < ActiveRecord::TestCase
|
||||
assert_equal Topic.count(:conditions => {:approved => true}), Topic.approved.count
|
||||
end
|
||||
|
||||
def test_scopes_with_string_name_can_be_composed
|
||||
# NOTE that scopes defined with a string as a name worked on their own
|
||||
# but when called on another scope the other scope was completely replaced
|
||||
assert_equal Topic.replied.approved, Topic.replied.approved_as_string
|
||||
end
|
||||
|
||||
def test_scopes_can_be_specified_with_deep_hash_conditions
|
||||
assert_equal Topic.replied.approved, Topic.replied.approved_as_hash_condition
|
||||
end
|
||||
|
||||
def test_scopes_are_composable
|
||||
assert_equal (approved = Topic.find(:all, :conditions => {:approved => true})), Topic.approved
|
||||
assert_equal (replied = Topic.find(:all, :conditions => 'replies_count > 0')), Topic.replied
|
||||
@@ -77,6 +87,25 @@ class NamedScopeTest < ActiveRecord::TestCase
|
||||
assert_equal topics_written_before_the_second, Topic.written_before(topics(:second).written_on)
|
||||
end
|
||||
|
||||
def test_scopes_with_joins
|
||||
address = author_addresses(:david_address)
|
||||
posts_with_authors_at_address = Post.find(
|
||||
:all, :joins => 'JOIN authors ON authors.id = posts.author_id',
|
||||
:conditions => [ 'authors.author_address_id = ?', address.id ]
|
||||
)
|
||||
assert_equal posts_with_authors_at_address, Post.with_authors_at_address(address)
|
||||
end
|
||||
|
||||
def test_scopes_with_joins_respects_custom_select
|
||||
address = author_addresses(:david_address)
|
||||
posts_with_authors_at_address_titles = Post.find(:all,
|
||||
:select => 'title',
|
||||
:joins => 'JOIN authors ON authors.id = posts.author_id',
|
||||
:conditions => [ 'authors.author_address_id = ?', address.id ]
|
||||
)
|
||||
assert_equal posts_with_authors_at_address_titles, Post.with_authors_at_address(address).find(:all, :select => 'title')
|
||||
end
|
||||
|
||||
def test_extensions
|
||||
assert_equal 1, Topic.anonymous_extension.one
|
||||
assert_equal 2, Topic.named_extension.two
|
||||
@@ -154,4 +183,30 @@ class NamedScopeTest < ActiveRecord::TestCase
|
||||
topics.empty? # use loaded (no query)
|
||||
end
|
||||
end
|
||||
|
||||
def test_should_build_with_proxy_options
|
||||
topic = Topic.approved.build({})
|
||||
assert topic.approved
|
||||
end
|
||||
|
||||
def test_should_build_new_with_proxy_options
|
||||
topic = Topic.approved.new
|
||||
assert topic.approved
|
||||
end
|
||||
|
||||
def test_should_create_with_proxy_options
|
||||
topic = Topic.approved.create({})
|
||||
assert topic.approved
|
||||
end
|
||||
|
||||
def test_should_create_with_bang_with_proxy_options
|
||||
topic = Topic.approved.create!({})
|
||||
assert topic.approved
|
||||
end
|
||||
|
||||
def test_should_build_with_proxy_options_chained
|
||||
topic = Topic.approved.by_lifo.build({})
|
||||
assert topic.approved
|
||||
assert_equal 'lifo', topic.author_name
|
||||
end
|
||||
end
|
||||
|
||||
@@ -160,9 +160,9 @@ class ReflectionTest < ActiveRecord::TestCase
|
||||
|
||||
def test_reflection_of_all_associations
|
||||
# FIXME these assertions bust a lot
|
||||
assert_equal 22, Firm.reflect_on_all_associations.size
|
||||
assert_equal 17, Firm.reflect_on_all_associations(:has_many).size
|
||||
assert_equal 5, Firm.reflect_on_all_associations(:has_one).size
|
||||
assert_equal 24, Firm.reflect_on_all_associations.size
|
||||
assert_equal 18, Firm.reflect_on_all_associations(:has_many).size
|
||||
assert_equal 6, Firm.reflect_on_all_associations(:has_one).size
|
||||
assert_equal 0, Firm.reflect_on_all_associations(:belongs_to).size
|
||||
end
|
||||
|
||||
|
||||
@@ -72,6 +72,52 @@ class SchemaDumperTest < ActiveRecord::TestCase
|
||||
assert_match %r{:null => false}, output
|
||||
end
|
||||
|
||||
def test_schema_dump_includes_limit_constraint_for_integer_columns
|
||||
stream = StringIO.new
|
||||
|
||||
ActiveRecord::SchemaDumper.ignore_tables = [/^(?!integer_limits)/]
|
||||
ActiveRecord::SchemaDumper.dump(ActiveRecord::Base.connection, stream)
|
||||
output = stream.string
|
||||
|
||||
if current_adapter?(:PostgreSQLAdapter)
|
||||
assert_match %r{c_int_1.*:limit => 2}, output
|
||||
assert_match %r{c_int_2.*:limit => 2}, output
|
||||
|
||||
# int 3 is 4 bytes in postgresql
|
||||
assert_match %r{c_int_3.*}, output
|
||||
assert_no_match %r{c_int_3.*:limit}, output
|
||||
|
||||
assert_match %r{c_int_4.*}, output
|
||||
assert_no_match %r{c_int_4.*:limit}, output
|
||||
elsif current_adapter?(:MysqlAdapter)
|
||||
assert_match %r{c_int_1.*:limit => 1}, output
|
||||
assert_match %r{c_int_2.*:limit => 2}, output
|
||||
assert_match %r{c_int_3.*:limit => 3}, output
|
||||
|
||||
assert_match %r{c_int_4.*}, output
|
||||
assert_no_match %r{c_int_4.*:limit}, output
|
||||
elsif current_adapter?(:SQLiteAdapter)
|
||||
assert_match %r{c_int_1.*:limit => 1}, output
|
||||
assert_match %r{c_int_2.*:limit => 2}, output
|
||||
assert_match %r{c_int_3.*:limit => 3}, output
|
||||
assert_match %r{c_int_4.*:limit => 4}, output
|
||||
end
|
||||
assert_match %r{c_int_without_limit.*}, output
|
||||
assert_no_match %r{c_int_without_limit.*:limit}, output
|
||||
|
||||
if current_adapter?(:SQLiteAdapter)
|
||||
assert_match %r{c_int_5.*:limit => 5}, output
|
||||
assert_match %r{c_int_6.*:limit => 6}, output
|
||||
assert_match %r{c_int_7.*:limit => 7}, output
|
||||
assert_match %r{c_int_8.*:limit => 8}, output
|
||||
else
|
||||
assert_match %r{c_int_5.*:limit => 8}, output
|
||||
assert_match %r{c_int_6.*:limit => 8}, output
|
||||
assert_match %r{c_int_7.*:limit => 8}, output
|
||||
assert_match %r{c_int_8.*:limit => 8}, output
|
||||
end
|
||||
end
|
||||
|
||||
def test_schema_dump_with_string_ignored_table
|
||||
stream = StringIO.new
|
||||
|
||||
|
||||
@@ -1061,6 +1061,18 @@ class ValidationsTest < ActiveRecord::TestCase
|
||||
end
|
||||
end
|
||||
|
||||
def test_validates_length_of_with_block
|
||||
Topic.validates_length_of :content, :minimum => 5, :too_short=>"Your essay must be at least %d words.",
|
||||
:tokenizer => lambda {|str| str.scan(/\w+/) }
|
||||
t = Topic.create!(:content => "this content should be long enough")
|
||||
assert t.valid?
|
||||
|
||||
t.content = "not long enough"
|
||||
assert !t.valid?
|
||||
assert t.errors.on(:content)
|
||||
assert_equal "Your essay must be at least 5 words.", t.errors[:content]
|
||||
end
|
||||
|
||||
def test_validates_size_of_association_utf8
|
||||
with_kcode('UTF8') do
|
||||
assert_nothing_raised { Topic.validates_size_of :replies, :minimum => 1 }
|
||||
@@ -1381,6 +1393,7 @@ class ValidatesNumericalityTest < ActiveRecord::TestCase
|
||||
INTEGERS = [0, 10, -10] + INTEGER_STRINGS
|
||||
BIGDECIMAL = BIGDECIMAL_STRINGS.collect! { |bd| BigDecimal.new(bd) }
|
||||
JUNK = ["not a number", "42 not a number", "0xdeadbeef", "00-1", "--3", "+-3", "+3-1", "-+019.0", "12.12.13.12", "123\nnot a number"]
|
||||
INFINITY = [1.0/0.0]
|
||||
|
||||
def setup
|
||||
Topic.instance_variable_set("@validate_callbacks", ActiveSupport::Callbacks::CallbackChain.new)
|
||||
@@ -1392,27 +1405,27 @@ class ValidatesNumericalityTest < ActiveRecord::TestCase
|
||||
Topic.validates_numericality_of :approved
|
||||
|
||||
invalid!(NIL + BLANK + JUNK)
|
||||
valid!(FLOATS + INTEGERS + BIGDECIMAL)
|
||||
valid!(FLOATS + INTEGERS + BIGDECIMAL + INFINITY)
|
||||
end
|
||||
|
||||
def test_validates_numericality_of_with_nil_allowed
|
||||
Topic.validates_numericality_of :approved, :allow_nil => true
|
||||
|
||||
invalid!(BLANK + JUNK)
|
||||
valid!(NIL + FLOATS + INTEGERS + BIGDECIMAL)
|
||||
valid!(NIL + FLOATS + INTEGERS + BIGDECIMAL + INFINITY)
|
||||
end
|
||||
|
||||
def test_validates_numericality_of_with_integer_only
|
||||
Topic.validates_numericality_of :approved, :only_integer => true
|
||||
|
||||
invalid!(NIL + BLANK + JUNK + FLOATS + BIGDECIMAL)
|
||||
invalid!(NIL + BLANK + JUNK + FLOATS + BIGDECIMAL + INFINITY)
|
||||
valid!(INTEGERS)
|
||||
end
|
||||
|
||||
def test_validates_numericality_of_with_integer_only_and_nil_allowed
|
||||
Topic.validates_numericality_of :approved, :only_integer => true, :allow_nil => true
|
||||
|
||||
invalid!(BLANK + JUNK + FLOATS + BIGDECIMAL)
|
||||
invalid!(BLANK + JUNK + FLOATS + BIGDECIMAL + INFINITY)
|
||||
valid!(NIL + INTEGERS)
|
||||
end
|
||||
|
||||
@@ -1433,7 +1446,7 @@ class ValidatesNumericalityTest < ActiveRecord::TestCase
|
||||
def test_validates_numericality_with_equal_to
|
||||
Topic.validates_numericality_of :approved, :equal_to => 10
|
||||
|
||||
invalid!([-10, 11], 'must be equal to 10')
|
||||
invalid!([-10, 11] + INFINITY, 'must be equal to 10')
|
||||
valid!([10])
|
||||
end
|
||||
|
||||
|
||||
1
activerecord/test/fixtures/companies.yml
vendored
1
activerecord/test/fixtures/companies.yml
vendored
@@ -5,6 +5,7 @@ first_client:
|
||||
client_of: 2
|
||||
name: Summit
|
||||
ruby_type: Client
|
||||
firm_name: 37signals
|
||||
|
||||
first_firm:
|
||||
id: 1
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
class Author < ActiveRecord::Base
|
||||
has_many :posts
|
||||
has_many :posts, :accessible => true
|
||||
has_many :posts_with_comments, :include => :comments, :class_name => "Post"
|
||||
has_many :posts_with_comments_sorted_by_comment_id, :include => :comments, :class_name => "Post", :order => 'comments.id'
|
||||
has_many :posts_with_categories, :include => :categories, :class_name => "Post"
|
||||
has_many :posts_with_comments_and_categories, :include => [ :comments, :categories ], :order => "posts.id", :class_name => "Post"
|
||||
has_many :posts_containing_the_letter_a, :class_name => "Post"
|
||||
|
||||
@@ -2,6 +2,7 @@ class Category < ActiveRecord::Base
|
||||
has_and_belongs_to_many :posts
|
||||
has_and_belongs_to_many :special_posts, :class_name => "Post"
|
||||
has_and_belongs_to_many :other_posts, :class_name => "Post"
|
||||
has_and_belongs_to_many :posts_with_authors_sorted_by_author_id, :class_name => "Post", :include => :authors, :order => "authors.id"
|
||||
|
||||
has_and_belongs_to_many(:select_testing_posts,
|
||||
:class_name => 'Post',
|
||||
|
||||
@@ -46,11 +46,14 @@ class Firm < Company
|
||||
has_many :clients_using_finder_sql, :class_name => "Client", :finder_sql => 'SELECT * FROM companies WHERE 1=1'
|
||||
has_many :plain_clients, :class_name => 'Client'
|
||||
has_many :readonly_clients, :class_name => 'Client', :readonly => true
|
||||
has_many :clients_using_primary_key, :class_name => 'Client',
|
||||
:primary_key => 'name', :foreign_key => 'firm_name'
|
||||
|
||||
has_one :account, :foreign_key => "firm_id", :dependent => :destroy, :validate => true
|
||||
has_one :unvalidated_account, :foreign_key => "firm_id", :class_name => 'Account', :validate => false
|
||||
has_one :account_with_select, :foreign_key => "firm_id", :select => "id, firm_id", :class_name=>'Account'
|
||||
has_one :readonly_account, :foreign_key => "firm_id", :class_name => "Account", :readonly => true
|
||||
has_one :account_using_primary_key, :primary_key => "firm_id", :class_name => "Account"
|
||||
end
|
||||
|
||||
class DependentFirm < Company
|
||||
|
||||
@@ -6,5 +6,5 @@ class Person < ActiveRecord::Base
|
||||
has_many :references
|
||||
has_many :jobs, :through => :references
|
||||
has_one :favourite_reference, :class_name => 'Reference', :conditions => ['favourite=?', true]
|
||||
|
||||
has_many :posts_with_comments_sorted_by_comment_id, :through => :readers, :source => :post, :include => :comments, :order => 'comments.id'
|
||||
end
|
||||
|
||||
@@ -1,6 +1,11 @@
|
||||
class Post < ActiveRecord::Base
|
||||
named_scope :containing_the_letter_a, :conditions => "body LIKE '%a%'"
|
||||
|
||||
named_scope :with_authors_at_address, lambda { |address| {
|
||||
:conditions => [ 'authors.author_address_id = ?', address.id ],
|
||||
:joins => 'JOIN authors ON authors.id = posts.author_id'
|
||||
}
|
||||
}
|
||||
|
||||
belongs_to :author do
|
||||
def greeting
|
||||
"hello"
|
||||
@@ -28,6 +33,12 @@ class Post < ActiveRecord::Base
|
||||
has_and_belongs_to_many :categories
|
||||
has_and_belongs_to_many :special_categories, :join_table => "categories_posts", :association_foreign_key => 'category_id'
|
||||
|
||||
belongs_to :creatable_author, :class_name => 'Author', :accessible => true
|
||||
has_one :uncreatable_comment, :class_name => 'Comment', :accessible => false, :order => 'id desc'
|
||||
has_one :creatable_comment, :class_name => 'Comment', :accessible => true, :order => 'id desc'
|
||||
has_many :creatable_comments, :class_name => 'Comment', :accessible => true, :dependent => :destroy
|
||||
has_and_belongs_to_many :creatable_categories, :class_name => 'Category', :accessible => true
|
||||
|
||||
has_many :taggings, :as => :taggable
|
||||
has_many :tags, :through => :taggings do
|
||||
def add_joins_and_select
|
||||
|
||||
@@ -4,6 +4,10 @@ class Topic < ActiveRecord::Base
|
||||
{ :conditions => ['written_on < ?', time] }
|
||||
}
|
||||
named_scope :approved, :conditions => {:approved => true}
|
||||
named_scope :by_lifo, :conditions => {:author_name => 'lifo'}
|
||||
|
||||
named_scope :approved_as_hash_condition, :conditions => {:topics => {:approved => true}}
|
||||
named_scope 'approved_as_string', :conditions => {:approved => true}
|
||||
named_scope :replied, :conditions => ['replies_count > 0']
|
||||
named_scope :anonymous_extension do
|
||||
def one
|
||||
|
||||
@@ -66,6 +66,7 @@ ActiveRecord::Schema.define do
|
||||
create_table :categories, :force => true do |t|
|
||||
t.string :name, :null => false
|
||||
t.string :type
|
||||
t.integer :categorizations_count
|
||||
end
|
||||
|
||||
create_table :categories_posts, :force => true, :id => false do |t|
|
||||
@@ -102,6 +103,7 @@ ActiveRecord::Schema.define do
|
||||
t.string :type
|
||||
t.string :ruby_type
|
||||
t.integer :firm_id
|
||||
t.string :firm_name
|
||||
t.string :name
|
||||
t.integer :client_of
|
||||
t.integer :rating, :default => 1
|
||||
@@ -407,6 +409,13 @@ ActiveRecord::Schema.define do
|
||||
t.column :key, :string
|
||||
end
|
||||
|
||||
create_table :integer_limits, :force => true do |t|
|
||||
t.integer :"c_int_without_limit"
|
||||
(1..8).each do |i|
|
||||
t.integer :"c_int_#{i}", :limit => i
|
||||
end
|
||||
end
|
||||
|
||||
except 'SQLite' do
|
||||
# fk_test_has_fk should be before fk_test_has_pk
|
||||
create_table :fk_test_has_fk, :force => true do |t|
|
||||
|
||||
Reference in New Issue
Block a user