adaptive_alias 0.1.0 → 0.2.2

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 81757ab8f4098990940d499ee2286c8c831fdac6462dfcafcd59b868ff596ec2
4
- data.tar.gz: b88816e4745352dc63fb29a4d102a52935538bd0f5ef5591f8ce56e9057dc9d5
3
+ metadata.gz: 53def64d14130ef1552a0a427246706ce42fb8696dfba356c323adcef3c39f97
4
+ data.tar.gz: 7c6b4ed35d6a0c90d06b09368b1f0c1617abfffac05f153015f3a4a8878ec6a5
5
5
  SHA512:
6
- metadata.gz: 60cb4e6e2f31787f93f6edf5415bd3fbe283999c50d0fba89d9e48e055a5c06ca7479ee8a158ec4618453352bc8034a18e9acbafae5905f4e4f2a7a0ee8ba54f
7
- data.tar.gz: e80d6cdd3e41254d07e70e4440bc120b6940bfddb31f54709e97becafc18dd4eef2341832fc049d750e247e002a8097f4d9128697de0f657c8fdd1b47310d103
6
+ metadata.gz: 9c8b4ec7ad1588f922bf0af037061216699a056c023ea70975796c66dafd57cf254c5d4915a98cfa7e1b9836b53f61ca2961ea0b9aa399e2fe7dc55510192d23
7
+ data.tar.gz: c6a532d2f341729637a7ca9630fe1338ddeb5b553cc0ea897e6cb784d18adbd47db21254df82746a06e915c57a2f2567227436a9562eac21cb150174be16d5e7
data/CHANGELOG.md CHANGED
@@ -1,10 +1,26 @@
1
1
  ## Change Log
2
2
 
3
+ ### [v0.2.1](https://github.com/khiav223577/adaptive_alias/compare/v0.2.0...v0.2.1) 2022/08/11
4
+ - [#13](https://github.com/khiav223577/adaptive_alias/pull/13) [Fix] Nested module include is not supported until ruby 3.0 (@khiav223577)
5
+ - [#12](https://github.com/khiav223577/adaptive_alias/pull/12) [Test] Add test cases to test column_names (@khiav223577)
6
+
7
+ ### [v0.2.0](https://github.com/khiav223577/adaptive_alias/compare/v0.1.0...v0.2.0) 2022/08/05
8
+ - [#11](https://github.com/khiav223577/adaptive_alias/pull/11) [Feature] Support polymorphic (@khiav223577)
9
+ - [#10](https://github.com/khiav223577/adaptive_alias/pull/10) [Enhance] Prevent adding methods directly in class / module (@khiav223577)
10
+ - [#9](https://github.com/khiav223577/adaptive_alias/pull/9) [Enhance] Prevent changing original order of where conditions (@khiav223577)
11
+ - [#8](https://github.com/khiav223577/adaptive_alias/pull/8) [Test] Make sure we are reset to use original patch when some test cases fail (@khiav223577)
12
+ - [#7](https://github.com/khiav223577/adaptive_alias/pull/7) [Test] Add test cases to test destroy (@khiav223577)
13
+
14
+ ### [v0.1.0](https://github.com/khiav223577/adaptive_alias/compare/v0.0.3...v0.1.0) 2022/08/01
15
+ - [#6](https://github.com/khiav223577/adaptive_alias/pull/6) [Feature] Deal with creating records (@khiav223577)
16
+ - [#5](https://github.com/khiav223577/adaptive_alias/pull/5) [Enhance] Prevent infinite loop if something went wrong (@khiav223577)
17
+ - [#4](https://github.com/khiav223577/adaptive_alias/pull/4) [Fix] Attributes writer method should be defined after schema changes (@khiav223577)
18
+
3
19
  ### [v0.0.3](https://github.com/khiav223577/adaptive_alias/compare/v0.0.2...v0.0.3) 2022/07/27
4
- - [#3](https://github.com/khiav223577/adaptive_alias/pull/3) Fix: prevent calling custom column names from raising missing attributes (@khiav223577)
20
+ - [#3](https://github.com/khiav223577/adaptive_alias/pull/3) [Fix] Prevent calling custom column names from raising missing attributes (@khiav223577)
5
21
 
6
22
  ### [v0.0.2](https://github.com/khiav223577/adaptive_alias/compare/v0.0.1...v0.0.2) 2022/07/26
7
- - [#2](https://github.com/khiav223577/adaptive_alias/pull/2) Doesn't need rails_compatibility in runtime (@khiav223577)
23
+ - [#2](https://github.com/khiav223577/adaptive_alias/pull/2) [Enhance] Doesn't need rails_compatibility in runtime (@khiav223577)
8
24
 
9
25
  ### v0.0.1 2022/07/22
10
- - [#1](https://github.com/khiav223577/adaptive_alias/pull/1) Implement adaptive_alias features (@khiav223577)
26
+ - [#1](https://github.com/khiav223577/adaptive_alias/pull/1) [Feature] Implement adaptive_alias features (@khiav223577)
@@ -0,0 +1,17 @@
1
+ require 'active_record'
2
+
3
+ module AdaptiveAlias
4
+ module ActiveModelPatches
5
+ module ApplyScope
6
+ def apply_scope(scope, table, key, value)
7
+ klass = table.instance_variable_get(:@klass) || table.send(:type_caster).send(:types)
8
+ key = klass.attribute_aliases[key] || key
9
+ super(scope, table, key, value)
10
+ end
11
+ end
12
+ end
13
+ end
14
+
15
+ class ActiveRecord::Associations::AssociationScope
16
+ prepend AdaptiveAlias::ActiveModelPatches::ApplyScope
17
+ end
@@ -1,22 +1,31 @@
1
1
  require 'active_record'
2
2
 
3
- module ActiveRecord::AttributeMethods::Read
4
- def read_attribute(attr_name, &block) # :nodoc:
5
- name = attr_name.to_s
6
- name = self.class.attribute_aliases[name] || name
3
+ module AdaptiveAlias
4
+ module ActiveModelPatches
5
+ module ReadAttribute
6
+ def read_attribute(attr_name, &block) # :nodoc:
7
+ name = attr_name.to_s
8
+ name = self.class.attribute_aliases[name] || name
7
9
 
8
- name = @primary_key if name == 'id' && @primary_key
9
- _read_attribute(name, &block)
10
- end
10
+ name = @primary_key if name == 'id' && @primary_key
11
+ _read_attribute(name, &block)
12
+ end
11
13
 
12
- # This method exists to avoid the expensive primary_key check internally, without
13
- # breaking compatibility with the write_attribute API
14
- def _read_attribute(attr_name, &block) # :nodoc:
15
- name = attr_name.to_s
16
- name = self.class.attribute_aliases[name] || name
14
+ # This method exists to avoid the expensive primary_key check internally, without
15
+ # breaking compatibility with the write_attribute API
16
+ def _read_attribute(attr_name, &block) # :nodoc:
17
+ name = attr_name.to_s
18
+ name = self.class.attribute_aliases[name] || name
17
19
 
18
- sync_with_transaction_state if @transaction_state&.finalized?
19
- return yield(name) if block_given? and AdaptiveAlias.missing_value?(@attributes, self.class, name)
20
- return @attributes.fetch_value(name, &block)
20
+ sync_with_transaction_state if @transaction_state&.finalized?
21
+ return yield(name) if block_given? and AdaptiveAlias.missing_value?(@attributes, self.class, name)
22
+ return @attributes.fetch_value(name, &block)
23
+ end
24
+ end
21
25
  end
22
26
  end
27
+
28
+ # Nested module include is not supported until ruby 3.0
29
+ class ActiveRecord::Base
30
+ prepend AdaptiveAlias::ActiveModelPatches::ReadAttribute
31
+ end
@@ -1,18 +1,31 @@
1
1
  require 'active_model'
2
2
 
3
- module ActiveModel::AttributeMethods
4
- module ClassMethods
5
- def remove_proxy_call(mod, name)
6
- mod.module_eval "remove_method(:'#{name}')", __FILE__, __LINE__ + 1
7
- end
3
+ module AdaptiveAlias
4
+ module ActiveModelPatches
5
+ module RemoveAliasAttribute
6
+ def remove_proxy_call(mod, name)
7
+ mod.module_eval "remove_method(:'#{name}')", __FILE__, __LINE__ + 1
8
+ end
8
9
 
9
- def remove_alias_attribute(new_name)
10
- self.attribute_aliases = attribute_aliases.except(new_name.to_s)
10
+ def remove_alias_attribute(new_name)
11
+ self.attribute_aliases = attribute_aliases.except(new_name.to_s)
11
12
 
12
- attribute_method_matchers.each do |matcher|
13
- matcher_new = matcher.method_name(new_name).to_s
14
- remove_proxy_call self, matcher_new
13
+ attribute_method_matchers.each do |matcher|
14
+ matcher_new = matcher.method_name(new_name).to_s
15
+ remove_proxy_call self, matcher_new
16
+ end
15
17
  end
16
18
  end
17
19
  end
18
20
  end
21
+
22
+ # Nested module include is not supported until ruby 3.0
23
+ if Gem::Version.new(RUBY_VERSION) < Gem::Version.new('3')
24
+ AdaptiveAlias::ActiveModelPatches::RemoveAliasAttribute.instance_methods.each do |method|
25
+ ActiveModel::AttributeMethods::ClassMethods.define_method(method, AdaptiveAlias::ActiveModelPatches::RemoveAliasAttribute.instance_method(method))
26
+ end
27
+ else
28
+ module ActiveModel::AttributeMethods::ClassMethods
29
+ include AdaptiveAlias::ActiveModelPatches::RemoveAliasAttribute
30
+ end
31
+ end
@@ -1,22 +1,25 @@
1
1
  require 'active_record'
2
2
 
3
- module ActiveRecord::AttributeMethods::Write
4
- def write_attribute(attr_name, value)
5
- name = attr_name.to_s
6
- name = self.class.attribute_aliases[name] || name
3
+ module AdaptiveAlias
4
+ module ActiveModelPatches
5
+ module WriteAttribute
6
+ def write_attribute(attr_name, value)
7
+ name = attr_name.to_s
8
+ name = self.class.attribute_aliases[name] || name
9
+ super(name, value)
10
+ end
7
11
 
8
- name = @primary_key if name == 'id' && @primary_key
9
- _write_attribute(name, value)
12
+ # This method exists to avoid the expensive primary_key check internally, without
13
+ # breaking compatibility with the write_attribute API
14
+ def _write_attribute(attr_name, value) # :nodoc:
15
+ name = attr_name.to_s
16
+ name = self.class.attribute_aliases[name] || name
17
+ super(name, value)
18
+ end
19
+ end
10
20
  end
21
+ end
11
22
 
12
- # This method exists to avoid the expensive primary_key check internally, without
13
- # breaking compatibility with the write_attribute API
14
- def _write_attribute(attr_name, value) # :nodoc:
15
- name = attr_name.to_s
16
- name = self.class.attribute_aliases[name] || name
17
-
18
- sync_with_transaction_state if @transaction_state&.finalized?
19
- @attributes.write_from_user(name, value)
20
- value
21
- end
23
+ class ActiveRecord::Base
24
+ prepend AdaptiveAlias::ActiveModelPatches::WriteAttribute
22
25
  end
@@ -2,11 +2,11 @@ module AdaptiveAlias
2
2
  module Hooks
3
3
  module Association
4
4
  def find_target(*)
5
- AdaptiveAlias.rescue_statement_invalid(nil){ super }
5
+ AdaptiveAlias.rescue_statement_invalid(nil, reflection){ super }
6
6
  end
7
7
 
8
8
  def create!(attributes = {}, &block)
9
- AdaptiveAlias.rescue_statement_invalid(association_scope){ super }
9
+ AdaptiveAlias.rescue_statement_invalid(association_scope, reflection){ super }
10
10
  end
11
11
  end
12
12
  end
@@ -2,15 +2,15 @@ module AdaptiveAlias
2
2
  module Hooks
3
3
  module Relation
4
4
  def pluck(*)
5
- AdaptiveAlias.rescue_statement_invalid(self){ super }
5
+ AdaptiveAlias.rescue_statement_invalid(self, nil){ super }
6
6
  end
7
7
 
8
8
  def select_all(*)
9
- AdaptiveAlias.rescue_statement_invalid(self){ super }
9
+ AdaptiveAlias.rescue_statement_invalid(self, nil){ super }
10
10
  end
11
11
 
12
12
  def exec_queries(*)
13
- AdaptiveAlias.rescue_statement_invalid(self){ super }
13
+ AdaptiveAlias.rescue_statement_invalid(self, nil){ super }
14
14
  end
15
15
  end
16
16
  end
@@ -15,7 +15,9 @@ module AdaptiveAlias
15
15
  super
16
16
  @klass.remove_alias_attribute(@old_column)
17
17
  @klass.define_attribute_method(@old_column)
18
- ForwardPatch.new(@klass, @old_column, @new_column).apply!
18
+ new_patch = ForwardPatch.new(@klass, @old_column, @new_column)
19
+ new_patch.apply!
20
+ return new_patch
19
21
  end
20
22
  end
21
23
  end
@@ -46,6 +46,9 @@ module AdaptiveAlias
46
46
 
47
47
  expected_association_err_msgs = [
48
48
  "Mysql2::Error: Unknown column '#{klass.table_name}.#{current_column}' in 'where clause'".freeze,
49
+ ].freeze
50
+
51
+ expected_ambiguous_association_err_msgs = [
49
52
  "Mysql2::Error: Unknown column '#{current_column}' in 'field list'".freeze,
50
53
  ].freeze
51
54
 
@@ -64,21 +67,33 @@ module AdaptiveAlias
64
67
  next true
65
68
  end
66
69
 
67
- @fix_association = proc do |target, error|
70
+ @fix_association = proc do |relation, reflection, error|
68
71
  next false if not patch.removable
69
72
  next false if patch.removed
70
- next false if not expected_association_err_msgs.include?(error.message)
73
+
74
+ ambiguous = expected_ambiguous_association_err_msgs.include?(error.message)
75
+
76
+ if ambiguous
77
+ next false if relation and klass != relation.klass
78
+ next false if reflection and klass != reflection.klass
79
+ end
80
+
81
+ next false if not expected_association_err_msgs.include?(error.message) and not ambiguous
71
82
 
72
83
  patch.remove!
73
84
 
74
- if target
75
- hash = target.where_values_hash
76
- hash[alias_column] = hash.delete(current_column) if hash.key?(current_column)
77
- hash[alias_column.to_s] = hash.delete(current_column.to_s) if hash.key?(current_column.to_s)
78
- target.instance_variable_set(:@arel, nil)
79
- target.unscope!(:where).where!(hash)
85
+ if relation
86
+ relation.where_clause.send(:predicates).each do |node|
87
+ next if node.left.name != current_column.to_s
88
+ next if klass.table_name != node.left.relation.name
89
+
90
+ node.left = node.left.clone
91
+ node.left.name = alias_column.to_s
92
+ end
80
93
  end
81
94
 
95
+ reflection.clear_association_scope_cache if reflection
96
+
82
97
  next true
83
98
  end
84
99
  end
@@ -15,7 +15,9 @@ module AdaptiveAlias
15
15
  super
16
16
  @klass.remove_alias_attribute(@new_column)
17
17
  @klass.define_attribute_method(@new_column)
18
- BackwardPatch.new(@klass, @old_column, @new_column).apply!
18
+ new_patch = BackwardPatch.new(@klass, @old_column, @new_column)
19
+ new_patch.apply!
20
+ return new_patch
19
21
  end
20
22
  end
21
23
  end
@@ -1,3 +1,3 @@
1
1
  module AdaptiveAlias
2
- VERSION = '0.1.0'
2
+ VERSION = '0.2.2'
3
3
  end
@@ -4,6 +4,7 @@ require 'adaptive_alias/version'
4
4
  require 'adaptive_alias/active_model_patches/read_attribute'
5
5
  require 'adaptive_alias/active_model_patches/write_attribute'
6
6
  require 'adaptive_alias/active_model_patches/remove_alias_attribute'
7
+ require 'adaptive_alias/active_model_patches/apply_scope'
7
8
  require 'adaptive_alias/patches/backward_patch'
8
9
  require 'adaptive_alias/patches/forward_patch'
9
10
 
@@ -32,19 +33,19 @@ module AdaptiveAlias
32
33
  extend ActiveSupport::Concern
33
34
 
34
35
  included do
35
- patch = (column_names.include?(new_column) ? Patches::BackwardPatch : Patches::ForwardPatch).new(self, old_column, new_column)
36
+ patch = (column_names.include?(new_column.to_s) ? Patches::BackwardPatch : Patches::ForwardPatch).new(self, old_column, new_column)
36
37
  patch.apply!
37
38
  patch.mark_removable
38
39
  end
39
40
  end
40
41
  end
41
42
 
42
- def rescue_statement_invalid(relation, &block)
43
+ def rescue_statement_invalid(relation, reflection, &block)
43
44
  yield
44
45
  rescue ActiveRecord::StatementInvalid => error
45
- raise error if AdaptiveAlias.current_patches.all?{|_key, patch| !patch.fix_association.call(relation, error) }
46
+ raise error if AdaptiveAlias.current_patches.all?{|_key, patch| !patch.fix_association.call(relation, reflection, error) }
46
47
 
47
- result = rescue_statement_invalid(relation, &block)
48
+ result = rescue_statement_invalid(relation, reflection, &block)
48
49
  AdaptiveAlias.current_patches.each_value(&:mark_removable)
49
50
  return result
50
51
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: adaptive_alias
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 0.2.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - khiav reoy
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2022-08-01 00:00:00.000000000 Z
11
+ date: 2022-08-11 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -123,6 +123,7 @@ files:
123
123
  - gemfiles/6.1.gemfile
124
124
  - gemfiles/7.0.gemfile
125
125
  - lib/adaptive_alias.rb
126
+ - lib/adaptive_alias/active_model_patches/apply_scope.rb
126
127
  - lib/adaptive_alias/active_model_patches/read_attribute.rb
127
128
  - lib/adaptive_alias/active_model_patches/remove_alias_attribute.rb
128
129
  - lib/adaptive_alias/active_model_patches/write_attribute.rb