secondbase 0.5.0 → 0.6.0

Sign up to get free protection for your applications and to get access to all the features.
data/CHANGELOG.md ADDED
@@ -0,0 +1,8 @@
1
+ # CHANGELOG
2
+
3
+ ## 0.6
4
+
5
+ * This version of the gem ONLY SUPPORTS Rails 3.x. For 2.x support, check out the branch 'rails_2_3' (or version .5 of the gem)
6
+ * patched has_and_belongs_to_many associations, for secondbase models, so that ActiveRecord understands that the join table is in the secondbase.
7
+ * patched ActiveRecord::TestFixtures so that transactional fixture support is respected for the SecondBase.
8
+ * reorganized monkey patches to make it easier to work in fixes for different versions of rails.
data/Gemfile CHANGED
@@ -7,7 +7,7 @@ source "http://rubygems.org"
7
7
  # Include everything needed to run rake, tests, features, etc.
8
8
  group :development do
9
9
  gem "shoulda", ">= 0"
10
- gem "bundler", "~> 1.0.0"
11
- gem "jeweler", "~> 1.5.1"
10
+ gem "bundler", ">= 1.0.0"
11
+ gem "jeweler", "~> 1.8.2"
12
12
  gem "activerecord", "~> 3.0.0"
13
13
  end
data/Gemfile.lock CHANGED
@@ -16,11 +16,15 @@ GEM
16
16
  builder (2.1.2)
17
17
  git (1.2.5)
18
18
  i18n (0.4.1)
19
- jeweler (1.5.1)
20
- bundler (~> 1.0.0)
19
+ jeweler (1.8.4)
20
+ bundler (~> 1.0)
21
21
  git (>= 1.2.5)
22
22
  rake
23
- rake (0.8.7)
23
+ rdoc
24
+ json (1.7.5)
25
+ rake (0.9.2.2)
26
+ rdoc (3.12)
27
+ json (~> 1.4)
24
28
  shoulda (2.11.1)
25
29
  tzinfo (0.3.23)
26
30
 
@@ -29,6 +33,6 @@ PLATFORMS
29
33
 
30
34
  DEPENDENCIES
31
35
  activerecord (~> 3.0.0)
32
- bundler (~> 1.0.0)
33
- jeweler (~> 1.5.1)
36
+ bundler (>= 1.0.0)
37
+ jeweler (~> 1.8.2)
34
38
  shoulda
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.5.0
1
+ 0.6.0
data/lib/secondbase.rb CHANGED
@@ -1,9 +1,10 @@
1
1
  require 'active_record'
2
+ require 'secondbase/active_record/patches'
2
3
 
3
4
  module SecondBase
4
5
  CONNECTION_PREFIX = 'secondbase'
5
6
 
6
- require 'secondbase/railtie' if Rails::VERSION::MAJOR == 3
7
+ require 'secondbase/railtie'
7
8
  require 'secondbase/rake_method_chain'
8
9
 
9
10
  def self.do
@@ -0,0 +1,66 @@
1
+ module ActiveRecord
2
+ # = Active Record Has And Belongs To Many Association
3
+ module Associations
4
+ class HasAndBelongsToManyAssociation < AssociationCollection
5
+
6
+ # determines the appropriate engine for the join table's parent klass
7
+ def arel_engine
8
+ Arel::Sql::Engine.new(@reflection.klass.engine)
9
+ end
10
+
11
+ # This method is entirely replicated, except for line 25. We simply
12
+ # need to pass in the appropriate engine to Arel.
13
+ def insert_record(record, force = true, validate = true)
14
+ if record.new_record?
15
+ if force
16
+ record.save!
17
+ else
18
+ return false unless record.save(:validate => validate)
19
+ end
20
+ end
21
+
22
+ if @reflection.options[:insert_sql]
23
+ @owner.connection.insert(interpolate_and_sanitize_sql(@reflection.options[:insert_sql], record))
24
+ else
25
+ relation = Arel::Table.new(@reflection.options[:join_table], arel_engine)
26
+ timestamps = record_timestamp_columns(record)
27
+ timezone = record.send(:current_time_from_proper_timezone) if timestamps.any?
28
+
29
+ attributes = Hash[columns.map do |column|
30
+ name = column.name
31
+ value = case name.to_s
32
+ when @reflection.primary_key_name.to_s
33
+ @owner.id
34
+ when @reflection.association_foreign_key.to_s
35
+ record.id
36
+ when *timestamps
37
+ timezone
38
+ else
39
+ @owner.send(:quote_value, record[name], column) if record.has_attribute?(name)
40
+ end
41
+ [relation[name], value] unless value.nil?
42
+ end]
43
+
44
+ relation.insert(attributes)
45
+ end
46
+
47
+ return true
48
+ end
49
+
50
+ # This method is entirely replicated, except for line 57. We simply
51
+ # need to pass in the appropriate engine to Arel.
52
+ def delete_records(records)
53
+ if sql = @reflection.options[:delete_sql]
54
+ records.each { |record| @owner.connection.delete(interpolate_and_sanitize_sql(sql, record)) }
55
+ else
56
+
57
+ relation = Arel::Table.new(@reflection.options[:join_table], arel_engine)
58
+
59
+ relation.where(relation[@reflection.primary_key_name].eq(@owner.id).
60
+ and(relation[@reflection.association_foreign_key].in(records.map { |x| x.id }.compact))
61
+ ).delete
62
+ end
63
+ end
64
+ end
65
+ end
66
+ end
@@ -0,0 +1,13 @@
1
+ module ActiveRecord
2
+ class Base
3
+
4
+ # Arel is concerned with "engines". Normally the engine defaults to the primary
5
+ # connection (ActiveRecord::Base). This will let us easily override the engine
6
+ # when dealing with Seoncdbase models (deep in ActiveRecord code).
7
+ # Since SecondBase::Base inherits from ActiveRecord::Base, this will pass the
8
+ # right engine around.
9
+ def self.engine
10
+ self
11
+ end
12
+ end
13
+ end
@@ -1,5 +1,3 @@
1
- require 'secondbase/model'
2
-
3
1
  ###########################
4
2
  # Monkey patch Fixtures
5
3
  # Fixtures needs to load fixtures into the database defined by the parent class!
@@ -7,7 +5,7 @@ require 'secondbase/model'
7
5
  # I feel like the concepts here could be incorporated directly into Fixtures.
8
6
  # I mean, they shouldn't be so presumptions to think that every model lives in the
9
7
  # same database....
10
- class Fixtures
8
+ class Fixtures < (RUBY_VERSION < '1.9' ? YAML::Omap : Hash)
11
9
  def self.create_fixtures(fixtures_directory, table_names, class_names = {})
12
10
  table_names = [table_names].flatten.map { |n| n.to_s }
13
11
  table_names.each { |n| class_names[n.tr('/', '_').to_sym] = n.classify if n.include?('/') }
@@ -0,0 +1,13 @@
1
+ ####################
2
+ ## ActiveRecord patches for all versions of rails
3
+ require 'secondbase/active_record/base'
4
+
5
+
6
+ ####################
7
+ ## ActiveRecord patches for specific versions of rails
8
+ if Rails.env.test?
9
+ require 'secondbase/active_record/fixtures'
10
+ require 'secondbase/active_record/test_fixtures'
11
+ end
12
+
13
+ require 'secondbase/active_record/associations/has_and_belongs_to_many_association'
@@ -0,0 +1,32 @@
1
+ ## ActiveRecord::TestFixtures
2
+ ## Monkey patch active record's test_fixtures module to manage
3
+ ## transactions for the SecondBase
4
+ module ActiveRecord
5
+ module TestFixtures
6
+ alias_method :original_setup_fixtures, :setup_fixtures
7
+ alias_method :original_teardown_fixtures, :teardown_fixtures
8
+
9
+ def setup_fixtures
10
+ original_setup_fixtures
11
+ # start tx for secondbase, if required
12
+ # Load fixtures once and begin transaction.
13
+ if run_in_transaction?
14
+ SecondBase::Base.connection.increment_open_transactions
15
+ SecondBase::Base.connection.transaction_joinable = false
16
+ SecondBase::Base.connection.begin_db_transaction
17
+ end
18
+ end
19
+
20
+ def teardown_fixtures
21
+ original_teardown_fixtures
22
+
23
+ # Rollback secondbase changes if a transaction is active.
24
+ if run_in_transaction? && SecondBase::Base.connection.open_transactions != 0
25
+ SecondBase::Base.connection.rollback_db_transaction
26
+ SecondBase::Base.connection.decrement_open_transactions
27
+ end
28
+
29
+ SecondBase::Base.clear_active_connections!
30
+ end
31
+ end
32
+ end
@@ -2,10 +2,9 @@
2
2
  #
3
3
  # NOTE: By extending this model, you assume that the underlying table will be located in your Second (Data)base
4
4
  module SecondBase
5
- require 'active_record'
6
5
 
7
6
  class Base < ActiveRecord::Base
8
- establish_connection ActiveRecord::Base.configurations[CONNECTION_PREFIX][Rails.env]
7
+ establish_connection ActiveRecord::Base.configurations[SecondBase::CONNECTION_PREFIX][Rails.env]
9
8
 
10
9
  self.abstract_class = true
11
10
  end
data/secondbase.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{secondbase}
8
- s.version = "0.5.0"
8
+ s.version = "0.6.0"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["karledurante"]
12
- s.date = %q{2011-12-22}
12
+ s.date = %q{2012-08-31}
13
13
  s.description = %q{Secondbase provides support to Rails to create a homogeneous environment for a dual database project. Using the rake tasks already familiar to you, this gem enables Rails to work with two primary databases, instead of just one.}
14
14
  s.email = %q{kdurante@customink.com}
15
15
  s.extra_rdoc_files = [
@@ -18,6 +18,7 @@ Gem::Specification.new do |s|
18
18
  ]
19
19
  s.files = [
20
20
  ".document",
21
+ "CHANGELOG.md",
21
22
  "Gemfile",
22
23
  "Gemfile.lock",
23
24
  "LICENSE.txt",
@@ -28,7 +29,11 @@ Gem::Specification.new do |s|
28
29
  "lib/generators/secondbase/migration_generator.rb",
29
30
  "lib/generators/secondbase/templates/migration.rb",
30
31
  "lib/secondbase.rb",
31
- "lib/secondbase/fixtures.rb",
32
+ "lib/secondbase/active_record/associations/has_and_belongs_to_many_association.rb",
33
+ "lib/secondbase/active_record/base.rb",
34
+ "lib/secondbase/active_record/fixtures.rb",
35
+ "lib/secondbase/active_record/patches.rb",
36
+ "lib/secondbase/active_record/test_fixtures.rb",
32
37
  "lib/secondbase/model.rb",
33
38
  "lib/secondbase/railtie.rb",
34
39
  "lib/secondbase/rake_method_chain.rb",
@@ -45,31 +50,27 @@ Gem::Specification.new do |s|
45
50
  s.require_paths = ["lib"]
46
51
  s.rubygems_version = %q{1.4.2}
47
52
  s.summary = %q{Allow Rails manage second database in your projects}
48
- s.test_files = [
49
- "test/helper.rb",
50
- "test/test_secondbase.rb"
51
- ]
52
53
 
53
54
  if s.respond_to? :specification_version then
54
55
  s.specification_version = 3
55
56
 
56
57
  if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
57
58
  s.add_development_dependency(%q<shoulda>, [">= 0"])
58
- s.add_development_dependency(%q<bundler>, ["~> 1.0.0"])
59
- s.add_development_dependency(%q<jeweler>, ["~> 1.5.1"])
59
+ s.add_development_dependency(%q<bundler>, [">= 1.0.0"])
60
+ s.add_development_dependency(%q<jeweler>, ["~> 1.8.2"])
60
61
  s.add_development_dependency(%q<activerecord>, ["~> 3.0.0"])
61
62
  s.add_development_dependency(%q<activerecord>, ["~> 3.0.0"])
62
63
  else
63
64
  s.add_dependency(%q<shoulda>, [">= 0"])
64
- s.add_dependency(%q<bundler>, ["~> 1.0.0"])
65
- s.add_dependency(%q<jeweler>, ["~> 1.5.1"])
65
+ s.add_dependency(%q<bundler>, [">= 1.0.0"])
66
+ s.add_dependency(%q<jeweler>, ["~> 1.8.2"])
66
67
  s.add_dependency(%q<activerecord>, ["~> 3.0.0"])
67
68
  s.add_dependency(%q<activerecord>, ["~> 3.0.0"])
68
69
  end
69
70
  else
70
71
  s.add_dependency(%q<shoulda>, [">= 0"])
71
- s.add_dependency(%q<bundler>, ["~> 1.0.0"])
72
- s.add_dependency(%q<jeweler>, ["~> 1.5.1"])
72
+ s.add_dependency(%q<bundler>, [">= 1.0.0"])
73
+ s.add_dependency(%q<jeweler>, ["~> 1.8.2"])
73
74
  s.add_dependency(%q<activerecord>, ["~> 3.0.0"])
74
75
  s.add_dependency(%q<activerecord>, ["~> 3.0.0"])
75
76
  end
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: secondbase
3
3
  version: !ruby/object:Gem::Version
4
- hash: 11
4
+ hash: 7
5
5
  prerelease:
6
6
  segments:
7
7
  - 0
8
- - 5
8
+ - 6
9
9
  - 0
10
- version: 0.5.0
10
+ version: 0.6.0
11
11
  platform: ruby
12
12
  authors:
13
13
  - karledurante
@@ -15,11 +15,11 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2011-12-22 00:00:00 -05:00
18
+ date: 2012-08-31 00:00:00 -04:00
19
19
  default_executable:
20
20
  dependencies:
21
21
  - !ruby/object:Gem::Dependency
22
- type: :development
22
+ prerelease: false
23
23
  version_requirements: &id001 !ruby/object:Gem::Requirement
24
24
  none: false
25
25
  requirements:
@@ -30,14 +30,14 @@ dependencies:
30
30
  - 0
31
31
  version: "0"
32
32
  requirement: *id001
33
- prerelease: false
33
+ type: :development
34
34
  name: shoulda
35
35
  - !ruby/object:Gem::Dependency
36
- type: :development
36
+ prerelease: false
37
37
  version_requirements: &id002 !ruby/object:Gem::Requirement
38
38
  none: false
39
39
  requirements:
40
- - - ~>
40
+ - - ">="
41
41
  - !ruby/object:Gem::Version
42
42
  hash: 23
43
43
  segments:
@@ -46,26 +46,26 @@ dependencies:
46
46
  - 0
47
47
  version: 1.0.0
48
48
  requirement: *id002
49
- prerelease: false
49
+ type: :development
50
50
  name: bundler
51
51
  - !ruby/object:Gem::Dependency
52
- type: :development
52
+ prerelease: false
53
53
  version_requirements: &id003 !ruby/object:Gem::Requirement
54
54
  none: false
55
55
  requirements:
56
56
  - - ~>
57
57
  - !ruby/object:Gem::Version
58
- hash: 1
58
+ hash: 51
59
59
  segments:
60
60
  - 1
61
- - 5
62
- - 1
63
- version: 1.5.1
61
+ - 8
62
+ - 2
63
+ version: 1.8.2
64
64
  requirement: *id003
65
- prerelease: false
65
+ type: :development
66
66
  name: jeweler
67
67
  - !ruby/object:Gem::Dependency
68
- type: :development
68
+ prerelease: false
69
69
  version_requirements: &id004 !ruby/object:Gem::Requirement
70
70
  none: false
71
71
  requirements:
@@ -78,10 +78,10 @@ dependencies:
78
78
  - 0
79
79
  version: 3.0.0
80
80
  requirement: *id004
81
- prerelease: false
81
+ type: :development
82
82
  name: activerecord
83
83
  - !ruby/object:Gem::Dependency
84
- type: :development
84
+ prerelease: false
85
85
  version_requirements: &id005 !ruby/object:Gem::Requirement
86
86
  none: false
87
87
  requirements:
@@ -94,7 +94,7 @@ dependencies:
94
94
  - 0
95
95
  version: 3.0.0
96
96
  requirement: *id005
97
- prerelease: false
97
+ type: :development
98
98
  name: activerecord
99
99
  description: Secondbase provides support to Rails to create a homogeneous environment for a dual database project. Using the rake tasks already familiar to you, this gem enables Rails to work with two primary databases, instead of just one.
100
100
  email: kdurante@customink.com
@@ -107,6 +107,7 @@ extra_rdoc_files:
107
107
  - README.rdoc
108
108
  files:
109
109
  - .document
110
+ - CHANGELOG.md
110
111
  - Gemfile
111
112
  - Gemfile.lock
112
113
  - LICENSE.txt
@@ -117,7 +118,11 @@ files:
117
118
  - lib/generators/secondbase/migration_generator.rb
118
119
  - lib/generators/secondbase/templates/migration.rb
119
120
  - lib/secondbase.rb
120
- - lib/secondbase/fixtures.rb
121
+ - lib/secondbase/active_record/associations/has_and_belongs_to_many_association.rb
122
+ - lib/secondbase/active_record/base.rb
123
+ - lib/secondbase/active_record/fixtures.rb
124
+ - lib/secondbase/active_record/patches.rb
125
+ - lib/secondbase/active_record/test_fixtures.rb
121
126
  - lib/secondbase/model.rb
122
127
  - lib/secondbase/railtie.rb
123
128
  - lib/secondbase/rake_method_chain.rb
@@ -162,6 +167,5 @@ rubygems_version: 1.4.2
162
167
  signing_key:
163
168
  specification_version: 3
164
169
  summary: Allow Rails manage second database in your projects
165
- test_files:
166
- - test/helper.rb
167
- - test/test_secondbase.rb
170
+ test_files: []
171
+