arel-extensions 6.0.0 → 6.0.0.8

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: a2e57daa4864ca189927f6f4197009f057ce83d6cc4a1f12d7fd12e20a63ac68
4
- data.tar.gz: 39d7ab6d734005b482dd04f1e03c1e8b71b5a463d2c35b9cec3a71d46bf84b20
3
+ metadata.gz: 87c1e3d344cef64601be578c9efa5e05ca8a0fb2a0443cb81f586c06a3e1009f
4
+ data.tar.gz: 361a92b9257df496481556ccb63f78e399168dc021a5461f5a3b5b4e324a401e
5
5
  SHA512:
6
- metadata.gz: 4fbf0b2cdd5c76f856b027495b46ca5084dbadd5e1e0a5bcad2ab62de4fa0915a1453ee63ee35b4de397aa9fd1cdc214d10a2586025be6656cc985ed43468996
7
- data.tar.gz: d438b922e697b704c58a22734b647c7027defbf53cce02502ec52a3753fe8417cdf17976e1e956bc7c1e63eb7be0c7b2e8dbc4d5ca87ccd4cf4d1ce805567a03
6
+ metadata.gz: 4e83c72da829bf31e4113d777f4cede440c1ecb8d3ad7c552225978788956af72030c669b782aa935cc4945990bb02449c224e582643ed8e88694d4b439a1995
7
+ data.tar.gz: ade28f1b9fad88a81eeeb0d25a7a3608900c802858f0579a9f0713dd68a655433ce2c2f4504939c83600db20e77e4a28995feb2bd0db2573772c4ba762f00372
data/.gitignore CHANGED
@@ -1 +1,3 @@
1
1
  .DS_Store
2
+ *.gem
3
+ Gemfile.lock
@@ -8,14 +8,13 @@ cache:
8
8
  - /home/travis/.rvm/gems
9
9
 
10
10
  rvm:
11
- - 2.5
12
11
  - 2.6
13
12
 
14
13
  env:
15
14
  matrix:
16
- - RAILS_VERSION=v6.0.0.rc1 GEM=activerecord:mysql2
17
- - RAILS_VERSION=v6.0.0.rc1 GEM=activerecord:sqlite3
18
- - RAILS_VERSION=v6.0.0.rc1 GEM=activerecord:postgresql
15
+ - RAILS_VERSION=v6.0.3.1 GEM=activerecord:mysql2
16
+ - RAILS_VERSION=v6.0.3.1 GEM=activerecord:sqlite3
17
+ - RAILS_VERSION=v6.0.3.1 GEM=activerecord:postgresql
19
18
 
20
19
  services:
21
20
  - mysql
@@ -26,6 +25,7 @@ before_install:
26
25
  - unset BUNDLE_GEMFILE
27
26
  - gem update --system
28
27
  - gem update bundler
28
+ - gem install bundler -v 1.17.3
29
29
 
30
30
  install:
31
31
  - git clone https://github.com/rails/rails.git ~/build/rails
@@ -37,7 +37,7 @@ install:
37
37
  - "sed -i \"/group :db do/a gem 'arel-extensions', require: 'arel/extensions', path: File.expand_path\\('~\\/build\\/malomalo\\/arel-extensions'\\)\" ~/build/rails/Gemfile"
38
38
  - sed -i "/rb-inotify/d" ~/build/rails/Gemfile
39
39
  - cat ~/build/rails/Gemfile
40
- - bundle install --jobs=3 --retry=3
40
+ - bundle install --jobs=3 --retry=3 --full-index
41
41
  - popd
42
42
 
43
43
  script:
@@ -1,7 +1,6 @@
1
1
  Gem::Specification.new do |gem|
2
2
  gem.name = 'arel-extensions'
3
- gem.version = '6.0.0'
4
-
3
+ gem.version = '6.0.0.8'
5
4
  gem.authors = ["Jon Bracy"]
6
5
  gem.email = ["jonbracy@gmail.com"]
7
6
  gem.summary = %q{Adds support for missing SQL operators and functions to Arel}
@@ -12,12 +11,14 @@ Gem::Specification.new do |gem|
12
11
  gem.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
13
12
  gem.require_paths = ["lib"]
14
13
 
15
- gem.add_dependency 'activerecord', '>= 6.0.0.rc1'
14
+ gem.add_dependency 'activerecord', '>= 6.0.0'
16
15
 
17
16
  gem.add_development_dependency "bundler"
18
17
  gem.add_development_dependency "rake"
19
18
  gem.add_development_dependency 'minitest'
20
19
  gem.add_development_dependency 'minitest-reporters'
20
+ gem.add_development_dependency "sunstone"
21
+ gem.add_development_dependency "webmock"
21
22
  gem.add_development_dependency 'pg'
22
23
  gem.add_development_dependency 'rgeo'
23
24
 
@@ -0,0 +1,14 @@
1
+ module Arel
2
+ module Nodes
3
+ class Ascending < Ordering
4
+
5
+ attr_accessor :nulls
6
+
7
+ def initialize expr, nulls=nil
8
+ super(expr)
9
+ @nulls = nulls
10
+ end
11
+
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,15 @@
1
+ module Arel
2
+ module Nodes
3
+ class Descending < Ordering
4
+
5
+ attr_accessor :nulls
6
+
7
+ def initialize expr, nulls=nil
8
+ super(expr)
9
+ @nulls = nulls
10
+ end
11
+
12
+ end
13
+
14
+ end
15
+ end
@@ -0,0 +1,14 @@
1
+ # Ordering with :nulls_last, :nulls_first options
2
+ module Arel
3
+ module OrderPredications
4
+
5
+ def asc(nulls=nil)
6
+ Nodes::Ascending.new self, nulls
7
+ end
8
+
9
+ def desc(nulls=nil)
10
+ Nodes::Descending.new self, nulls
11
+ end
12
+
13
+ end
14
+ end
@@ -9,6 +9,11 @@ require File.expand_path('../nodes/contained_by', __FILE__)
9
9
  require File.expand_path('../array_predications', __FILE__)
10
10
  Arel::Attributes::Attribute.include(Arel::ArrayPredications)
11
11
 
12
+ require File.expand_path('../nodes/random', __FILE__)
13
+ require File.expand_path(File.join(__FILE__, '../../../ext/arel/nodes/ascending'))
14
+ require File.expand_path(File.join(__FILE__, '../../../ext/arel/nodes/descending'))
15
+ require File.expand_path(File.join(__FILE__, '../../../ext/arel/order_predications'))
16
+
12
17
 
13
18
  require File.expand_path('../attributes/key', __FILE__)
14
19
  require File.expand_path('../attributes/cast', __FILE__)
@@ -26,6 +31,7 @@ require File.expand_path('../nodes/ts_rank_cd', __FILE__)
26
31
  require File.expand_path('../ts_predications', __FILE__)
27
32
  Arel::Attributes::Attribute.include(Arel::TSPredications)
28
33
 
34
+ require File.expand_path('../nodes/relation', __FILE__)
29
35
 
30
36
  require File.expand_path('../gis_predications', __FILE__)
31
37
  Arel::Attributes::Attribute.include(Arel::GISPredications)
@@ -38,4 +44,8 @@ end
38
44
 
39
45
  if defined?(Arel::Visitors::Sunstone)
40
46
  require File.expand_path('../visitors/sunstone_extensions', __FILE__)
47
+ end
48
+
49
+ if defined?(Arel::Visitors::ToSql)
50
+ require File.expand_path('../visitors/to_sql_extensions', __FILE__)
41
51
  end
@@ -0,0 +1,7 @@
1
+ module Arel
2
+ module Nodes
3
+ class RandomOrdering < Arel::Nodes::Node
4
+
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,35 @@
1
+ module Arel
2
+ module Attributes
3
+ class Relation < Attribute
4
+
5
+ attr_accessor :collection, :for_write
6
+
7
+ def initialize(relation, name, collection = false, for_write=false)
8
+ self[:relation] = relation
9
+ self[:name] = name
10
+ @collection = collection
11
+ @for_write = for_write
12
+ end
13
+
14
+ def able_to_type_cast?
15
+ false
16
+ end
17
+
18
+ def table_name
19
+ nil
20
+ end
21
+
22
+ def eql? other
23
+ self.class == other.class &&
24
+ self.relation == other.relation &&
25
+ self.name == other.name &&
26
+ self.collection == other.collection
27
+ end
28
+
29
+ def type_cast_for_database(value)
30
+ relation.type_cast_for_database(value)
31
+ end
32
+
33
+ end
34
+ end
35
+ end
@@ -2,11 +2,11 @@ module Arel
2
2
  module TSPredications
3
3
 
4
4
  def ts_query(expression, language=nil)
5
- vector = Arel::Nodes::TSVector.new(self, language)
6
- query = Arel::Nodes::TSQuery.new(expression, language)
5
+ vector = Arel::Nodes::TSVector.new(self, language: language)
6
+ query = Arel::Nodes::TSQuery.new(expression, language: language)
7
7
 
8
8
  Arel::Nodes::TSMatch.new(vector, query)
9
9
  end
10
10
 
11
11
  end
12
- end
12
+ end
@@ -8,6 +8,26 @@ module Arel
8
8
  super
9
9
  end
10
10
 
11
+ def visit_Arel_Nodes_Ascending o, collector
12
+ case o.nulls
13
+ when :nulls_first then visit(o.expr, collector) << ' ASC NULLS FIRST'
14
+ when :nulls_last then visit(o.expr, collector) << ' ASC NULLS LAST'
15
+ else visit(o.expr, collector) << ' ASC'
16
+ end
17
+ end
18
+
19
+ def visit_Arel_Nodes_Descending o, collector
20
+ case o.nulls
21
+ when :nulls_first then visit(o.expr, collector) << ' DESC NULLS FIRST'
22
+ when :nulls_last then visit(o.expr, collector) << ' DESC NULLS LAST'
23
+ else visit(o.expr, collector) << ' DESC'
24
+ end
25
+ end
26
+
27
+ def visit_Arel_Nodes_RandomOrdering o, collector
28
+ collector << "RANDOM()"
29
+ end
30
+
11
31
  def visit_Arel_Nodes_Contains o, collector
12
32
  visit o.left, collector
13
33
  collector << ' @> '
@@ -2,7 +2,67 @@ module Arel
2
2
  module Visitors
3
3
  class Sunstone
4
4
  private
5
+
6
+ def visit_Arel_Nodes_Ascending o, collector
7
+ hash = visit(o.expr, collector)
8
+
9
+ value = case o.nulls
10
+ when :nulls_first
11
+ {asc: :nulls_first}
12
+ when :nulls_last
13
+ {asc: :nulls_last}
14
+ else
15
+ :asc
16
+ end
17
+
18
+ if hash.is_a?(Hash)
19
+ add_to_bottom_of_hash_or_array(hash, value)
20
+ else
21
+ hash = { hash => value }
22
+ end
23
+
24
+ hash
25
+ end
26
+
27
+ def visit_Arel_Nodes_Descending o, collector
28
+ hash = visit(o.expr, collector)
29
+
30
+ value = case o.nulls
31
+ when :nulls_first
32
+ {desc: :nulls_first}
33
+ when :nulls_last
34
+ {desc: :nulls_last}
35
+ else
36
+ :desc
37
+ end
38
+
39
+ if hash.is_a?(Hash)
40
+ add_to_bottom_of_hash_or_array(hash, value)
41
+ else
42
+ hash = { hash => value }
43
+ end
44
+
45
+ hash
46
+ end
47
+
48
+ def visit_Arel_Nodes_RandomOrdering o, collector
49
+ :random
50
+ end
51
+
52
+ def visit_Hash o, collector
53
+ rvalue = {}
54
+ o.each do |key, value|
55
+ rvalue[visit(key, collector)] = visit(value, collector)
56
+ end
57
+ rvalue
58
+ end
5
59
 
60
+ alias :visit_String :literal
61
+
62
+ def visit_Symbol o, collector
63
+ o.to_s
64
+ end
65
+
6
66
  def visit_Arel_Nodes_Contains o, collector
7
67
  key = visit(o.left, collector)
8
68
  value = { contains: visit(o.right, collector) }
@@ -40,6 +100,30 @@ module Arel
40
100
  end
41
101
  end
42
102
 
103
+ def visit_Arel_Nodes_Overlaps o, collector
104
+ key = visit(o.left, collector)
105
+ value = { overlaps: o.left.type_cast_for_database(o.right) }
106
+
107
+ if key.is_a?(Hash)
108
+ add_to_bottom_of_hash_or_array(key, value)
109
+ key
110
+ else
111
+ {key => value}
112
+ end
113
+ end
114
+
115
+ def visit_Arel_Nodes_NotOverlaps o, collector
116
+ key = visit(o.left, collector)
117
+ value = { not_overlaps: o.left.type_cast_for_database(o.right) }
118
+
119
+ if key.is_a?(Hash)
120
+ add_to_bottom_of_hash_or_array(key, value)
121
+ key
122
+ else
123
+ {key => value}
124
+ end
125
+ end
126
+
43
127
  def visit_Arel_Nodes_HasKey o, collector
44
128
  key = visit(o.left, collector)
45
129
  value = {has_key: (o.right.nil? ? nil : o.right.to_s)}
@@ -64,7 +148,7 @@ module Arel
64
148
 
65
149
  def visit_Arel_Nodes_HasAnyKey o, collector
66
150
  key = visit(o.left, collector)
67
- value = {has_any_key: Array(o.right).map(&:to_s)}
151
+ value = { has_any_key: visit(Array(o.right), collector) }
68
152
 
69
153
  if key.is_a?(Hash)
70
154
  add_to_bottom_of_hash(key, value)
@@ -0,0 +1,11 @@
1
+ module Arel
2
+ module Visitors
3
+ class ToSql
4
+
5
+ def visit_Arel_Attributes_Relation(o, collector)
6
+ visit(o.relation, collector)
7
+ end
8
+
9
+ end
10
+ end
11
+ end
@@ -22,19 +22,30 @@ ActiveRecord::Migration.suppress_messages do
22
22
  create_table "properties", force: :cascade do |t|
23
23
  t.string "name", limit: 255
24
24
  t.tsvector 'vector_col'
25
+ t.jsonb 'metadata'
25
26
  end
26
27
 
27
28
  end
28
29
  end
29
30
 
30
31
  class Address < ActiveRecord::Base
31
-
32
32
  belongs_to :property
33
-
34
33
  end
35
34
 
36
35
  class Property < ActiveRecord::Base
37
-
38
36
  has_many :addresses
37
+ end
38
+
39
+ class SunstoneRecord < ActiveRecord::Base
40
+ self.abstract_class = true
41
+ end
42
+
43
+ class SunstoneAddress < SunstoneRecord
44
+ belongs_to :property, class_name: 'SunstoneProperty'
45
+ end
46
+
47
+ class SunstoneProperty < SunstoneRecord
48
+ has_many :addresses, class_name: 'SunstoneAddress'
49
+ end
39
50
 
40
- end
51
+ SunstoneRecord.establish_connection(adapter: 'sunstone', url: 'http://example.com')
@@ -0,0 +1,47 @@
1
+ require 'test_helper'
2
+
3
+ class OrderTest < ActiveSupport::TestCase
4
+
5
+ test '::order(column.asc)' do
6
+ assert_sql(<<~SQL, Property.order(Property.arel_table[:id].asc))
7
+ SELECT "properties".* FROM "properties" ORDER BY "properties"."id" ASC
8
+ SQL
9
+ end
10
+
11
+ test '::order(column1.asc, column2.asc)' do
12
+ assert_sql(<<~SQL, Property.order(Property.arel_table[:id].asc, Property.arel_table[:name].asc))
13
+ SELECT "properties".* FROM "properties" ORDER BY "properties"."id" ASC, "properties"."name" ASC
14
+ SQL
15
+ end
16
+
17
+ test '::order(column.desc)' do
18
+ assert_sql(<<~SQL, Property.order(Property.arel_table[:id].desc))
19
+ SELECT "properties".* FROM "properties" ORDER BY "properties"."id" DESC
20
+ SQL
21
+ end
22
+
23
+ test '::order(column.asc(:nulls_first))' do
24
+ assert_sql(<<~SQL, Property.order(Property.arel_table[:id].asc(:nulls_first)))
25
+ SELECT "properties".* FROM "properties" ORDER BY "properties"."id" ASC NULLS FIRST
26
+ SQL
27
+ end
28
+
29
+ test '::order(column.asc(:nulls_last))' do
30
+ assert_sql(<<~SQL, Property.order(Property.arel_table[:id].asc(:nulls_last)))
31
+ SELECT "properties".* FROM "properties" ORDER BY "properties"."id" ASC NULLS LAST
32
+ SQL
33
+ end
34
+
35
+ test '::order(column.desc(:nulls_first))' do
36
+ assert_sql(<<~SQL, Property.order(Property.arel_table[:id].desc(:nulls_first)))
37
+ SELECT "properties".* FROM "properties" ORDER BY "properties"."id" DESC NULLS FIRST
38
+ SQL
39
+ end
40
+
41
+ test '::order(column.desc(:nulls_last))' do
42
+ assert_sql(<<~SQL, Property.order(Property.arel_table[:id].desc(:nulls_last)))
43
+ SELECT "properties".* FROM "properties" ORDER BY "properties"."id" DESC NULLS LAST
44
+ SQL
45
+ end
46
+
47
+ end
@@ -0,0 +1,149 @@
1
+ require 'test_helper'
2
+
3
+ class SunstoneTest < ActiveSupport::TestCase
4
+
5
+ # schema do
6
+ # create_table "properties", force: :cascade do |t|
7
+ # t.jsonb 'metadata'
8
+ # end
9
+ # end
10
+
11
+ # class Property < ActiveRecord::Base
12
+ # end
13
+
14
+ # test "::filter json_column: STRING throws an error" do
15
+ # assert_raises(ActiveRecord::UnkownFilterError) do
16
+ # Property.filter(metadata: 'string').load
17
+ # end
18
+ # end
19
+
20
+ # test "::filter json_column: {eq: JSON_HASH}" do
21
+ # query = Property.where(metadata: {eq: {json: 'string'}})
22
+ # assert_equal(<<-SQL.strip.gsub(/\s+/, ' '), query.to_sql.strip)
23
+ # SELECT "properties".*
24
+ # FROM "properties"
25
+ # WHERE "properties"."metadata" = '{\"json\":\"string\"}'
26
+ # SQL
27
+ # end
28
+
29
+ test "::filter json_column: {contains: JSON_HASH}" do
30
+ query = SunstoneProperty.where(SunstoneProperty.arel_attribute('metadata').contains({json: 'string'}))
31
+ assert_sar(query, 'GET', '/sunstone_properties', {
32
+ where: {metadata: {contains: { json: 'string' }}}
33
+ })
34
+
35
+ # query = Property.where(metadata: {contains: {json: 'string'}})
36
+ # assert_equal(<<-SQL.strip.gsub(/\s+/, ' '), query.to_sql.strip)
37
+ # SELECT "properties".*
38
+ # FROM "properties"
39
+ # WHERE "properties"."metadata" @> '{\"json\":\"string\"}'
40
+ # SQL
41
+ end
42
+
43
+ # test "::filter json_column: {contained_by: JSON_HASH}" do
44
+ # query = Property.filter(metadata: {contained_by: {json: 'string'}})
45
+ # assert_equal(<<-SQL.strip.gsub(/\s+/, ' '), query.to_sql.strip)
46
+ # SELECT "properties".*
47
+ # FROM "properties"
48
+ # WHERE "properties"."metadata" <@ '{\"json\":\"string\"}'
49
+ # SQL
50
+ # end
51
+
52
+ # test "::filter json_column: {has_key: STRING}" do
53
+ # query = Property.filter(metadata: {has_key: 'string'})
54
+ # assert_equal(<<-SQL.strip.gsub(/\s+/, ' '), query.to_sql.strip)
55
+ # SELECT "properties".*
56
+ # FROM "properties"
57
+ # WHERE "properties"."metadata" ? 'string'
58
+ # SQL
59
+ # end
60
+
61
+ # test "::filter json_column.subkey: {eq: JSON_HASH}" do
62
+ # query = Property.filter("metadata.subkey" => {eq: 'string'})
63
+ # assert_equal(<<-SQL.strip.gsub(/\s+/, ' '), query.to_sql.strip)
64
+ # SELECT "properties".*
65
+ # FROM "properties"
66
+ # WHERE "properties"."metadata"#>'{subkey}' = 'string'
67
+ # SQL
68
+ # end
69
+
70
+ # test "::filter json_column: BOOLEAN" do
71
+ # query = Property.filter(metadata: true)
72
+ # assert_equal(<<-SQL.strip.gsub(/\s+/, ' '), query.to_sql.strip)
73
+ # SELECT "properties".*
74
+ # FROM "properties"
75
+ # WHERE "properties"."metadata" IS NOT NULL
76
+ # SQL
77
+
78
+ # query = Property.filter(metadata: "true")
79
+ # assert_equal(<<-SQL.strip.gsub(/\s+/, ' '), query.to_sql.strip)
80
+ # SELECT "properties".*
81
+ # FROM "properties"
82
+ # WHERE "properties"."metadata" IS NOT NULL
83
+ # SQL
84
+
85
+ # query = Property.filter(metadata: false)
86
+ # assert_equal(<<-SQL.strip.gsub(/\s+/, ' '), query.to_sql.strip)
87
+ # SELECT "properties".*
88
+ # FROM "properties"
89
+ # WHERE "properties"."metadata" IS NULL
90
+ # SQL
91
+
92
+ # query = Property.filter(metadata: "false")
93
+ # assert_equal(<<-SQL.strip.gsub(/\s+/, ' '), query.to_sql.strip)
94
+ # SELECT "properties".*
95
+ # FROM "properties"
96
+ # WHERE "properties"."metadata" IS NULL
97
+ # SQL
98
+ # end
99
+
100
+ test '::order(column.asc)' do
101
+ query = SunstoneProperty.order(SunstoneProperty.arel_table[:id].asc)
102
+ assert_sar(query, 'GET', '/sunstone_properties', {
103
+ order: [{ id: :asc }]
104
+ })
105
+ end
106
+
107
+ test '::order(column1.asc, column2.asc)' do
108
+ query = SunstoneProperty.order(SunstoneProperty.arel_table[:id].asc, SunstoneProperty.arel_table[:name].asc)
109
+ assert_sar(query, 'GET', '/sunstone_properties', {
110
+ order: [{ id: :asc }, { name: :asc }]
111
+ })
112
+ end
113
+
114
+ test '::order(column.desc)' do
115
+ query = SunstoneProperty.order(SunstoneProperty.arel_table[:id].desc)
116
+ assert_sar(query, 'GET', '/sunstone_properties', {
117
+ order: [{ id: :desc }]
118
+ })
119
+ end
120
+
121
+ test '::order(column.asc(:nulls_first))' do
122
+ query = SunstoneProperty.order(SunstoneProperty.arel_table[:id].asc(:nulls_first))
123
+ assert_sar(query, 'GET', '/sunstone_properties', {
124
+ order: [{ id: { asc: :nulls_first } }]
125
+ })
126
+ end
127
+
128
+ test '::order(column.asc(:nulls_last))' do
129
+ query = SunstoneProperty.order(SunstoneProperty.arel_table[:id].asc(:nulls_last))
130
+ assert_sar(query, 'GET', '/sunstone_properties', {
131
+ order: [{ id: { asc: :nulls_last } }]
132
+ })
133
+ end
134
+
135
+ test '::order(column.desc(:nulls_first))' do
136
+ query = SunstoneProperty.order(SunstoneProperty.arel_table[:id].desc(:nulls_first))
137
+ assert_sar(query, 'GET', '/sunstone_properties', {
138
+ order: [{ id: { desc: :nulls_first } }]
139
+ })
140
+ end
141
+
142
+ test '::order(column.desc(:nulls_last))' do
143
+ query = SunstoneProperty.order(SunstoneProperty.arel_table[:id].desc(:nulls_last))
144
+ assert_sar(query, 'GET', '/sunstone_properties', {
145
+ order: [{ id: { desc: :nulls_last } }]
146
+ })
147
+ end
148
+
149
+ end
@@ -12,11 +12,13 @@ require 'rgeo'
12
12
  require "minitest/autorun"
13
13
  require 'minitest/unit'
14
14
  require 'minitest/reporters'
15
- # require 'webmock/minitest'
15
+ require 'webmock/minitest'
16
16
  # require 'mocha/minitest'
17
17
  require 'active_record'
18
+ require 'sunstone'
18
19
  require 'arel/extensions'
19
20
 
21
+
20
22
  # Setup the test db
21
23
  ActiveSupport.test_order = :random
22
24
  require File.expand_path('../database', __FILE__)
@@ -27,7 +29,7 @@ $debugging = false
27
29
 
28
30
  # File 'lib/active_support/testing/declarative.rb', somewhere in rails....
29
31
  class ActiveSupport::TestCase
30
- # include WebMock::API
32
+ include WebMock::API
31
33
 
32
34
  # File 'lib/active_support/testing/declarative.rb'
33
35
  def self.test(name, &block)
@@ -54,6 +56,51 @@ class ActiveSupport::TestCase
54
56
  end
55
57
  end
56
58
  end
59
+
60
+ def setup
61
+ sunstone_schema = {
62
+ addresses: {
63
+ columns: {
64
+ id: { type: :integer, primary_key: true, null: false, array: false },
65
+ name: { type: :string, primary_key: false, null: true, array: false },
66
+ property_id: { type: :integer, primary_key: false, null: true, array: false }
67
+ }
68
+ },
69
+ properties: {
70
+ columns: {
71
+ id: { type: :integer, primary_key: true, null: false, array: false },
72
+ name: { type: :string, primary_key: false, null: true, array: false },
73
+ metadata: { type: :json, primary_key: false, null: true, array: false }
74
+ }
75
+ }
76
+ }
77
+
78
+ req_stub = stub_request(:get, /^http:\/\/example.com/).with do |req|
79
+ case req.uri.path
80
+ when '/tables'
81
+ true
82
+ when /^\/\w+\/schema$/i
83
+ true
84
+ else
85
+ false
86
+ end
87
+ end
88
+
89
+ req_stub.to_return do |req|
90
+ case req.uri.path
91
+ when '/tables'
92
+ {
93
+ body: sunstone_schema.keys.to_json,
94
+ headers: { 'StandardAPI-Version' => '5.0.0.5' }
95
+ }
96
+ when /^\/(\w+)\/schema$/i
97
+ {
98
+ body: sunstone_schema[$1.to_sym].to_json,
99
+ headers: { 'StandardAPI-Version' => '5.0.0.5' }
100
+ }
101
+ end
102
+ end
103
+ end
57
104
 
58
105
  def debug
59
106
  ActiveRecord::Base.logger = Logger.new(STDOUT)
@@ -112,6 +159,37 @@ class ActiveSupport::TestCase
112
159
  end
113
160
  ActiveSupport::Notifications.subscribe('sql.active_record', SQLLogger.new)
114
161
 
162
+ def deep_transform_query(object)
163
+ case object
164
+ when Hash
165
+ object.each_with_object({}) do |(key, value), result|
166
+ result[key.to_s] = deep_transform_query(value)
167
+ end
168
+ when Array
169
+ object.map {|e| deep_transform_query(e) }
170
+ when Symbol
171
+ object.to_s
172
+ else
173
+ object
174
+ end
175
+ end
176
+
177
+ def assert_sar(query, method, path, query_params = {}, body = nil)
178
+ sar = query.to_sar
179
+
180
+ assert_equal method, sar.method
181
+ assert_equal path, sar.path.split('?').first
182
+ assert_equal deep_transform_query(query_params), MessagePack.unpack(CGI::unescape(sar.path.split('?').last))
183
+ if body.nil?
184
+ assert_nil sar.body
185
+ else
186
+ assert_equal body, sar.body
187
+ end
188
+ end
189
+
190
+ def assert_sql(expected, query)
191
+ assert_equal expected.strip, query.to_sql.strip.gsub(/\s+/, ' ')
192
+ end
115
193
  # test/unit backwards compatibility methods
116
194
  alias :assert_raise :assert_raises
117
195
  alias :assert_not_empty :refute_empty
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: arel-extensions
3
3
  version: !ruby/object:Gem::Version
4
- version: 6.0.0
4
+ version: 6.0.0.8
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jon Bracy
8
- autorequire:
8
+ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2019-05-29 00:00:00.000000000 Z
11
+ date: 2020-06-26 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activerecord
@@ -16,14 +16,14 @@ dependencies:
16
16
  requirements:
17
17
  - - ">="
18
18
  - !ruby/object:Gem::Version
19
- version: 6.0.0.rc1
19
+ version: 6.0.0
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - ">="
25
25
  - !ruby/object:Gem::Version
26
- version: 6.0.0.rc1
26
+ version: 6.0.0
27
27
  - !ruby/object:Gem::Dependency
28
28
  name: bundler
29
29
  requirement: !ruby/object:Gem::Requirement
@@ -80,6 +80,34 @@ dependencies:
80
80
  - - ">="
81
81
  - !ruby/object:Gem::Version
82
82
  version: '0'
83
+ - !ruby/object:Gem::Dependency
84
+ name: sunstone
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - ">="
88
+ - !ruby/object:Gem::Version
89
+ version: '0'
90
+ type: :development
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - ">="
95
+ - !ruby/object:Gem::Version
96
+ version: '0'
97
+ - !ruby/object:Gem::Dependency
98
+ name: webmock
99
+ requirement: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - ">="
102
+ - !ruby/object:Gem::Version
103
+ version: '0'
104
+ type: :development
105
+ prerelease: false
106
+ version_requirements: !ruby/object:Gem::Requirement
107
+ requirements:
108
+ - - ">="
109
+ - !ruby/object:Gem::Version
110
+ version: '0'
83
111
  - !ruby/object:Gem::Dependency
84
112
  name: pg
85
113
  requirement: !ruby/object:Gem::Requirement
@@ -108,7 +136,7 @@ dependencies:
108
136
  - - ">="
109
137
  - !ruby/object:Gem::Version
110
138
  version: '0'
111
- description:
139
+ description:
112
140
  email:
113
141
  - jonbracy@gmail.com
114
142
  executables: []
@@ -118,11 +146,13 @@ files:
118
146
  - ".gitignore"
119
147
  - ".travis.yml"
120
148
  - Gemfile
121
- - Gemfile.lock
122
149
  - LICENSE
123
150
  - README.md
124
151
  - Rakefile
125
152
  - arel-extensions.gemspec
153
+ - ext/arel/nodes/ascending.rb
154
+ - ext/arel/nodes/descending.rb
155
+ - ext/arel/order_predications.rb
126
156
  - lib/active_record/query_methods.rb
127
157
  - lib/arel/array_predications.rb
128
158
  - lib/arel/attributes/cast.rb
@@ -138,6 +168,8 @@ files:
138
168
  - lib/arel/nodes/has_keys.rb
139
169
  - lib/arel/nodes/hex_encoded_binary.rb
140
170
  - lib/arel/nodes/overlaps.rb
171
+ - lib/arel/nodes/random.rb
172
+ - lib/arel/nodes/relation.rb
141
173
  - lib/arel/nodes/ts_match.rb
142
174
  - lib/arel/nodes/ts_query.rb
143
175
  - lib/arel/nodes/ts_rank.rb
@@ -147,14 +179,17 @@ files:
147
179
  - lib/arel/ts_predications.rb
148
180
  - lib/arel/visitors/postgresql_extensions.rb
149
181
  - lib/arel/visitors/sunstone_extensions.rb
182
+ - lib/arel/visitors/to_sql_extensions.rb
150
183
  - test/database.rb
184
+ - test/order_test.rb
185
+ - test/sunstone_test.rb
151
186
  - test/test_helper.rb
152
187
  - test/ts_test.rb
153
188
  homepage: https://github.com/malomalo/arel-extensions
154
189
  licenses:
155
190
  - MIT
156
191
  metadata: {}
157
- post_install_message:
192
+ post_install_message:
158
193
  rdoc_options: []
159
194
  require_paths:
160
195
  - lib
@@ -169,11 +204,13 @@ required_rubygems_version: !ruby/object:Gem::Requirement
169
204
  - !ruby/object:Gem::Version
170
205
  version: '0'
171
206
  requirements: []
172
- rubygems_version: 3.0.3
173
- signing_key:
207
+ rubygems_version: 3.1.2
208
+ signing_key:
174
209
  specification_version: 4
175
210
  summary: Adds support for missing SQL operators and functions to Arel
176
211
  test_files:
177
212
  - test/database.rb
213
+ - test/order_test.rb
214
+ - test/sunstone_test.rb
178
215
  - test/test_helper.rb
179
216
  - test/ts_test.rb
@@ -1,54 +0,0 @@
1
- PATH
2
- remote: .
3
- specs:
4
- arel-extensions (6.0.0)
5
- activerecord (>= 6.0.0.rc1)
6
-
7
- GEM
8
- remote: https://rubygems.org/
9
- specs:
10
- activemodel (6.0.0.rc1)
11
- activesupport (= 6.0.0.rc1)
12
- activerecord (6.0.0.rc1)
13
- activemodel (= 6.0.0.rc1)
14
- activesupport (= 6.0.0.rc1)
15
- activesupport (6.0.0.rc1)
16
- concurrent-ruby (~> 1.0, >= 1.0.2)
17
- i18n (>= 0.7, < 2)
18
- minitest (~> 5.1)
19
- tzinfo (~> 1.1)
20
- zeitwerk (~> 2.1, >= 2.1.4)
21
- ansi (1.5.0)
22
- builder (3.2.3)
23
- concurrent-ruby (1.1.5)
24
- i18n (1.6.0)
25
- concurrent-ruby (~> 1.0)
26
- minitest (5.11.3)
27
- minitest-reporters (1.3.5)
28
- ansi
29
- builder
30
- minitest (>= 5.0)
31
- ruby-progressbar
32
- pg (1.1.3)
33
- rake (12.3.1)
34
- rgeo (1.0.0)
35
- ruby-progressbar (1.10.0)
36
- thread_safe (0.3.6)
37
- tzinfo (1.2.5)
38
- thread_safe (~> 0.1)
39
- zeitwerk (2.1.6)
40
-
41
- PLATFORMS
42
- ruby
43
-
44
- DEPENDENCIES
45
- arel-extensions!
46
- bundler
47
- minitest
48
- minitest-reporters
49
- pg
50
- rake
51
- rgeo
52
-
53
- BUNDLED WITH
54
- 1.17.3