acts_as_graph 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.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 85713371daed2a84ea58c068c10a373165ad9b3b
4
+ data.tar.gz: 448fd7508d466a053e8568e3958326f0115bd68f
5
+ SHA512:
6
+ metadata.gz: da1fe3794e4b6d89fe824908f1d1767e3a45dad7206dcf1cb3b4dee9926ff253c6085e7e3067608f2a795dbee6362463a65fc8dc4cbf8346d33573fb43ff6cc5
7
+ data.tar.gz: 6f2f24d36ca3530c70f9d2a3f700e93fcb6b216b6305ee4a4d8e634445273b91427da69745eaa3f12ba0d0117845ad31438ac6367576f7a133649c342fc6a021
@@ -0,0 +1,4 @@
1
+ acts_as_graph-*.gem
2
+ .rspec_status
3
+ tags
4
+ .byebug_history
data/Gemfile ADDED
@@ -0,0 +1,3 @@
1
+ source 'https://rubygems.org'
2
+
3
+ gemspec
@@ -0,0 +1,32 @@
1
+ PATH
2
+ remote: .
3
+ specs:
4
+ acts_as_graph (0.0.1)
5
+ rspec
6
+
7
+ GEM
8
+ remote: https://rubygems.org/
9
+ specs:
10
+ diff-lcs (1.3)
11
+ rspec (3.7.0)
12
+ rspec-core (~> 3.7.0)
13
+ rspec-expectations (~> 3.7.0)
14
+ rspec-mocks (~> 3.7.0)
15
+ rspec-core (3.7.1)
16
+ rspec-support (~> 3.7.0)
17
+ rspec-expectations (3.7.0)
18
+ diff-lcs (>= 1.2.0, < 2.0)
19
+ rspec-support (~> 3.7.0)
20
+ rspec-mocks (3.7.0)
21
+ diff-lcs (>= 1.2.0, < 2.0)
22
+ rspec-support (~> 3.7.0)
23
+ rspec-support (3.7.1)
24
+
25
+ PLATFORMS
26
+ ruby
27
+
28
+ DEPENDENCIES
29
+ acts_as_graph!
30
+
31
+ BUNDLED WITH
32
+ 1.16.1
@@ -0,0 +1,3 @@
1
+ # acts_as_graph
2
+
3
+ working in progress
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env rake
2
+
3
+ require 'bundler/gem_tasks'
4
+ require 'rspec/core/rake_task'
5
+
6
+ RSpec::Core::RakeTask.new(:spec)
7
+
8
+ task default: [:spec]
@@ -0,0 +1,26 @@
1
+ lib = File.expand_path('../lib/', __FILE__)
2
+ $:.unshift lib unless $:.include?(lib)
3
+
4
+ require 'acts_as_graph/version'
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = 'acts_as_graph'
8
+ s.version = ActsAsGraph::VERSION
9
+ s.platform = Gem::Platform::RUBY
10
+ s.authors = ['Zhichao Feng']
11
+ s.email = ['flankerfc@gmail.com']
12
+ s.homepage = 'https://github.com/flanker'
13
+ s.summary = 'A very simple acts as graph for your model'
14
+ s.description = 'A very simple acts as graph for your model'
15
+ s.license = 'MIT'
16
+
17
+ s.required_ruby_version = '>= 2.3'
18
+ s.required_rubygems_version = '>= 1.3.6'
19
+
20
+ s.files = `git ls-files`.split("\n")
21
+ s.test_files = `git ls-files -- test/*`.split("\n")
22
+ s.require_path = ['lib']
23
+
24
+ s.add_runtime_dependency 'rspec'
25
+
26
+ end
@@ -0,0 +1,60 @@
1
+ module ActsAsGraph
2
+
3
+ def self.included base
4
+ base.extend ClassMethods
5
+ end
6
+
7
+ module ClassMethods
8
+
9
+ def acts_as_graph children: nil
10
+ @children_method_name = children
11
+
12
+ define_method "descendant_#{children}" do
13
+ descendant_vertices
14
+ end
15
+ end
16
+
17
+ def children_method_name
18
+ @children_method_name
19
+ end
20
+
21
+ end
22
+
23
+ def descendant_vertices
24
+ vertices_found = []
25
+ collect_child_vertices vertices_found, starting_vertice: self
26
+ vertices_found
27
+ end
28
+
29
+ def collect_child_vertices vertices_found, starting_vertice: nil
30
+ child_vertices.each do |child_vertice|
31
+ next if vertices_found.include?(child_vertice) || child_vertice == starting_vertice
32
+ vertices_found << child_vertice
33
+ child_vertice.collect_child_vertices vertices_found, starting_vertice: starting_vertice
34
+ end
35
+ end
36
+
37
+ def has_circular_reference?
38
+ vertices_found = []
39
+ has_circular_reference_in_child_vertices? vertices_found, starting_vertice: self
40
+ end
41
+
42
+ def has_circular_reference_in_child_vertices? vertices_found, starting_vertice: nil
43
+ child_vertices.any? do |child_vertice|
44
+ return true if vertices_found.include?(child_vertice) || child_vertice == starting_vertice
45
+ vertices_found << child_vertice
46
+ child_vertice.has_circular_reference_in_child_vertices? vertices_found, starting_vertice: starting_vertice
47
+ end
48
+ end
49
+
50
+ private
51
+
52
+ def children_method_name
53
+ self.class.children_method_name
54
+ end
55
+
56
+ def child_vertices
57
+ self.send children_method_name
58
+ end
59
+
60
+ end
@@ -0,0 +1,3 @@
1
+ module ActsAsGraph
2
+ VERSION = '0.0.1'
3
+ end
@@ -0,0 +1,101 @@
1
+ require 'spec_helper'
2
+
3
+ RSpec.describe ActsAsGraph do
4
+
5
+ class Task
6
+
7
+ include ActsAsGraph
8
+
9
+ acts_as_graph children: :depended_tasks
10
+
11
+ attr_reader :title
12
+ attr_accessor :depended_tasks
13
+
14
+ def initialize title, depended_tasks = []
15
+ @title = title
16
+ @depended_tasks = depended_tasks
17
+ end
18
+
19
+ end
20
+
21
+ context '#descendant_depended_tasks' do
22
+
23
+ it 'should get all descendant tasks' do
24
+ task_1 = Task.new 'task_1'
25
+ task_2 = Task.new 'task_2'
26
+ task_3 = Task.new 'task_3', [task_1, task_2]
27
+
28
+ descendant_depended_tasks = task_3.descendant_depended_tasks
29
+ expect(descendant_depended_tasks.length).to eq(2)
30
+ expect(descendant_depended_tasks).to match_array([task_1, task_2])
31
+ end
32
+
33
+ it 'should handle the circular reference' do
34
+ task_1 = Task.new 'task_1'
35
+ task_2 = Task.new 'task_2', [task_1]
36
+ task_3 = Task.new 'task_3', [task_2]
37
+ task_1.depended_tasks = [task_3]
38
+
39
+ descendant_depended_tasks = task_3.descendant_depended_tasks
40
+ expect(descendant_depended_tasks.length).to eq(2)
41
+ expect(descendant_depended_tasks).to match_array([task_1, task_2])
42
+ end
43
+
44
+ it 'should handle a more complex case' do
45
+ task_1 = Task.new 'task_1'
46
+ task_2 = Task.new 'task_2'
47
+ task_3 = Task.new 'task_3'
48
+ task_4 = Task.new 'task_4'
49
+ task_5 = Task.new 'task_5'
50
+ task_6 = Task.new 'task_6'
51
+ task_1.depended_tasks = [task_2]
52
+ task_2.depended_tasks = [task_3, task_4]
53
+ task_3.depended_tasks = [task_1, task_5, task_6]
54
+ task_4.depended_tasks = [task_5]
55
+
56
+ descendant_depended_tasks = task_1.descendant_depended_tasks
57
+ expect(descendant_depended_tasks.length).to eq(5)
58
+ expect(descendant_depended_tasks).to match_array([task_2, task_3, task_4, task_5, task_6])
59
+ end
60
+ end
61
+
62
+ context '#has_circular_reference?' do
63
+
64
+ it 'works if there is no circular reference' do
65
+ task_1 = Task.new 'task_1'
66
+ task_2 = Task.new 'task_2'
67
+ task_3 = Task.new 'task_3', [task_1, task_2]
68
+
69
+ expect(task_3.has_circular_reference?).to be false
70
+ end
71
+
72
+ it 'works if there is a child vertice references the starting vertice' do
73
+ task_1 = Task.new 'task_1'
74
+ task_2 = Task.new 'task_2'
75
+ task_3 = Task.new 'task_3'
76
+
77
+ task_1.depended_tasks = [task_2]
78
+ task_2.depended_tasks = [task_3]
79
+ task_3.depended_tasks = [task_1]
80
+
81
+ expect(task_1.has_circular_reference?).to be true
82
+ expect(task_2.has_circular_reference?).to be true
83
+ expect(task_3.has_circular_reference?).to be true
84
+ end
85
+
86
+ it 'works if there are two vertices reference with each other' do
87
+ task_1 = Task.new 'task_1'
88
+ task_2 = Task.new 'task_2'
89
+ task_3 = Task.new 'task_3'
90
+
91
+ task_1.depended_tasks = [task_2]
92
+ task_2.depended_tasks = [task_3]
93
+ task_3.depended_tasks = [task_2]
94
+
95
+ expect(task_1.has_circular_reference?).to be true
96
+ expect(task_2.has_circular_reference?).to be true
97
+ expect(task_3.has_circular_reference?).to be true
98
+ end
99
+ end
100
+
101
+ end
@@ -0,0 +1,14 @@
1
+ require 'bundler/setup'
2
+ require 'acts_as_graph'
3
+
4
+ RSpec.configure do |config|
5
+ # Enable flags like --only-failures and --next-failure
6
+ config.example_status_persistence_file_path = '.rspec_status'
7
+
8
+ # Disable RSpec exposing methods globally on `Module` and `main`
9
+ config.disable_monkey_patching!
10
+
11
+ config.expect_with :rspec do |c|
12
+ c.syntax = :expect
13
+ end
14
+ end
metadata ADDED
@@ -0,0 +1,68 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: acts_as_graph
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Zhichao Feng
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2018-05-10 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: rspec
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ description: A very simple acts as graph for your model
28
+ email:
29
+ - flankerfc@gmail.com
30
+ executables: []
31
+ extensions: []
32
+ extra_rdoc_files: []
33
+ files:
34
+ - ".gitignore"
35
+ - Gemfile
36
+ - Gemfile.lock
37
+ - README.md
38
+ - Rakefile
39
+ - acts_as_graph.gemspec
40
+ - lib/acts_as_graph.rb
41
+ - lib/acts_as_graph/version.rb
42
+ - spec/acts_as_graph_spec.rb
43
+ - spec/spec_helper.rb
44
+ homepage: https://github.com/flanker
45
+ licenses:
46
+ - MIT
47
+ metadata: {}
48
+ post_install_message:
49
+ rdoc_options: []
50
+ require_paths:
51
+ - lib
52
+ required_ruby_version: !ruby/object:Gem::Requirement
53
+ requirements:
54
+ - - ">="
55
+ - !ruby/object:Gem::Version
56
+ version: '2.3'
57
+ required_rubygems_version: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - ">="
60
+ - !ruby/object:Gem::Version
61
+ version: 1.3.6
62
+ requirements: []
63
+ rubyforge_project:
64
+ rubygems_version: 2.6.14
65
+ signing_key:
66
+ specification_version: 4
67
+ summary: A very simple acts as graph for your model
68
+ test_files: []