File: eager_graph_eager_spec.rb

package info (click to toggle)
ruby-sequel 5.63.0-2
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 10,408 kB
  • sloc: ruby: 113,747; makefile: 3
file content (111 lines) | stat: -rw-r--r-- 7,180 bytes parent folder | download | duplicates (3)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
require_relative "spec_helper"

describe "eager_graph_eager plugin" do
  before do
    @c = Class.new(Sequel::Model(:items))
    @c.columns :id, :parent_id
    @c.plugin :eager_graph_eager
    @c.one_to_many :children, :class=>@c, :key=>:parent_id
    @c.many_to_one :parent, :class=>@c
    @c.db.sqls
  end

  it "should support Dataset#eager_graph_eager for eager loading dependencies of eager_graph associations for one_to_many associations" do
    a = @c.eager_graph(:children).
      with_fetch([{:id=>1, :parent_id=>nil, :children_id=>3, :children_parent_id=>1}, {:id=>2, :parent_id=>nil}]).
      eager_graph_eager([:children], :children=>proc{|ds| ds.with_fetch(:id=>4, :parent_id=>3)}).
      all
    @c.db.sqls.must_equal ["SELECT items.id, items.parent_id, children.id AS children_id, children.parent_id AS children_parent_id FROM items LEFT OUTER JOIN items AS children ON (children.parent_id = items.id)",
      "SELECT * FROM items WHERE (items.parent_id IN (3))"]

    a.must_equal [@c.load(:id=>1, :parent_id=>nil), @c.load(:id=>2, :parent_id=>nil)]
    a.map(&:children).must_equal [[@c.load(:id=>3, :parent_id=>1)], []]
    a.first.children.first.children.must_equal [@c.load(:id=>4, :parent_id=>3)]
    @c.db.sqls.must_equal []
  end

  it "should support Dataset#eager_graph_eager for eager loading dependencies of eager_graph associations for many_to_one associations" do
    a = @c.eager_graph(:parent).
      with_fetch([{:id=>4, :parent_id=>3, :parent_id_0=>3, :parent_parent_id=>1}, {:id=>2, :parent_id=>nil}]).
      eager_graph_eager([:parent], :parent=>proc{|ds| ds.with_fetch(:id=>1, :parent_id=>nil)}).
      all
    @c.db.sqls.must_equal ["SELECT items.id, items.parent_id, parent.id AS parent_id_0, parent.parent_id AS parent_parent_id FROM items LEFT OUTER JOIN items AS parent ON (parent.id = items.parent_id)",
      "SELECT * FROM items WHERE (items.id IN (1))"]

    a.must_equal [@c.load(:id=>4, :parent_id=>3), @c.load(:id=>2, :parent_id=>nil)]
    a.map(&:parent).must_equal [@c.load(:id=>3, :parent_id=>1), nil]
    a.first.parent.parent.must_equal @c.load(:id=>1, :parent_id=>nil)
    @c.db.sqls.must_equal []
  end

  it "should support multiple entries in dependency chain" do
    a = @c.eager_graph(:children=>:children).
      with_fetch([{:id=>1, :parent_id=>nil, :children_id=>3, :children_parent_id=>1, :children_0_id=>4, :children_0_parent_id=>3}, {:id=>2, :parent_id=>nil}]).
      eager_graph_eager([:children, :children], :children=>proc{|ds| ds.with_fetch(:id=>5, :parent_id=>4)}).
      all
    @c.db.sqls.must_equal ["SELECT items.id, items.parent_id, children.id AS children_id, children.parent_id AS children_parent_id, children_0.id AS children_0_id, children_0.parent_id AS children_0_parent_id FROM items LEFT OUTER JOIN items AS children ON (children.parent_id = items.id) LEFT OUTER JOIN items AS children_0 ON (children_0.parent_id = children.id)",
      "SELECT * FROM items WHERE (items.parent_id IN (4))"]

    a.must_equal [@c.load(:id=>1, :parent_id=>nil), @c.load(:id=>2, :parent_id=>nil)]
    a.map(&:children).must_equal [[@c.load(:id=>3, :parent_id=>1)], []]
    a.first.children.first.children.must_equal [@c.load(:id=>4, :parent_id=>3)]
    a.first.children.first.children.first.children.must_equal [@c.load(:id=>5, :parent_id=>4)]
    @c.db.sqls.must_equal []
  end

  it "should support multiple dependency chains" do
    a = @c.eager_graph(:children, :parent).
      with_fetch([{:id=>4, :parent_id=>3, :children_id=>5, :children_parent_id=>4, :parent_id_0=>3, :parent_parent_id=>1}, {:id=>2, :parent_id=>nil}]).
      eager_graph_eager([:children], :children=>proc{|ds| ds.with_fetch(:id=>6, :parent_id=>5)}).
      eager_graph_eager([:parent], :parent=>proc{|ds| ds.with_fetch(:id=>1, :parent_id=>nil)}).
      all
    @c.db.sqls.must_equal ["SELECT items.id, items.parent_id, children.id AS children_id, children.parent_id AS children_parent_id, parent.id AS parent_id_0, parent.parent_id AS parent_parent_id FROM items LEFT OUTER JOIN items AS children ON (children.parent_id = items.id) LEFT OUTER JOIN items AS parent ON (parent.id = items.parent_id)",
      "SELECT * FROM items WHERE (items.parent_id IN (5))",
      "SELECT * FROM items WHERE (items.id IN (1))"]

    a.must_equal [@c.load(:id=>4, :parent_id=>3), @c.load(:id=>2, :parent_id=>nil)]
    a.map(&:children).must_equal [[@c.load(:id=>5, :parent_id=>4)], []]
    a.map(&:parent).must_equal [@c.load(:id=>3, :parent_id=>1), nil]
    a.first.children.first.children.must_equal [@c.load(:id=>6, :parent_id=>5)]
    a.first.parent.parent.must_equal @c.load(:id=>1, :parent_id=>nil)
    @c.db.sqls.must_equal []
  end

  it "should raise for invalid dependency chains" do
    proc{@c.dataset.eager_graph_eager([], :children)}.must_raise Sequel::Error
    proc{@c.dataset.eager_graph_eager(:children, :children)}.must_raise Sequel::Error
    proc{@c.dataset.eager_graph_eager(['foo'], :children)}.must_raise Sequel::Error
    proc{@c.dataset.eager_graph_eager([:foo], :children)}.must_raise Sequel::Error
  end

  it "should handle cases where not all associated objects are unique" do
    a = @c.eager_graph(:parent=>:children).
      with_fetch([
        {:id=>4, :parent_id=>3, :parent_id_0=>3, :parent_parent_id=>1, :children_id=>4, :children_parent_id=>3},
        {:id=>5, :parent_id=>3, :parent_id_0=>3, :parent_parent_id=>1, :children_id=>4, :children_parent_id=>3},
        {:id=>4, :parent_id=>3, :parent_id_0=>3, :parent_parent_id=>1, :children_id=>5, :children_parent_id=>3},
        {:id=>5, :parent_id=>3, :parent_id_0=>3, :parent_parent_id=>1, :children_id=>5, :children_parent_id=>3}
      ]).
      eager_graph_eager([:parent], :parent=>proc{|ds| ds.with_fetch(:id=>1, :parent_id=>nil)}).
      all
    @c.db.sqls.must_equal ["SELECT items.id, items.parent_id, parent.id AS parent_id_0, parent.parent_id AS parent_parent_id, children.id AS children_id, children.parent_id AS children_parent_id FROM items LEFT OUTER JOIN items AS parent ON (parent.id = items.parent_id) LEFT OUTER JOIN items AS children ON (children.parent_id = parent.id)",
      "SELECT * FROM items WHERE (items.id IN (1))"]

    a.must_equal [@c.load(:id=>4, :parent_id=>3), @c.load(:id=>5, :parent_id=>3)]
    a.map(&:parent).must_equal [@c.load(:id=>3, :parent_id=>1), @c.load(:id=>3, :parent_id=>1)]
    a.map(&:parent).map(&:children).must_equal [a, a]
    a.map(&:parent).map(&:parent).must_equal [@c.load(:id=>1, :parent_id=>nil), @c.load(:id=>1, :parent_id=>nil)]
    @c.db.sqls.must_equal []
  end

  it "should not affect eager_graph usage without eager_graph_eager" do
    a = @c.eager_graph(:children).
      with_fetch([{:id=>1, :parent_id=>nil, :children_id=>3, :children_parent_id=>1}, {:id=>2, :parent_id=>nil}]).
      all
    @c.db.sqls.must_equal ["SELECT items.id, items.parent_id, children.id AS children_id, children.parent_id AS children_parent_id FROM items LEFT OUTER JOIN items AS children ON (children.parent_id = items.id)"]

    a.must_equal [@c.load(:id=>1, :parent_id=>nil), @c.load(:id=>2, :parent_id=>nil)]
    a.map(&:children).must_equal [[@c.load(:id=>3, :parent_id=>1)], []]
    @c.db.sqls.must_equal []
  end
end