nexter 0.0.5 → 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/lib/nexter.rb +6 -3
- data/lib/nexter/compass.rb +4 -6
- data/lib/nexter/query.rb +37 -0
- data/lib/nexter/query/direction.rb +25 -0
- data/lib/nexter/query/section.rb +38 -0
- data/lib/nexter/version.rb +1 -1
- data/lib/nexter/wrap.rb +18 -30
- data/nexter.gemspec +0 -1
- data/spec/book.rb +7 -2
- data/spec/nexter/compass_spec.rb +1 -1
- data/spec/nexter/query/direction_spec.rb +21 -0
- data/spec/nexter/query/section_spec.rb +21 -0
- data/spec/nexter/query_spec.rb +23 -0
- data/spec/nexter/wrap_spec.rb +52 -9
- data/spec/spec_helper.rb +4 -3
- metadata +12 -20
- data/lib/nexter/derange.rb +0 -66
- data/spec/nexter/derange_spec.rb +0 -53
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 9fe3377bb4621f5dd4334001c71bfc251c1aab7a
|
4
|
+
data.tar.gz: b40d8a4a5dd7cfc932313cbceb18b538008e9bad
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: b19d7a48206c5276a18d6d6805c771d5d3f443047504d54b074a72ee1cfe9f77bf57743b5381f7a1738d276d72980f15f5df7af21168f7912edd13a8f33aa587
|
7
|
+
data.tar.gz: 7214177fefacbade18b798b5058a4b01979199fc4837ecfe5858af830fa3012a59e6fc184eddd0d13b0ce52e304589cd211bb07c0a9f4fbe867c2fd3d97121fc
|
data/.gitignore
CHANGED
data/lib/nexter.rb
CHANGED
@@ -1,11 +1,14 @@
|
|
1
1
|
require "bundler/setup"
|
2
2
|
|
3
|
-
require "active_support/
|
4
|
-
require "active_support/dependencies"
|
3
|
+
require "active_support/all"
|
4
|
+
# require "active_support/dependencies"
|
5
5
|
|
6
6
|
require "nexter/version"
|
7
7
|
require "nexter/wrap"
|
8
|
-
require "nexter/
|
8
|
+
require "nexter/query"
|
9
|
+
require "nexter/query/section"
|
10
|
+
require "nexter/query/direction"
|
11
|
+
|
9
12
|
require "nexter/compass"
|
10
13
|
require "nexter/eyecontact"
|
11
14
|
|
data/lib/nexter/compass.rb
CHANGED
@@ -14,17 +14,15 @@ module Nexter
|
|
14
14
|
end
|
15
15
|
|
16
16
|
def bracket
|
17
|
-
|
17
|
+
sign == -1 ? '<' : '>'
|
18
18
|
end
|
19
19
|
|
20
20
|
def redirection
|
21
|
-
|
21
|
+
sign == -1 ? 'DESC' : 'ASC'
|
22
22
|
end
|
23
23
|
|
24
|
-
|
25
|
-
|
26
|
-
def signature
|
27
|
-
DIREC[direction.to_sym] * GOTO[goto]
|
24
|
+
def sign
|
25
|
+
DIREC[direction.downcase.to_sym] * GOTO[goto]
|
28
26
|
end
|
29
27
|
end
|
30
28
|
end
|
data/lib/nexter/query.rb
ADDED
@@ -0,0 +1,37 @@
|
|
1
|
+
module Nexter
|
2
|
+
class Query
|
3
|
+
attr_reader :columns, :compass, :wheres, :reorders
|
4
|
+
|
5
|
+
def initialize(columns, goto)
|
6
|
+
@columns = columns
|
7
|
+
@compass = Compass.new(goto)
|
8
|
+
@wheres = []
|
9
|
+
@reorders = []
|
10
|
+
iterate
|
11
|
+
end
|
12
|
+
|
13
|
+
def iterate
|
14
|
+
columns = @columns.dup
|
15
|
+
|
16
|
+
while column = columns.pop do
|
17
|
+
section = Section.new(columns)
|
18
|
+
direction = Direction.new(column, compass)
|
19
|
+
|
20
|
+
reorders.unshift("#{column[:col]} #{direction.compass.redirection}")
|
21
|
+
|
22
|
+
next unless direction.slice
|
23
|
+
|
24
|
+
@wheres << "#{section.sql}#{section.blank? ? '' : ' AND '}#{direction.sql}"
|
25
|
+
end
|
26
|
+
|
27
|
+
# binding.pry
|
28
|
+
@wheres.compact!
|
29
|
+
end
|
30
|
+
|
31
|
+
alias sql iterate
|
32
|
+
|
33
|
+
|
34
|
+
|
35
|
+
|
36
|
+
end
|
37
|
+
end
|
@@ -0,0 +1,25 @@
|
|
1
|
+
class Nexter::Query
|
2
|
+
class Direction
|
3
|
+
attr_reader :column, :compass
|
4
|
+
delegate :goto, :bracket, :redirection, to: :compass
|
5
|
+
|
6
|
+
def initialize(column, compass)
|
7
|
+
@column = column
|
8
|
+
@compass = compass
|
9
|
+
compass.direction = column[:dir]
|
10
|
+
end
|
11
|
+
|
12
|
+
def slice
|
13
|
+
if column[:val].present?
|
14
|
+
delimited = "#{column[:col]} #{bracket} '#{column[:val]}'"
|
15
|
+
delimited.concat(" OR #{column[:col]} IS NULL") if @compass.sign == 1
|
16
|
+
"(#{delimited})"
|
17
|
+
elsif @compass.sign == -1
|
18
|
+
"#{column[:col]} IS NOT NULL"
|
19
|
+
end
|
20
|
+
end
|
21
|
+
alias sql slice
|
22
|
+
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
@@ -0,0 +1,38 @@
|
|
1
|
+
class Nexter::Query
|
2
|
+
|
3
|
+
# Iterates over the columns, extracts their values
|
4
|
+
# and builds query part that says :
|
5
|
+
#
|
6
|
+
# > "col1 = value1"
|
7
|
+
# > "col2 = value2"
|
8
|
+
#
|
9
|
+
# then joins them with AND :
|
10
|
+
#
|
11
|
+
# > "col1 = value1 AND col2 = value2"
|
12
|
+
#
|
13
|
+
class Section
|
14
|
+
attr_reader :columns, :compass
|
15
|
+
|
16
|
+
# TODO : check if compass is needed (don't think so!)
|
17
|
+
def initialize(columns)
|
18
|
+
@columns = columns
|
19
|
+
@compass = compass
|
20
|
+
end
|
21
|
+
|
22
|
+
def iterate
|
23
|
+
@where ||= columns.map do |column|
|
24
|
+
if column[:val]
|
25
|
+
"#{column[:col]} = '#{column[:val]}'"
|
26
|
+
else
|
27
|
+
"#{column[:col]} IS NULL"
|
28
|
+
end
|
29
|
+
end.join(' AND ')
|
30
|
+
end
|
31
|
+
alias sql iterate
|
32
|
+
|
33
|
+
def blank?
|
34
|
+
iterate.blank?
|
35
|
+
end
|
36
|
+
|
37
|
+
end #section
|
38
|
+
end
|
data/lib/nexter/version.rb
CHANGED
data/lib/nexter/wrap.rb
CHANGED
@@ -7,17 +7,11 @@ module Nexter
|
|
7
7
|
# extracted values from the relation
|
8
8
|
attr_reader :order_values, :associations
|
9
9
|
|
10
|
-
# list of build strings for finale SQL
|
11
|
-
attr_reader :wheres, :reorders
|
12
|
-
|
13
|
-
|
14
10
|
def initialize(relation, model)
|
15
11
|
@relation = relation
|
16
12
|
@model = model
|
17
13
|
@order_values = parse_order( relation.order_values )
|
18
14
|
@associations = relation.includes_values
|
19
|
-
# @cursor_column = extract_attr( @ranges.pop )
|
20
|
-
# @cursor = model.send( @cursor_column.to_sym, )
|
21
15
|
end
|
22
16
|
|
23
17
|
# TODO : let user determine which strategy to choose:
|
@@ -31,37 +25,31 @@ module Nexter
|
|
31
25
|
end
|
32
26
|
|
33
27
|
def after
|
34
|
-
|
35
|
-
|
36
|
-
# r = r.order(:id) if derange.reorder
|
37
|
-
r
|
28
|
+
query = Query.new(map_column_values, :next)
|
29
|
+
relation.where( query.wheres.join(' OR ') )
|
38
30
|
end
|
39
31
|
|
40
32
|
def before
|
41
|
-
|
42
|
-
relation.where( wheres.join(' OR ') ).
|
33
|
+
query = Query.new(map_column_values, :previous)
|
34
|
+
relation.where( query.wheres.join(' OR ') ).
|
35
|
+
reorder( query.reorders.join(", ") )
|
43
36
|
end
|
44
37
|
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
# 2. (a and b > b.val)
|
49
|
-
# 3. (a > a.val))
|
50
|
-
def cut(goto = :next)
|
51
|
-
order_vals = @order_values.dup
|
52
|
-
@wheres = []
|
53
|
-
@reorders = []
|
54
|
-
derange = Nexter::Derange.new(model, goto)
|
55
|
-
|
56
|
-
while order_col = order_vals.pop do
|
57
|
-
derange.set_vals(order_vals, order_col)
|
58
|
-
|
59
|
-
# should be derange's result
|
60
|
-
wheres << derange.where
|
61
|
-
reorders.unshift(derange.reorder)
|
38
|
+
def map_column_values
|
39
|
+
@column_values ||= @order_values.map do |column|
|
40
|
+
{col: column[0], val: value_of(column[0]), dir: column[1]}
|
62
41
|
end
|
42
|
+
end
|
63
43
|
|
64
|
-
|
44
|
+
private
|
45
|
+
def value_of(cursor)
|
46
|
+
splits = cursor.split(".")
|
47
|
+
result = if splits.first == model.class.table_name || splits.size == 1
|
48
|
+
model.send(splits.last) if model.respond_to?(splits.last)
|
49
|
+
else
|
50
|
+
asso = model.class.reflections.keys.grep(/#{splits.first.singularize}/).first
|
51
|
+
asso = model.send(asso) and asso.send(splits.last)
|
52
|
+
end
|
65
53
|
end
|
66
54
|
|
67
55
|
# helper to turn mixed order attributes to a consistant
|
data/nexter.gemspec
CHANGED
data/spec/book.rb
CHANGED
@@ -1,13 +1,18 @@
|
|
1
1
|
Book = Struct.new(:genre, :name, :title) do
|
2
2
|
|
3
|
+
|
3
4
|
def id; 71; end
|
4
5
|
|
5
6
|
def self.table_name
|
6
7
|
"books"
|
7
8
|
end
|
8
9
|
|
9
|
-
def
|
10
|
-
{
|
10
|
+
def self.sanitize(args)
|
11
|
+
"'#{args}'"
|
12
|
+
end
|
13
|
+
|
14
|
+
def self.reflections
|
15
|
+
{author: "blurb"}
|
11
16
|
end
|
12
17
|
|
13
18
|
def author
|
data/spec/nexter/compass_spec.rb
CHANGED
@@ -0,0 +1,21 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
|
3
|
+
describe Nexter::Query::Direction do
|
4
|
+
|
5
|
+
let(:compass) {Nexter::Compass.new(:next)}
|
6
|
+
let(:columns) {[
|
7
|
+
{col: "authors.name", val: "nabokov", dir: "asc"},
|
8
|
+
{col: "genre", val: "novel", dir: "asc"},
|
9
|
+
{col: "title", val: "ada", dir: "asc"}
|
10
|
+
]}
|
11
|
+
|
12
|
+
describe "#slice", focus: true do
|
13
|
+
|
14
|
+
it "should be awesome" do
|
15
|
+
direction = Nexter::Query::Direction.new(columns.pop, compass)
|
16
|
+
|
17
|
+
expect(direction.slice).to eq("(title > 'ada' OR title IS NULL)")
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
|
3
|
+
describe Nexter::Query::Section, focus: true do
|
4
|
+
|
5
|
+
# let(:compass) {Nexter::Compass.new(:next)}
|
6
|
+
let(:columns) {[
|
7
|
+
{col: "authors.name", val: "nabokov", dir: "asc"},
|
8
|
+
{col: "genre", val: "novel", dir: "asc"},
|
9
|
+
{col: "title", val: "ada", dir: "asc"}
|
10
|
+
]}
|
11
|
+
|
12
|
+
describe "#iterate" do
|
13
|
+
|
14
|
+
it "should iterate mother fucker" do
|
15
|
+
section = Nexter::Query::Section.new(columns)
|
16
|
+
|
17
|
+
expect(section.iterate).to eq(
|
18
|
+
"authors.name = 'nabokov' AND genre = 'novel' AND title = 'ada'")
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
require "spec_helper"
|
2
|
+
|
3
|
+
describe Nexter::Query, broken: true do
|
4
|
+
|
5
|
+
let(:columns) {[
|
6
|
+
{col: "authors.name", val: "nabokov", dir: "asc"},
|
7
|
+
{col: "genre", val: "novel", dir: "asc"},
|
8
|
+
{col: "title", val: "ada", dir: "asc"}
|
9
|
+
]}
|
10
|
+
|
11
|
+
describe "#where" do
|
12
|
+
|
13
|
+
it "builds the query from its ashes" do
|
14
|
+
query = Nexter::Query.new(columns, :next)
|
15
|
+
|
16
|
+
expect(query.wheres).to eq(
|
17
|
+
[ "authors.name = 'nabokov' AND genre = 'novel' AND title > 'ada'",
|
18
|
+
"authors.name = 'nabokov' AND genre > 'novel'",
|
19
|
+
"authors.name > 'nabokov'"])
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
end
|
data/spec/nexter/wrap_spec.rb
CHANGED
@@ -1,8 +1,23 @@
|
|
1
1
|
require "spec_helper"
|
2
2
|
|
3
3
|
describe Nexter::Wrap do
|
4
|
+
let(:relation) {Relation.new.tap{|r| r.order_values=["authors.name","genre","title"]}}
|
5
|
+
let(:book) {Book.new("novel", "nabokov", "ada")}
|
4
6
|
|
5
|
-
|
7
|
+
describe "#map_column_values", focus: true do
|
8
|
+
|
9
|
+
it "should create hashes of attributes out of the order values" do
|
10
|
+
nexter = Nexter::Wrap.new(relation, book)
|
11
|
+
|
12
|
+
expect(nexter.map_column_values).to eq(
|
13
|
+
[ {col: "authors.name", val: "nabokov", dir: "asc"},
|
14
|
+
{col: "genre", val: "novel", dir: "asc"},
|
15
|
+
{col: "title", val: "ada", dir: "asc"}
|
16
|
+
])
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
context "no missing values", broken: true do
|
6
21
|
let(:relation) { Relation.new.tap {|rel| rel.order_values=["authors.name", "title"]} }
|
7
22
|
let(:book) { Book.new("novel", "nabokov", "ada") }
|
8
23
|
|
@@ -27,36 +42,64 @@ describe Nexter::Wrap do
|
|
27
42
|
nexter = Nexter::Wrap.new(relation, book)
|
28
43
|
nexter.before
|
29
44
|
|
30
|
-
expect(nexter.reorders[0]).to eq(" authors.name
|
45
|
+
expect(nexter.reorders[0]).to eq(" authors.name DESC")
|
31
46
|
end
|
32
47
|
end
|
33
48
|
end
|
34
49
|
|
35
|
-
context "nil values" do
|
36
|
-
let(:relation) {
|
50
|
+
context "nil values", broken: true do
|
51
|
+
let(:relation) {Relation.new.tap {|r| r.order_values=["genre", "title", "id"]} }
|
37
52
|
|
38
|
-
describe "#wheres" do
|
53
|
+
describe "#wheres with Book#genre IS NULL" do
|
39
54
|
let(:book) { Book.new(nil, "nabokov", "Ada") }
|
40
55
|
|
41
56
|
it "has the right SQL condition" do
|
57
|
+
skip
|
42
58
|
nexter = Nexter::Wrap.new(relation, book)
|
43
59
|
nexter.after
|
44
60
|
|
45
|
-
expect(nexter.wheres
|
61
|
+
expect(nexter.wheres).to eq("(genre IS NULL AND title > 'Ada')")
|
46
62
|
end
|
47
63
|
end
|
48
64
|
|
49
|
-
describe "#wheres" do
|
65
|
+
describe "#wheres with Book#title IS NULL" do
|
50
66
|
let(:book) { Book.new("novel", "nabokov", nil) }
|
51
67
|
|
52
|
-
it "has the right SQL condition" do
|
68
|
+
it "has the right SQL condition for NEXT" do
|
53
69
|
nexter = Nexter::Wrap.new(relation, book)
|
54
70
|
nexter.after
|
55
71
|
|
56
|
-
expect(nexter.wheres[0]).to
|
72
|
+
expect(nexter.wheres[0]).to \
|
73
|
+
eq("(genre = 'novel' AND title IS NULL AND id > '#{book.id}')")
|
74
|
+
|
75
|
+
expect(nexter.wheres[1]).to \
|
76
|
+
eq("( genre > 'novel')")
|
77
|
+
end
|
78
|
+
|
79
|
+
|
80
|
+
it "has the right SQL condition for PREVIOUS" do
|
81
|
+
nexter = Nexter::Wrap.new(relation, book)
|
82
|
+
nexter.before
|
83
|
+
|
84
|
+
expect(nexter.wheres[0]).to \
|
85
|
+
eq("(genre = 'novel' AND title IS NULL AND id < '#{book.id}')")
|
86
|
+
|
87
|
+
expect(nexter.wheres[1]).to \
|
88
|
+
eq("( genre > 'novel')")
|
57
89
|
end
|
58
90
|
end
|
59
91
|
|
92
|
+
describe "#after with Book#title IS NULL" do
|
93
|
+
let(:book) { Book.new("novel", "nabokov", nil) }
|
94
|
+
|
95
|
+
it "has the right SQL condition" do
|
96
|
+
nexter = Nexter::Wrap.new(relation, book)
|
97
|
+
nexter.after
|
98
|
+
|
99
|
+
expect(nexter.wheres[0]).to \
|
100
|
+
eq("(genre = 'novel' AND title IS NULL AND id > '#{book.id}')")
|
101
|
+
end
|
102
|
+
end
|
60
103
|
end #contextr
|
61
104
|
|
62
105
|
end
|
data/spec/spec_helper.rb
CHANGED
@@ -7,13 +7,14 @@
|
|
7
7
|
require "book"
|
8
8
|
require "nexter"
|
9
9
|
require "active_support"
|
10
|
-
|
10
|
+
require "pry"
|
11
11
|
|
12
12
|
|
13
13
|
RSpec.configure do |config|
|
14
|
-
config.treat_symbols_as_metadata_keys_with_true_values = true
|
14
|
+
# config.treat_symbols_as_metadata_keys_with_true_values = true
|
15
15
|
config.run_all_when_everything_filtered = true
|
16
|
-
config.filter_run :
|
16
|
+
config.filter_run focus: true
|
17
|
+
config.filter_run_excluding broken: true
|
17
18
|
|
18
19
|
# Run specs in random order to surface order dependencies. If you find an
|
19
20
|
# order dependency and want to debug it, you can fix the order by providing
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: nexter
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0
|
4
|
+
version: 0.1.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Charles Sistovaris
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2015-12-21 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activerecord
|
@@ -94,20 +94,6 @@ dependencies:
|
|
94
94
|
- - ">="
|
95
95
|
- !ruby/object:Gem::Version
|
96
96
|
version: '0'
|
97
|
-
- !ruby/object:Gem::Dependency
|
98
|
-
name: pry-plus
|
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'
|
111
97
|
description: 'What is Nexter ? A misspelled tv show or a killer feature ? Almost :
|
112
98
|
it wraps your model with an ordered scope and cuts out the next and previous record.
|
113
99
|
It also works with associations & nested columns.'
|
@@ -128,14 +114,18 @@ files:
|
|
128
114
|
- Rakefile
|
129
115
|
- lib/nexter.rb
|
130
116
|
- lib/nexter/compass.rb
|
131
|
-
- lib/nexter/derange.rb
|
132
117
|
- lib/nexter/eyecontact.rb
|
118
|
+
- lib/nexter/query.rb
|
119
|
+
- lib/nexter/query/direction.rb
|
120
|
+
- lib/nexter/query/section.rb
|
133
121
|
- lib/nexter/version.rb
|
134
122
|
- lib/nexter/wrap.rb
|
135
123
|
- nexter.gemspec
|
136
124
|
- spec/book.rb
|
137
125
|
- spec/nexter/compass_spec.rb
|
138
|
-
- spec/nexter/
|
126
|
+
- spec/nexter/query/direction_spec.rb
|
127
|
+
- spec/nexter/query/section_spec.rb
|
128
|
+
- spec/nexter/query_spec.rb
|
139
129
|
- spec/nexter/wrap_spec.rb
|
140
130
|
- spec/spec_helper.rb
|
141
131
|
homepage: https://github.com/charly/nexter
|
@@ -158,7 +148,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
158
148
|
version: '0'
|
159
149
|
requirements: []
|
160
150
|
rubyforge_project:
|
161
|
-
rubygems_version: 2.
|
151
|
+
rubygems_version: 2.4.5.1
|
162
152
|
signing_key:
|
163
153
|
specification_version: 4
|
164
154
|
summary: Wrap your model with an ordered scope and cut out the _next_ and _previous_
|
@@ -166,6 +156,8 @@ summary: Wrap your model with an ordered scope and cut out the _next_ and _previ
|
|
166
156
|
test_files:
|
167
157
|
- spec/book.rb
|
168
158
|
- spec/nexter/compass_spec.rb
|
169
|
-
- spec/nexter/
|
159
|
+
- spec/nexter/query/direction_spec.rb
|
160
|
+
- spec/nexter/query/section_spec.rb
|
161
|
+
- spec/nexter/query_spec.rb
|
170
162
|
- spec/nexter/wrap_spec.rb
|
171
163
|
- spec/spec_helper.rb
|
data/lib/nexter/derange.rb
DELETED
@@ -1,66 +0,0 @@
|
|
1
|
-
module Nexter
|
2
|
-
class Derange
|
3
|
-
|
4
|
-
attr_reader :model, :compass, :table_name, :reorder
|
5
|
-
|
6
|
-
attr_accessor :delimiter, :columns, :trunks
|
7
|
-
|
8
|
-
delegate :goto, :bracket, :redirection, to: :compass
|
9
|
-
|
10
|
-
|
11
|
-
def initialize(model, goto)
|
12
|
-
@model = model
|
13
|
-
@table_name = model.class.table_name
|
14
|
-
@trunks = []
|
15
|
-
@reorder = false
|
16
|
-
@or_null = false
|
17
|
-
@compass = Nexter::Compass.new(goto)
|
18
|
-
end
|
19
|
-
|
20
|
-
def set_vals(order_vals, order_col)
|
21
|
-
@columns = order_vals
|
22
|
-
@delimiter = order_col[0]
|
23
|
-
compass.direction = order_col[1]
|
24
|
-
end
|
25
|
-
|
26
|
-
def where
|
27
|
-
"(#{range} #{range.blank? ? '' : 'AND'} #{slice})"
|
28
|
-
end
|
29
|
-
|
30
|
-
def reorder
|
31
|
-
" #{delimiter} #{redirection}"
|
32
|
-
end
|
33
|
-
|
34
|
-
def range
|
35
|
-
trunk = columns.map do |col|
|
36
|
-
if range_value = value_of(col[0])
|
37
|
-
# binding.pry
|
38
|
-
"#{col[0]} = #{model.class.sanitize range_value}"
|
39
|
-
else
|
40
|
-
"#{col[0]} IS NULL"
|
41
|
-
end
|
42
|
-
end.join(' AND ')
|
43
|
-
end
|
44
|
-
|
45
|
-
def slice
|
46
|
-
if val = value_of(delimiter)
|
47
|
-
d = model.class.sanitize val
|
48
|
-
delimited = "#{delimiter} #{bracket} #{d}"
|
49
|
-
else
|
50
|
-
# @reorder = true
|
51
|
-
"#{delimiter} IS NULL AND #{table_name}.id > #{model.id}"
|
52
|
-
end
|
53
|
-
end
|
54
|
-
|
55
|
-
def value_of(cursor)
|
56
|
-
splits = cursor.split(".")
|
57
|
-
result = if splits.first == table_name || splits.size == 1
|
58
|
-
model.send(splits.last)
|
59
|
-
else
|
60
|
-
# binding.pry
|
61
|
-
asso = model.class.reflections.keys.grep(/#{splits.first.singularize}/).first
|
62
|
-
asso = model.send(asso) and asso.send(splits.last)
|
63
|
-
end
|
64
|
-
end
|
65
|
-
end
|
66
|
-
end
|
data/spec/nexter/derange_spec.rb
DELETED
@@ -1,53 +0,0 @@
|
|
1
|
-
require "spec_helper"
|
2
|
-
|
3
|
-
describe Nexter::Derange do
|
4
|
-
|
5
|
-
let(:relation) { Relation.new }
|
6
|
-
let(:book) { Book.new("novel", "nabokov", "Ada") }
|
7
|
-
let(:nexter) { Nexter::Wrap.new(relation, book)}
|
8
|
-
|
9
|
-
describe "#range" do
|
10
|
-
it "returns a range of rows related to the current model (book)" do
|
11
|
-
derange = Nexter::Derange.new(book, :next)
|
12
|
-
derange.columns = nexter.order_values.tap(&:pop)
|
13
|
-
|
14
|
-
expect(derange.range).to eq("books.genre = 'novel' AND authors.name = 'nabokov'")
|
15
|
-
end
|
16
|
-
|
17
|
-
it "handles nil values" do
|
18
|
-
book.genre = nil
|
19
|
-
derange = Nexter::Derange.new(book, :next)
|
20
|
-
derange.columns = nexter.order_values.tap(&:pop)
|
21
|
-
|
22
|
-
expect(derange.range).to eq("books.genre IS NULL AND authors.name = 'nabokov'")
|
23
|
-
end
|
24
|
-
|
25
|
-
it "handles nil values (just for peace of mind)" do
|
26
|
-
book.name = nil
|
27
|
-
derange = Nexter::Derange.new(book, :next)
|
28
|
-
derange.columns = nexter.order_values.tap(&:pop)
|
29
|
-
|
30
|
-
expect(derange.range).to eq("books.genre = 'novel' AND authors.name IS NULL")
|
31
|
-
end
|
32
|
-
end
|
33
|
-
|
34
|
-
describe "#slice" do
|
35
|
-
it "returns a range of rows related to the current model (book)" do
|
36
|
-
derange = Nexter::Derange.new(book, :next)
|
37
|
-
order_col = nexter.order_values.pop
|
38
|
-
derange.set_vals(nexter.order_values, order_col)
|
39
|
-
|
40
|
-
expect(derange.slice).to eq("books.title > 'Ada'")
|
41
|
-
end
|
42
|
-
|
43
|
-
it "handles nil values" do
|
44
|
-
book.title = nil
|
45
|
-
derange = Nexter::Derange.new(book, :next)
|
46
|
-
order_col = nexter.order_values.pop
|
47
|
-
derange.set_vals(nexter.order_values, order_col)
|
48
|
-
|
49
|
-
expect(derange.slice).to eq("books.title IS NULL AND books.id > 71")
|
50
|
-
end
|
51
|
-
end
|
52
|
-
|
53
|
-
end
|