pgrel 0.1.1 → 0.3.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +5 -5
- data/CHANGELOG.md +31 -0
- data/{MIT-LICENSE → LICENSE.txt} +1 -1
- data/README.md +56 -13
- data/lib/pgrel.rb +4 -2
- data/lib/pgrel/active_record.rb +9 -2
- data/lib/pgrel/active_record/query_methods.rb +7 -5
- data/lib/pgrel/active_record/querying.rb +7 -0
- data/lib/pgrel/active_record/relation.rb +19 -0
- data/lib/pgrel/active_record/store/flexible_hstore.rb +24 -0
- data/lib/pgrel/active_record/store/flexible_jsonb.rb +25 -0
- data/lib/pgrel/active_record/store/flexible_store.rb +13 -0
- data/lib/pgrel/active_record/store_chain.rb +108 -36
- data/lib/pgrel/active_record/store_chain/array_chain.rb +3 -1
- data/lib/pgrel/active_record/store_chain/hstore_chain.rb +18 -23
- data/lib/pgrel/active_record/store_chain/jsonb_chain.rb +47 -32
- data/lib/pgrel/version.rb +3 -1
- metadata +19 -60
- data/.gitignore +0 -36
- data/.rubocop.yml +0 -41
- data/.travis.yml +0 -21
- data/Gemfile +0 -11
- data/Rakefile +0 -6
- data/gemfiles/rails40.gemfile +0 -5
- data/gemfiles/rails41.gemfile +0 -5
- data/gemfiles/rails42.gemfile +0 -5
- data/gemfiles/rails5.gemfile +0 -6
- data/pgrel.gemspec +0 -27
- data/spec/pgrel/array_spec.rb +0 -71
- data/spec/pgrel/hstore_spec.rb +0 -130
- data/spec/pgrel/jsonb_spec.rb +0 -137
- data/spec/spec_helper.rb +0 -35
- data/spec/support/array_store.rb +0 -2
- data/spec/support/hstore.rb +0 -2
- data/spec/support/jsonb.rb +0 -2
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module ActiveRecord
|
2
4
|
module QueryMethods
|
3
5
|
# Store chain for array columns.
|
@@ -11,7 +13,7 @@ module ActiveRecord
|
|
11
13
|
# Model.store(:store).overlap('c').all #=> [Model(name: 'first', ...)]
|
12
14
|
# Model.store(:store).overlap(['b']).size #=> 2
|
13
15
|
def overlap(*vals)
|
14
|
-
update_scope "#{
|
16
|
+
update_scope "#{quoted_store_name} && #{type_cast(vals.flatten)}"
|
15
17
|
end
|
16
18
|
end
|
17
19
|
end
|
@@ -1,35 +1,30 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module ActiveRecord
|
2
4
|
module QueryMethods
|
3
5
|
# Store chain for hstore columns.
|
4
6
|
class HstoreChain < KeyStoreChain
|
5
|
-
#
|
6
|
-
#
|
7
|
-
# Supports array values.
|
7
|
+
# Overlap values
|
8
8
|
#
|
9
9
|
# Example
|
10
|
-
# Model.create!(name: 'first', store: {
|
11
|
-
# Model.create!(name: 'second', store: {b:
|
10
|
+
# Model.create!(name: 'first', store: {a: 1, b: 2})
|
11
|
+
# Model.create!(name: 'second', store: {b: 1, c: 3})
|
12
12
|
#
|
13
|
-
# Model.store(:store,
|
14
|
-
# Model
|
15
|
-
def
|
16
|
-
|
17
|
-
where_with_prefix "#{@store_name}->", opts
|
13
|
+
# Model.store(:store).overlap_values(1, 2).all
|
14
|
+
# #=>[Model(name: 'first', ...), Model(name: 'second')]
|
15
|
+
def overlap_values(*values)
|
16
|
+
update_scope("avals(#{quoted_store_name}) && ARRAY[?]", values.map(&:to_s))
|
18
17
|
end
|
19
18
|
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
Hash[val.map { |k, v| [stringify(k), stringify(v)] }]
|
30
|
-
else
|
31
|
-
val.to_s
|
32
|
-
end
|
19
|
+
# Contains values
|
20
|
+
#
|
21
|
+
# Example
|
22
|
+
# Model.create!(name: 'first', store: {a: 1, b: 2})
|
23
|
+
# Model.create!(name: 'second', store: {b: 1, c: 3})
|
24
|
+
#
|
25
|
+
# Model.store(:store).contains_values(1, 2).all #=> [Model(name: 'first', ...)]
|
26
|
+
def contains_values(*values)
|
27
|
+
update_scope("avals(#{quoted_store_name}) @> ARRAY[?]", values.map(&:to_s))
|
33
28
|
end
|
34
29
|
end
|
35
30
|
end
|
@@ -1,24 +1,12 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module ActiveRecord
|
2
4
|
module QueryMethods
|
3
5
|
# Store chain for jsonb columns.
|
4
6
|
class JsonbChain < KeyStoreChain
|
5
|
-
|
6
|
-
# Supports array values (convert to IN statement).
|
7
|
-
#
|
8
|
-
# Example
|
9
|
-
# Model.create!(name: 'first', store: {b: 1, c: 2})
|
10
|
-
# Model.create!(name: 'second', store: {b: 2, c: 3})
|
11
|
-
#
|
12
|
-
# Model.store(:store, c: 2).all #=> [Model(name: 'first', ...)]
|
13
|
-
# Model.store(:store, b: [1, 2]).size #=> 2
|
14
|
-
def where(opts)
|
15
|
-
opts = flatten_json(opts)
|
16
|
-
where_with_prefix "#{@store_name}->", opts
|
17
|
-
end
|
7
|
+
OPERATORS = {contains: "@>", overlap: "&&"}.freeze
|
18
8
|
|
19
|
-
# Query by
|
20
|
-
#
|
21
|
-
# Path can be set as object or as args.
|
9
|
+
# Query by value in path.
|
22
10
|
#
|
23
11
|
# Example:
|
24
12
|
# Model.create!(name: 'first', store: {b: 1, c: { d: 3 } })
|
@@ -30,37 +18,48 @@ module ActiveRecord
|
|
30
18
|
args = flatten_hash(args.first) if args.size == 1
|
31
19
|
val = args.pop
|
32
20
|
|
33
|
-
path = "{#{args.join(
|
21
|
+
path = "{#{args.join(",")}}"
|
34
22
|
|
35
23
|
case val
|
36
24
|
when Hash
|
37
|
-
op =
|
25
|
+
op = "#>"
|
38
26
|
val = ::ActiveSupport::JSON.encode(val)
|
39
27
|
when Array
|
40
|
-
op =
|
28
|
+
op = "#>>"
|
41
29
|
val = val.map(&:to_s)
|
42
30
|
else
|
43
|
-
op =
|
31
|
+
op = "#>>"
|
44
32
|
val = val.to_s
|
45
33
|
end
|
46
34
|
|
47
|
-
where_with_prefix "#{
|
35
|
+
where_with_prefix "#{quoted_store_name}#{op}", path => val
|
48
36
|
end
|
49
37
|
|
50
|
-
|
38
|
+
# Overlap values
|
39
|
+
#
|
40
|
+
# Example
|
41
|
+
# Model.create!(name: 'first', store: {a: 1, b: 2})
|
42
|
+
# Model.create!(name: 'second', store: {b: 1, c: 3})
|
43
|
+
#
|
44
|
+
# Model.store(:store).overlap_values(1, 2).all
|
45
|
+
# #=>[Model(name: 'first', ...), Model(name: 'second')]
|
46
|
+
def overlap_values(*values)
|
47
|
+
update_scope(value_query(:overlap), cast_values(values))
|
48
|
+
end
|
51
49
|
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
]
|
50
|
+
# Contains values
|
51
|
+
#
|
52
|
+
# Example
|
53
|
+
# Model.create!(name: 'first', store: {a: 1, b: 2})
|
54
|
+
# Model.create!(name: 'second', store: {b: 1, c: 3})
|
55
|
+
#
|
56
|
+
# Model.store(:store).contains_values(1, 2).all #=> [Model(name: 'first', ...)]
|
57
|
+
def contains_values(*values)
|
58
|
+
update_scope(value_query(:contains), cast_values(values))
|
62
59
|
end
|
63
60
|
|
61
|
+
private
|
62
|
+
|
64
63
|
def flatten_hash(hash)
|
65
64
|
case hash
|
66
65
|
when Hash
|
@@ -71,6 +70,22 @@ module ActiveRecord
|
|
71
70
|
hash
|
72
71
|
end
|
73
72
|
end
|
73
|
+
|
74
|
+
def value_query(operator)
|
75
|
+
oper = OPERATORS[operator]
|
76
|
+
"(SELECT array_agg(value) FROM jsonb_each(#{quoted_store_name})) #{oper} ARRAY[?]::jsonb[]"
|
77
|
+
end
|
78
|
+
|
79
|
+
def cast_values(values)
|
80
|
+
values.map do |v|
|
81
|
+
case v
|
82
|
+
when Hash, Array, String
|
83
|
+
v.to_json
|
84
|
+
else
|
85
|
+
v.to_s
|
86
|
+
end
|
87
|
+
end
|
88
|
+
end
|
74
89
|
end
|
75
90
|
end
|
76
91
|
end
|
data/lib/pgrel/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: pgrel
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.3.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- palkan
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2020-12-18 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activerecord
|
@@ -16,84 +16,56 @@ dependencies:
|
|
16
16
|
requirements:
|
17
17
|
- - ">="
|
18
18
|
- !ruby/object:Gem::Version
|
19
|
-
version: 4.0
|
19
|
+
version: '4.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: 4.0
|
26
|
+
version: '4.0'
|
27
27
|
- !ruby/object:Gem::Dependency
|
28
28
|
name: pg
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
30
30
|
requirements:
|
31
|
-
- - "
|
31
|
+
- - ">="
|
32
32
|
- !ruby/object:Gem::Version
|
33
33
|
version: '0.18'
|
34
34
|
type: :development
|
35
35
|
prerelease: false
|
36
36
|
version_requirements: !ruby/object:Gem::Requirement
|
37
37
|
requirements:
|
38
|
-
- - "
|
38
|
+
- - ">="
|
39
39
|
- !ruby/object:Gem::Version
|
40
40
|
version: '0.18'
|
41
41
|
- !ruby/object:Gem::Dependency
|
42
42
|
name: rake
|
43
|
-
requirement: !ruby/object:Gem::Requirement
|
44
|
-
requirements:
|
45
|
-
- - "~>"
|
46
|
-
- !ruby/object:Gem::Version
|
47
|
-
version: '10.1'
|
48
|
-
type: :development
|
49
|
-
prerelease: false
|
50
|
-
version_requirements: !ruby/object:Gem::Requirement
|
51
|
-
requirements:
|
52
|
-
- - "~>"
|
53
|
-
- !ruby/object:Gem::Version
|
54
|
-
version: '10.1'
|
55
|
-
- !ruby/object:Gem::Dependency
|
56
|
-
name: simplecov
|
57
43
|
requirement: !ruby/object:Gem::Requirement
|
58
44
|
requirements:
|
59
45
|
- - ">="
|
60
46
|
- !ruby/object:Gem::Version
|
61
|
-
version:
|
47
|
+
version: '10.1'
|
62
48
|
type: :development
|
63
49
|
prerelease: false
|
64
50
|
version_requirements: !ruby/object:Gem::Requirement
|
65
51
|
requirements:
|
66
52
|
- - ">="
|
67
53
|
- !ruby/object:Gem::Version
|
68
|
-
version:
|
54
|
+
version: '10.1'
|
69
55
|
- !ruby/object:Gem::Dependency
|
70
|
-
name:
|
56
|
+
name: rspec
|
71
57
|
requirement: !ruby/object:Gem::Requirement
|
72
58
|
requirements:
|
73
59
|
- - ">="
|
74
60
|
- !ruby/object:Gem::Version
|
75
|
-
version: '
|
61
|
+
version: '3.1'
|
76
62
|
type: :development
|
77
63
|
prerelease: false
|
78
64
|
version_requirements: !ruby/object:Gem::Requirement
|
79
65
|
requirements:
|
80
66
|
- - ">="
|
81
67
|
- !ruby/object:Gem::Version
|
82
|
-
version: '
|
83
|
-
- !ruby/object:Gem::Dependency
|
84
|
-
name: rspec
|
85
|
-
requirement: !ruby/object:Gem::Requirement
|
86
|
-
requirements:
|
87
|
-
- - "~>"
|
88
|
-
- !ruby/object:Gem::Version
|
89
|
-
version: 3.1.0
|
90
|
-
type: :development
|
91
|
-
prerelease: false
|
92
|
-
version_requirements: !ruby/object:Gem::Requirement
|
93
|
-
requirements:
|
94
|
-
- - "~>"
|
95
|
-
- !ruby/object:Gem::Version
|
96
|
-
version: 3.1.0
|
68
|
+
version: '3.1'
|
97
69
|
description: ActiveRecord extension for querying hstore and jsonb.
|
98
70
|
email:
|
99
71
|
- dementiev.vm@gmail.com
|
@@ -101,33 +73,22 @@ executables: []
|
|
101
73
|
extensions: []
|
102
74
|
extra_rdoc_files: []
|
103
75
|
files:
|
104
|
-
-
|
105
|
-
-
|
106
|
-
- ".travis.yml"
|
107
|
-
- Gemfile
|
108
|
-
- MIT-LICENSE
|
76
|
+
- CHANGELOG.md
|
77
|
+
- LICENSE.txt
|
109
78
|
- README.md
|
110
|
-
- Rakefile
|
111
|
-
- gemfiles/rails40.gemfile
|
112
|
-
- gemfiles/rails41.gemfile
|
113
|
-
- gemfiles/rails42.gemfile
|
114
|
-
- gemfiles/rails5.gemfile
|
115
79
|
- lib/pgrel.rb
|
116
80
|
- lib/pgrel/active_record.rb
|
117
81
|
- lib/pgrel/active_record/query_methods.rb
|
82
|
+
- lib/pgrel/active_record/querying.rb
|
83
|
+
- lib/pgrel/active_record/relation.rb
|
84
|
+
- lib/pgrel/active_record/store/flexible_hstore.rb
|
85
|
+
- lib/pgrel/active_record/store/flexible_jsonb.rb
|
86
|
+
- lib/pgrel/active_record/store/flexible_store.rb
|
118
87
|
- lib/pgrel/active_record/store_chain.rb
|
119
88
|
- lib/pgrel/active_record/store_chain/array_chain.rb
|
120
89
|
- lib/pgrel/active_record/store_chain/hstore_chain.rb
|
121
90
|
- lib/pgrel/active_record/store_chain/jsonb_chain.rb
|
122
91
|
- lib/pgrel/version.rb
|
123
|
-
- pgrel.gemspec
|
124
|
-
- spec/pgrel/array_spec.rb
|
125
|
-
- spec/pgrel/hstore_spec.rb
|
126
|
-
- spec/pgrel/jsonb_spec.rb
|
127
|
-
- spec/spec_helper.rb
|
128
|
-
- spec/support/array_store.rb
|
129
|
-
- spec/support/hstore.rb
|
130
|
-
- spec/support/jsonb.rb
|
131
92
|
homepage: http://github.com/palkan/pgrel
|
132
93
|
licenses:
|
133
94
|
- MIT
|
@@ -147,10 +108,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
147
108
|
- !ruby/object:Gem::Version
|
148
109
|
version: '0'
|
149
110
|
requirements: []
|
150
|
-
|
151
|
-
rubygems_version: 2.2.2
|
111
|
+
rubygems_version: 3.0.6
|
152
112
|
signing_key:
|
153
113
|
specification_version: 4
|
154
114
|
summary: ActiveRecord extension for querying hstore and jsonb.
|
155
115
|
test_files: []
|
156
|
-
has_rdoc:
|
data/.gitignore
DELETED
@@ -1,36 +0,0 @@
|
|
1
|
-
# Numerous always-ignore extensions
|
2
|
-
*.diff
|
3
|
-
*.err
|
4
|
-
*.orig
|
5
|
-
*.log
|
6
|
-
*.rej
|
7
|
-
*.swo
|
8
|
-
*.swp
|
9
|
-
*.vi
|
10
|
-
*~
|
11
|
-
*.sass-cache
|
12
|
-
*.iml
|
13
|
-
.idea/
|
14
|
-
|
15
|
-
# Sublime
|
16
|
-
*.sublime-project
|
17
|
-
*.sublime-workspace
|
18
|
-
|
19
|
-
# OS or Editor folders
|
20
|
-
.DS_Store
|
21
|
-
.cache
|
22
|
-
.project
|
23
|
-
.settings
|
24
|
-
.tmproj
|
25
|
-
Thumbs.db
|
26
|
-
coverage/
|
27
|
-
|
28
|
-
.bundle/
|
29
|
-
*.log
|
30
|
-
*.gem
|
31
|
-
pkg/
|
32
|
-
spec/dummy/log/*.log
|
33
|
-
spec/dummy/tmp/
|
34
|
-
spec/dummy/.sass-cache
|
35
|
-
Gemfile.local
|
36
|
-
Gemfile.lock
|
data/.rubocop.yml
DELETED
@@ -1,41 +0,0 @@
|
|
1
|
-
# This strict rubocop config should be used before submiting PR and should pass
|
2
|
-
# Doesn't include:
|
3
|
-
# - specs
|
4
|
-
|
5
|
-
|
6
|
-
AllCops:
|
7
|
-
# Include gemspec and Rakefile
|
8
|
-
Include:
|
9
|
-
- 'app/**/*.rb'
|
10
|
-
- 'config/**/*.rb'
|
11
|
-
- 'lib/**/*.rb'
|
12
|
-
- 'lib/**/*.rake'
|
13
|
-
Exclude:
|
14
|
-
- 'vendor/**/*'
|
15
|
-
- 'spec/**/*'
|
16
|
-
- 'db/*.rb'
|
17
|
-
- 'bin/**/*'
|
18
|
-
RunRailsCops: false
|
19
|
-
DisplayCopNames: true
|
20
|
-
StyleGuideCopsOnly: false
|
21
|
-
|
22
|
-
Metrics/LineLength:
|
23
|
-
Max: 100
|
24
|
-
|
25
|
-
Metrics/MethodLength:
|
26
|
-
Max: 15
|
27
|
-
|
28
|
-
Metrics/AbcSize:
|
29
|
-
Max: 20
|
30
|
-
|
31
|
-
Style/BarePercentLiterals:
|
32
|
-
Enabled: false
|
33
|
-
|
34
|
-
Style/CommentAnnotation:
|
35
|
-
Enabled: false
|
36
|
-
|
37
|
-
Style/RaiseArgs:
|
38
|
-
Enabled: false
|
39
|
-
|
40
|
-
Style/StringLiterals:
|
41
|
-
Enabled: false
|
data/.travis.yml
DELETED
@@ -1,21 +0,0 @@
|
|
1
|
-
language: ruby
|
2
|
-
cache: bundler
|
3
|
-
|
4
|
-
addons:
|
5
|
-
postgresql: "9.4"
|
6
|
-
|
7
|
-
before_script:
|
8
|
-
- createuser pgrel -d
|
9
|
-
- createdb -U pgrel pgrel
|
10
|
-
- psql -U postgres -d pgrel -c 'CREATE EXTENSION IF NOT EXISTS hstore;'
|
11
|
-
|
12
|
-
matrix:
|
13
|
-
include:
|
14
|
-
- rvm: 2.2.1
|
15
|
-
gemfile: gemfiles/rails5.gemfile
|
16
|
-
- rvm: 2.2.1
|
17
|
-
gemfile: gemfiles/rails42.gemfile
|
18
|
-
- rvm: 2.1
|
19
|
-
gemfile: gemfiles/rails41.gemfile
|
20
|
-
- rvm: 2.1
|
21
|
-
gemfile: gemfiles/rails40.gemfile
|