nql 0.0.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.
- data/.gitignore +18 -0
- data/Gemfile +4 -0
- data/LICENSE +22 -0
- data/README.md +29 -0
- data/Rakefile +2 -0
- data/lib/nql.rb +15 -0
- data/lib/nql/grammar.rb +761 -0
- data/lib/nql/grammar.treetop +109 -0
- data/lib/nql/version.rb +3 -0
- data/nql.gemspec +25 -0
- data/spec/comparison_parser_spec.rb +147 -0
- data/spec/coordination_parser_spec.rb +43 -0
- data/spec/migrations/20121108154439_create_countries.rb +9 -0
- data/spec/migrations/20121108154508_create_cities.rb +10 -0
- data/spec/models/city.rb +3 -0
- data/spec/models/country.rb +3 -0
- data/spec/ransack_spec.rb +135 -0
- data/spec/spec_helper.rb +45 -0
- data/spec/sql_spec.rb +93 -0
- metadata +139 -0
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,45 @@
|
|
1
|
+
require 'nql'
|
2
|
+
|
3
|
+
Dir["#{File.dirname(__FILE__)}/models/**/*.rb"].each {|f| require f}
|
4
|
+
|
5
|
+
ActiveRecord::Migrator.migrations_path = "#{File.dirname(__FILE__)}/migrations"
|
6
|
+
|
7
|
+
RSpec::Matchers.define :have_attribute do |expected|
|
8
|
+
match do |actual|
|
9
|
+
actual['a']['0']['name'] == expected
|
10
|
+
end
|
11
|
+
|
12
|
+
failure_message_for_should do |actual|
|
13
|
+
"expected: #{actual['a']['0']['name']}\n got: #{expected}"
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
RSpec::Matchers.define :have_predicate do |expected|
|
18
|
+
match do |actual|
|
19
|
+
actual['p'] == expected
|
20
|
+
end
|
21
|
+
|
22
|
+
failure_message_for_should do |actual|
|
23
|
+
"expected: #{actual['p']}\n got: #{expected}"
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
RSpec::Matchers.define :have_value do |expected|
|
28
|
+
match do |actual|
|
29
|
+
actual['v']['0']['value'] == expected
|
30
|
+
end
|
31
|
+
|
32
|
+
failure_message_for_should do |actual|
|
33
|
+
"expected: #{actual['v']['0']['value']}\n got: #{expected}"
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
RSpec::Matchers.define :produce_sql do |expected|
|
38
|
+
match do |actual|
|
39
|
+
actual.to_sql == expected
|
40
|
+
end
|
41
|
+
|
42
|
+
failure_message_for_should do |actual|
|
43
|
+
"expected: #{actual.to_sql}\n got: #{expected}"
|
44
|
+
end
|
45
|
+
end
|
data/spec/sql_spec.rb
ADDED
@@ -0,0 +1,93 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe 'SQL generation' do
|
4
|
+
|
5
|
+
before :all do
|
6
|
+
ActiveRecord::Base.establish_connection adapter: 'sqlite3', database: ":memory:"
|
7
|
+
ActiveRecord::Base.connection
|
8
|
+
ActiveRecord::Migrator.migrate ActiveRecord::Migrator.migrations_path
|
9
|
+
end
|
10
|
+
|
11
|
+
context 'Single comparisons' do
|
12
|
+
|
13
|
+
it 'Equals' do
|
14
|
+
q = 'name = abcd'
|
15
|
+
Country.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"countries\".* FROM \"countries\" WHERE \"countries\".\"name\" = 'abcd'"
|
16
|
+
end
|
17
|
+
|
18
|
+
it 'Not equals' do
|
19
|
+
q = 'name != abcd'
|
20
|
+
Country.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"countries\".* FROM \"countries\" WHERE (\"countries\".\"name\" != 'abcd')"
|
21
|
+
end
|
22
|
+
|
23
|
+
it 'Greater than' do
|
24
|
+
q = 'name > abcd'
|
25
|
+
Country.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"countries\".* FROM \"countries\" WHERE (\"countries\".\"name\" > 'abcd')"
|
26
|
+
end
|
27
|
+
|
28
|
+
it 'Greater or equals than' do
|
29
|
+
q = 'name >= abcd'
|
30
|
+
Country.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"countries\".* FROM \"countries\" WHERE (\"countries\".\"name\" >= 'abcd')"
|
31
|
+
end
|
32
|
+
|
33
|
+
it 'Less than' do
|
34
|
+
q = 'name < abcd'
|
35
|
+
Country.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"countries\".* FROM \"countries\" WHERE (\"countries\".\"name\" < 'abcd')"
|
36
|
+
end
|
37
|
+
|
38
|
+
it 'Less or equals than' do
|
39
|
+
q = 'name <= abcd'
|
40
|
+
Country.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"countries\".* FROM \"countries\" WHERE (\"countries\".\"name\" <= 'abcd')"
|
41
|
+
end
|
42
|
+
|
43
|
+
it 'Contains' do
|
44
|
+
q = 'name % abcd'
|
45
|
+
Country.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"countries\".* FROM \"countries\" WHERE (\"countries\".\"name\" LIKE '%abcd%')"
|
46
|
+
end
|
47
|
+
|
48
|
+
end
|
49
|
+
|
50
|
+
context 'Coordinated comparisons' do
|
51
|
+
|
52
|
+
it 'And' do
|
53
|
+
q = 'id > 1234 & name = abcd'
|
54
|
+
Country.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"countries\".* FROM \"countries\" WHERE ((\"countries\".\"id\" > 1234 AND \"countries\".\"name\" = 'abcd'))"
|
55
|
+
end
|
56
|
+
|
57
|
+
it 'Or' do
|
58
|
+
q = 'id < 1234 | name % abcd'
|
59
|
+
Country.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"countries\".* FROM \"countries\" WHERE ((\"countries\".\"id\" < 1234 OR \"countries\".\"name\" LIKE '%abcd%'))"
|
60
|
+
end
|
61
|
+
|
62
|
+
it 'And then Or' do
|
63
|
+
q = 'id > 1234 & name = abcd | name % efgh'
|
64
|
+
Country.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"countries\".* FROM \"countries\" WHERE ((\"countries\".\"id\" > 1234 AND (\"countries\".\"name\" = 'abcd' OR \"countries\".\"name\" LIKE '%efgh%')))"
|
65
|
+
end
|
66
|
+
|
67
|
+
it 'With parentheses' do
|
68
|
+
q = '(id > 1234 & name = abcd) | name % efgh'
|
69
|
+
Country.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"countries\".* FROM \"countries\" WHERE ((\"countries\".\"name\" LIKE '%efgh%' OR (\"countries\".\"id\" > 1234 AND \"countries\".\"name\" = 'abcd')))"
|
70
|
+
end
|
71
|
+
|
72
|
+
end
|
73
|
+
|
74
|
+
context 'Model joins' do
|
75
|
+
|
76
|
+
it 'Parent join' do
|
77
|
+
q = 'country.name % abcd'
|
78
|
+
City.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"cities\".* FROM \"cities\" LEFT OUTER JOIN \"countries\" ON \"countries\".\"id\" = \"cities\".\"country_id\" WHERE (\"countries\".\"name\" LIKE '%abcd%')"
|
79
|
+
end
|
80
|
+
|
81
|
+
it 'Children join' do
|
82
|
+
q = 'cities.name % abcd'
|
83
|
+
Country.search(NQL.to_ransack(q)).result.should produce_sql "SELECT \"countries\".* FROM \"countries\" LEFT OUTER JOIN \"cities\" ON \"cities\".\"country_id\" = \"countries\".\"id\" WHERE (\"cities\".\"name\" LIKE '%abcd%')"
|
84
|
+
end
|
85
|
+
|
86
|
+
it 'Children join distinct' do
|
87
|
+
q = 'cities.name % abcd'
|
88
|
+
Country.search(NQL.to_ransack(q)).result(distinct: true).should produce_sql "SELECT DISTINCT \"countries\".* FROM \"countries\" LEFT OUTER JOIN \"cities\" ON \"cities\".\"country_id\" = \"countries\".\"id\" WHERE (\"cities\".\"name\" LIKE '%abcd%')"
|
89
|
+
end
|
90
|
+
|
91
|
+
end
|
92
|
+
|
93
|
+
end
|
metadata
ADDED
@@ -0,0 +1,139 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: nql
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.0.1
|
5
|
+
prerelease:
|
6
|
+
platform: ruby
|
7
|
+
authors:
|
8
|
+
- Gabriel Naiman
|
9
|
+
autorequire:
|
10
|
+
bindir: bin
|
11
|
+
cert_chain: []
|
12
|
+
date: 2012-11-08 00:00:00.000000000 Z
|
13
|
+
dependencies:
|
14
|
+
- !ruby/object:Gem::Dependency
|
15
|
+
name: treetop
|
16
|
+
requirement: &25509144 !ruby/object:Gem::Requirement
|
17
|
+
none: false
|
18
|
+
requirements:
|
19
|
+
- - ! '>='
|
20
|
+
- !ruby/object:Gem::Version
|
21
|
+
version: '0'
|
22
|
+
type: :runtime
|
23
|
+
prerelease: false
|
24
|
+
version_requirements: *25509144
|
25
|
+
- !ruby/object:Gem::Dependency
|
26
|
+
name: activerecord
|
27
|
+
requirement: &25508652 !ruby/object:Gem::Requirement
|
28
|
+
none: false
|
29
|
+
requirements:
|
30
|
+
- - ! '>='
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: 3.2.0
|
33
|
+
type: :runtime
|
34
|
+
prerelease: false
|
35
|
+
version_requirements: *25508652
|
36
|
+
- !ruby/object:Gem::Dependency
|
37
|
+
name: activesupport
|
38
|
+
requirement: &25508232 !ruby/object:Gem::Requirement
|
39
|
+
none: false
|
40
|
+
requirements:
|
41
|
+
- - ! '>='
|
42
|
+
- !ruby/object:Gem::Version
|
43
|
+
version: 3.2.0
|
44
|
+
type: :runtime
|
45
|
+
prerelease: false
|
46
|
+
version_requirements: *25508232
|
47
|
+
- !ruby/object:Gem::Dependency
|
48
|
+
name: ransack
|
49
|
+
requirement: &25507908 !ruby/object:Gem::Requirement
|
50
|
+
none: false
|
51
|
+
requirements:
|
52
|
+
- - ! '>='
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '0'
|
55
|
+
type: :runtime
|
56
|
+
prerelease: false
|
57
|
+
version_requirements: *25507908
|
58
|
+
- !ruby/object:Gem::Dependency
|
59
|
+
name: sqlite3
|
60
|
+
requirement: &25507440 !ruby/object:Gem::Requirement
|
61
|
+
none: false
|
62
|
+
requirements:
|
63
|
+
- - ! '>='
|
64
|
+
- !ruby/object:Gem::Version
|
65
|
+
version: '0'
|
66
|
+
type: :development
|
67
|
+
prerelease: false
|
68
|
+
version_requirements: *25507440
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: rspec
|
71
|
+
requirement: &25506972 !ruby/object:Gem::Requirement
|
72
|
+
none: false
|
73
|
+
requirements:
|
74
|
+
- - ! '>='
|
75
|
+
- !ruby/object:Gem::Version
|
76
|
+
version: '0'
|
77
|
+
type: :development
|
78
|
+
prerelease: false
|
79
|
+
version_requirements: *25506972
|
80
|
+
description: Natural Query Language built on top of ActiveRecord and Ransack
|
81
|
+
email:
|
82
|
+
- gabynaiman@gmail.com
|
83
|
+
executables: []
|
84
|
+
extensions: []
|
85
|
+
extra_rdoc_files: []
|
86
|
+
files:
|
87
|
+
- .gitignore
|
88
|
+
- Gemfile
|
89
|
+
- LICENSE
|
90
|
+
- README.md
|
91
|
+
- Rakefile
|
92
|
+
- lib/nql.rb
|
93
|
+
- lib/nql/grammar.rb
|
94
|
+
- lib/nql/grammar.treetop
|
95
|
+
- lib/nql/version.rb
|
96
|
+
- nql.gemspec
|
97
|
+
- spec/comparison_parser_spec.rb
|
98
|
+
- spec/coordination_parser_spec.rb
|
99
|
+
- spec/migrations/20121108154439_create_countries.rb
|
100
|
+
- spec/migrations/20121108154508_create_cities.rb
|
101
|
+
- spec/models/city.rb
|
102
|
+
- spec/models/country.rb
|
103
|
+
- spec/ransack_spec.rb
|
104
|
+
- spec/spec_helper.rb
|
105
|
+
- spec/sql_spec.rb
|
106
|
+
homepage: https://github.com/gabynaiman/nql
|
107
|
+
licenses: []
|
108
|
+
post_install_message:
|
109
|
+
rdoc_options: []
|
110
|
+
require_paths:
|
111
|
+
- lib
|
112
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
113
|
+
none: false
|
114
|
+
requirements:
|
115
|
+
- - ! '>='
|
116
|
+
- !ruby/object:Gem::Version
|
117
|
+
version: '0'
|
118
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
119
|
+
none: false
|
120
|
+
requirements:
|
121
|
+
- - ! '>='
|
122
|
+
- !ruby/object:Gem::Version
|
123
|
+
version: '0'
|
124
|
+
requirements: []
|
125
|
+
rubyforge_project:
|
126
|
+
rubygems_version: 1.8.16
|
127
|
+
signing_key:
|
128
|
+
specification_version: 3
|
129
|
+
summary: Natural Query Language built on top of ActiveRecord and Ransack
|
130
|
+
test_files:
|
131
|
+
- spec/comparison_parser_spec.rb
|
132
|
+
- spec/coordination_parser_spec.rb
|
133
|
+
- spec/migrations/20121108154439_create_countries.rb
|
134
|
+
- spec/migrations/20121108154508_create_cities.rb
|
135
|
+
- spec/models/city.rb
|
136
|
+
- spec/models/country.rb
|
137
|
+
- spec/ransack_spec.rb
|
138
|
+
- spec/spec_helper.rb
|
139
|
+
- spec/sql_spec.rb
|