activegraph-extensions 0.0.1-java

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 ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 9c33fee6eede1db2664a17ae82a9f7dcb0d3611b2665605a024fd184a2695fa9
4
+ data.tar.gz: ea57d1a76c541d3b5c8c655f1b4cea22142917c83500a2275f4f2fc177f120af
5
+ SHA512:
6
+ metadata.gz: dc88d9b5d715d803ede073cfd97f60bdbb4b1efe93231416a95ba3963d5831af872bf7e55e53906061693009f9e052e725dea8e80bd8a1a5e44864221659b4ad
7
+ data.tar.gz: d0b79494bac58f25b9c972951c7bce4d27beb33c5bdcbf865905a81401375b344ab9b9cb101360e93aa1db9bfcc14015ecc1b7a853623e90f9a6a7ca59ff67a0
data/CHANGELOG.md ADDED
@@ -0,0 +1 @@
1
+ # Change Log
data/Gemfile ADDED
@@ -0,0 +1,24 @@
1
+ source "https://rubygems.org"
2
+
3
+ gemspec
4
+
5
+ gem 'listen', '< 3.1'
6
+ active_model_version = ENV['ACTIVE_MODEL_VERSION']
7
+ gem 'activemodel', "~> #{active_model_version}" if active_model_version&.length&.positive?
8
+
9
+ #gem 'zeitwerk'
10
+
11
+ group :test do
12
+ gem 'coveralls', require: false
13
+ gem 'overcommit'
14
+ gem 'codecov', require: false
15
+ gem 'simplecov', require: false
16
+ gem 'simplecov-html', require: false
17
+ gem 'its'
18
+ gem 'test-unit'
19
+ gem 'colored'
20
+ gem 'dotenv'
21
+ gem 'timecop'
22
+ gem 'pry'
23
+ gem 'activegraph'
24
+ end
data/README.md ADDED
@@ -0,0 +1 @@
1
+ # Extensions to activegraph gem.
@@ -0,0 +1,45 @@
1
+ lib = File.expand_path('lib', __dir__)
2
+ $LOAD_PATH.unshift lib unless $LOAD_PATH.include?(lib)
3
+
4
+ require 'active_graph_extensions/version'
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = 'activegraph-extensions'
8
+ s.version = ActiveGraphExtensions::VERSION
9
+
10
+ s.required_ruby_version = '>= 2.5'
11
+
12
+ s.authors = 'Amit Suryavanshi'
13
+ s.email = 'amitbsuryavabshi@mail.com'
14
+ s.homepage = 'https://github.com/neo4jrb/activegraph-extensions/'
15
+ s.summary = 'Additional features to activegraph'
16
+ s.license = 'MIT'
17
+ s.description = <<-DESCRIPTION
18
+ Additional features to activegraph, like sideload limiting, authorizing sideloads etc.
19
+ DESCRIPTION
20
+
21
+ s.require_path = 'lib'
22
+ s.files = Dir.glob('{bin,lib,config}/**/*') + %w(README.md CHANGELOG.md Gemfile activegraph-extensions.gemspec)
23
+ s.executables = []
24
+ s.extra_rdoc_files = %w( README.md )
25
+ s.rdoc_options = ['--quiet', '--title', 'Neo4j.rb', '--line-numbers', '--main', 'README.rdoc', '--inline-source']
26
+
27
+ s.platform = 'java'
28
+
29
+ s.add_dependency('parslet')
30
+ s.add_dependency('activegraph')
31
+
32
+ s.add_development_dependency('guard')
33
+ s.add_development_dependency('guard-rspec')
34
+ s.add_development_dependency('guard-rubocop')
35
+ s.add_development_dependency('neo4j-rake_tasks', '>= 0.3.0')
36
+ # s.add_development_dependency("neo4j-#{ENV['driver'] == 'java' ? 'java' : 'ruby'}-driver", '~> 4.1.0.beta.1')
37
+ s.add_development_dependency('os')
38
+ s.add_development_dependency('pry')
39
+ s.add_development_dependency('railties', '>= 4.0')
40
+ s.add_development_dependency('rake')
41
+ s.add_development_dependency('rubocop', '>= 0.56.0')
42
+ s.add_development_dependency('yard')
43
+ s.add_development_dependency('dryspec')
44
+ s.add_development_dependency('rspec', '< 3.10') # Cannot proxy frozen objects
45
+ end
@@ -0,0 +1,16 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ActiveGraphExtensions
4
+ module Node
5
+ module Query
6
+ # We need earlier proxy to generate cypher in query proxy eagerloading
7
+ module QueryProxy
8
+ def branch(&block)
9
+ proxy = super
10
+ proxy.instance_variable_set(:@break_proxy, as(identity).instance_eval(&block))
11
+ proxy
12
+ end
13
+ end
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,32 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ActiveGraphExtensions
4
+ module Node
5
+ module Query
6
+ module QueryProxyEagerLoading
7
+ # Used for eager loading associations with scope
8
+ module AssociationEagerLoad
9
+ extend ActiveSupport::Concern
10
+
11
+ class_methods do
12
+ def associations_to_eagerload
13
+ @associations_to_eagerload
14
+ end
15
+
16
+ def association_nodes(key, ids, filter)
17
+ send(@associations_to_eagerload[key], ids, filter)
18
+ end
19
+
20
+ def eagerload_associations(config)
21
+ @associations_to_eagerload = config
22
+ end
23
+
24
+ def eagerload_association?(key)
25
+ @associations_to_eagerload.keys.include?(key)
26
+ end
27
+ end
28
+ end
29
+ end
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,79 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ActiveGraphExtensions
4
+ module Node
5
+ module Query
6
+ module QueryProxyEagerLoading
7
+ module AssociationLimiting
8
+ def self.included(base)
9
+ base.attr_reader(:default_assoc_limit)
10
+ end
11
+
12
+ private
13
+
14
+ def rel_collection_str(path)
15
+ limit = association_limit(path)
16
+ collection_name = "[#{relationship_name(path)}, #{escape(path_name(path))}] "
17
+ collection = limit.present? ? "apoc.agg.slice(#{collection_name}, 0, #{limit})" : "collect(#{collection_name})"
18
+ "#{collection} AS #{escape("#{path_name(path)}_collection")}"
19
+ end
20
+
21
+ def relationship_name(path)
22
+ if path.last.rel_length
23
+ "last(relationships(#{escape("#{path_name(path)}_path")}))"
24
+ else
25
+ escape("#{path_name(path)}_rel")
26
+ end
27
+
28
+ end
29
+
30
+ def convert_to_list(collection_name, limit)
31
+ limit.present? ? "apoc.agg.slice(#{collection_name}, 0, #{limit})" : "collect(#{collection_name})"
32
+ end
33
+
34
+ def association_limit(path)
35
+ return if multipath?(path)
36
+
37
+ limit = path.last&.association_limit
38
+ limit.blank? || limit.to_i > default_assoc_limit ? default_assoc_limit : limit
39
+ end
40
+
41
+ def with_association_query_part(base_query, path, previous_with_vars)
42
+ with_args = [identity, rel_collection_str(path), *previous_with_vars]
43
+
44
+ optional_match_with_where(base_query, path, previous_with_vars).with(with_args)
45
+ end
46
+
47
+ def limit_node_in_where_clause(query, path)
48
+ root_path = path[0..0]
49
+ query.where("`#{path_name(root_path)}` in [i IN #{node_from_collection(root_path)} | i[1]]")
50
+ end
51
+
52
+ def node_from_collection(path_step)
53
+ "`#{path_name(path_step)}_collection`"
54
+ end
55
+
56
+ def path_alias(node_alias)
57
+ var_fix(node_alias, :path)
58
+ end
59
+
60
+ def rel_alias(node_alias)
61
+ var_fix(node_alias, :rel)
62
+ end
63
+
64
+ def multipath?(path)
65
+ path.size > 1
66
+ end
67
+
68
+ def association_limit_present?(path)
69
+ association_limit(path).present?
70
+ end
71
+
72
+ def multipath_with_sideload_limit?(path)
73
+ multipath?(path) && association_limit_present?(path[0..0])
74
+ end
75
+ end
76
+ end
77
+ end
78
+ end
79
+ end
@@ -0,0 +1,42 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ActiveGraphExtensions
4
+ module Node
5
+ module Query
6
+ module QueryProxyEagerLoading
7
+ # Used to append auth scopes to query proxy eagerloading
8
+ module EagerLoadingOrder
9
+ def optional_order(query, path, previous_with_vars)
10
+ node_alias = path_name(path)
11
+ order_clause = order_clause_for_query(node_alias)
12
+ if path.last.rel_length
13
+ order_clause.reject! { |el| el.include?('_rel') }
14
+ query.order("length(`#{node_alias}_path`)", *order_clause)
15
+ .with(*with_variables(path, node_alias, previous_with_vars))
16
+ else
17
+ query.order(*order_clause).with(*with_variables(path, node_alias, previous_with_vars))
18
+ end
19
+ end
20
+
21
+ def order_clause_for_query(node_alias)
22
+ (order = @order_spec&.fetch(node_alias, nil)) ? order.map(&method(:nested_order_clause).curry.call(node_alias)) : []
23
+ end
24
+
25
+ def nested_order_clause(node_alias, order_spec)
26
+ [node_or_rel_alias(node_alias, order_spec), name(order_spec)].join('.')
27
+ end
28
+
29
+ def order_clause(key, order_spec)
30
+ property_with_direction = name(order_spec)
31
+ node_alias = node_aliase_for_collection(key, order_spec) || node_aliase_for_order(property_with_direction)
32
+ [node_alias, property_with_direction].compact.join('.')
33
+ end
34
+
35
+ def skip_order?
36
+ @order_spec.blank? || @order_spec.keys.all?(&:blank?)
37
+ end
38
+ end
39
+ end
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,67 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ActiveGraphExtensions
4
+ module Node
5
+ module Query
6
+ module QueryProxyEagerLoading
7
+ # Tree allowing storage of additional information about the associations
8
+ class EnhancedTree < ::ActiveGraph::Node::Query::QueryProxyEagerLoading::AssociationTree
9
+ attr_reader :options, :association_limit
10
+
11
+ def initialize(model, name = nil, rel_length = nil, association_limit = nil)
12
+ @association_limit = association_limit
13
+ super(model, name, rel_length)
14
+ end
15
+
16
+ def add_spec_and_validate(spec)
17
+ add_spec(spec)
18
+ validate_for_zero_length_paths
19
+ end
20
+
21
+ def validate_for_zero_length_paths
22
+ fail 'Can not eager load more than one zero length path.' if values.count(&:zero_length_path?) > 1
23
+ end
24
+
25
+ def zero_length_path?
26
+ rel_length&.fetch(:min, nil)&.to_s == '0' || values.any?(&:zero_length_path?)
27
+ end
28
+
29
+ def add_key(key, length = nil, assoc_limit = nil)
30
+ self[key] ||= self.class.new(model, key, length, assoc_limit)
31
+ end
32
+
33
+ def add_nested(key, value, length = nil, assoc_limit = nil)
34
+ add_key(key, length, assoc_limit).add_spec(value)
35
+ end
36
+
37
+ def process_string(str)
38
+ # head, rest = str.split('.', 2)
39
+ # head, association_limit = extract_assoc_limit(head)
40
+ # k, length = head.split('*', -2)
41
+ # length = { max: length } if length
42
+ #add_nested(k.to_sym, rest, length, association_limit)
43
+ map = StringParsers::RelationParser.new.parse(str)
44
+ add_nested(map[:rel_name].to_sym, map[:rest_str].to_s.presence, map[:length_part], map[:limit_digit])
45
+ end
46
+
47
+ # def extract_assoc_limit(str)
48
+ # transformer = StringParsers::RelationParamTransformer.new(str)
49
+ # [transformer.rel_name_n_length, transformer.rel_limit_number]
50
+ # end
51
+
52
+ def process_hash(spec)
53
+ spec = spec.dup
54
+ @options = spec.delete(:_options)
55
+ super(spec)
56
+ end
57
+
58
+ def target_class(model, key)
59
+ association = model.associations[key.to_sym]
60
+ fail "Invalid association: #{[*path, key].join('.')}" unless association
61
+ model.associations[key].target_class
62
+ end
63
+ end
64
+ end
65
+ end
66
+ end
67
+ end
@@ -0,0 +1,50 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ActiveGraphExtensions
4
+ module Node
5
+ module Query
6
+ module QueryProxyEagerLoading
7
+ # Used to append auth scopes to query proxy eagerloading
8
+ module ScopeEagerLoading
9
+ def authorized_rel(path, var)
10
+ rel_model = relationship_model(path)
11
+ return {} if @opts.blank? || !(auth_scope = authorized_scope(rel_model, path))
12
+ conf = { rels: [], chain: {} }
13
+ proxy = auth_scope.call(var, "#{var}_rel", user: @opts[:user],
14
+ properties: properties_for(rel_model),
15
+ privileges: @opts[:privileges],
16
+ rel_length: path.last.rel_length)
17
+ proxy_rel_parts(proxy.instance_variable_get(:@break_proxy) || proxy, conf)
18
+ conf
19
+ end
20
+
21
+ def properties_for(rel_model)
22
+ return [] unless @opts[:properties]
23
+ @opts[:properties].select { |prop| prop.model.name == rel_model.name }.map(&:name)
24
+ end
25
+
26
+ def relationship_model(path)
27
+ path[0..-2].inject(model) { |mod, rel| mod.send(rel.name).model }
28
+ end
29
+
30
+ def authorized_scope(rel_model, path)
31
+ rel_model.scopes["authorized_#{path.last.association.name}".to_sym]
32
+ end
33
+
34
+ def proxy_rel_parts(auth_proxy, conf)
35
+ return unless auth_proxy&.association
36
+ rel_length = auth_proxy.instance_variable_get(:@rel_length)
37
+ conf[:rels] << relationship_part(auth_proxy.association, auth_proxy.identity, rel_length)
38
+ assign_config_chain(conf, auth_proxy, rel_length)
39
+ proxy_rel_parts(auth_proxy.query_proxy, conf)
40
+ end
41
+
42
+ def assign_config_chain(conf, auth_proxy, rel_length)
43
+ return unless (auth_chain = auth_proxy.instance_variable_get(:@chain))
44
+ conf[:chain][[auth_proxy.identity, rel_length ? "#{auth_proxy.identity}_rel" : nil]] = auth_chain
45
+ end
46
+ end
47
+ end
48
+ end
49
+ end
50
+ end
@@ -0,0 +1,148 @@
1
+ module ActiveGraphExtensions
2
+ module Node
3
+ module Query
4
+ module QueryProxyEagerLoading
5
+ extend ActiveSupport::Concern
6
+ include AssociationLimiting
7
+ include ScopeEagerLoading
8
+ include EagerLoadingOrder
9
+
10
+ def association_tree_class
11
+ EnhancedTree
12
+ end
13
+
14
+ def with_ordered_associations(spec, order, opts = {})
15
+ @default_assoc_limit = opts[:default_assoc_limit]
16
+ @with_vars = opts[:with_vars]
17
+ @order_spec = order.with_indifferent_access unless spec.empty?
18
+ @opts = opts
19
+ with_associations(spec)
20
+ end
21
+
22
+ def first
23
+ limit(1).to_a.first
24
+ end
25
+
26
+ class_methods do
27
+ def rel?(order_spec)
28
+ order_spec.is_a?(Hash) ? 0 : 1
29
+ end
30
+ end
31
+
32
+ def with_associations(*spec)
33
+ new_link.tap do |new_query_proxy|
34
+ new_query_proxy.with_associations_tree = with_associations_tree.clone
35
+ new_query_proxy.with_associations_tree.add_spec_and_validate(spec)
36
+ end
37
+ end
38
+
39
+ private
40
+
41
+ def query_from_association_tree
42
+ previous_with_vars = defalut_previous_with_vars
43
+ with_associations_tree.paths.inject(query_as(identity).with(base_query_with_vars)) do |query, path|
44
+ with_association_query_part(query, path, previous_with_vars).tap do
45
+ previous_with_vars << var_fix(path_name(path), :collection)
46
+ end
47
+ end
48
+ end
49
+
50
+ def defalut_previous_with_vars
51
+ @with_vars&.dup || []
52
+ end
53
+
54
+ def base_query_with_vars
55
+ [ensure_distinct(identity)] + (@with_vars || [])
56
+ end
57
+
58
+ def optional_match_with_where(query, path, vars)
59
+ computed_query = super
60
+ computed_query = limit_node_in_where_clause(computed_query, path) if multipath_with_sideload_limit?(path)
61
+ skip_order? && !path.last.rel_length ? computed_query : optional_order(computed_query, path, vars)
62
+ end
63
+
64
+ def optional_match(base_query, path)
65
+ start_path = "#{escape("#{path_name(path)}_path")}=(#{identity})"
66
+ conf = authorized_rel(path, path_name(path[0..-1]))
67
+ query = construct_optional_match(start_path, base_query, conf[:rels] ? path[0..-2] : path, conf[:rels])
68
+ conf[:rels] ? apply_chain(conf[:chain], query) : query
69
+ end
70
+
71
+ def construct_optional_match(start_path, base_query, path, scope_rels)
72
+ base_query.optional_match(
73
+ "#{start_path}#{path.each_with_index.map do |element, index|
74
+ relationship_part(element.association, path_name(path[0..index]), element.rel_length)
75
+ end.join}#{(scope_rels || []).reverse.join}"
76
+ )
77
+ end
78
+
79
+ def apply_chain(chain, query)
80
+ chain.each do |key, links|
81
+ query = links.inject(query) do |q, link|
82
+ args = link.args(*key)
83
+ args.is_a?(Array) ? q.send(link.clause, *args) : q.send(link.clause, args)
84
+ end
85
+ end
86
+ query
87
+ end
88
+
89
+ def with_variables(path, node_alias, previous_with_vars)
90
+ [identity, path.last.rel_length ? path_alias(node_alias) : rel_alias(node_alias), var_fix(node_alias)] +
91
+ previous_with_vars
92
+ end
93
+
94
+ def before_pluck(query)
95
+ return query if skip_order? && !include_with_path_length?
96
+ base_query = query.order(
97
+ (@order_spec || []).flat_map { |key, order_specs| order_specs.map(&method(:order_clause).curry.call(key)) }
98
+ )
99
+ query_from_chain(@postponed_chain, base_query, identity)
100
+ end
101
+
102
+ def node_aliase_for_collection(key, order_spec)
103
+ "#{var(key, :collection, &:itself)}[0][#{self.class.rel?(order_spec)}]" if key.present?
104
+ end
105
+
106
+ def node_aliase_for_order(property_with_direction)
107
+ identity unless @with_vars&.include?(property_with_direction.split(' ').first.to_sym)
108
+ end
109
+
110
+ def name(order_spec)
111
+ Array(order_spec).flatten.last.to_s
112
+ end
113
+
114
+ def node_or_rel_alias(node_alias, order_spec)
115
+ var(node_alias, order_spec.is_a?(Hash) ? :rel : nil, &:itself)
116
+ end
117
+
118
+ CLAUSES_TO_POSTPONE = %i[limit order skip].freeze
119
+
120
+ def include_with_path_length?(path = @with_associations_tree)
121
+ path.present? && (path.rel_length.present? || path.any? { |_, val| include_with_path_length?(val) })
122
+ end
123
+
124
+ def chain
125
+ return super if skip_order? && !include_with_path_length?
126
+ clauses = !skip_order? ? CLAUSES_TO_POSTPONE : %i[order]
127
+ @postponed_chain, other_chain = super.partition { |link| clauses.include?(link.clause) }
128
+ other_chain
129
+ end
130
+
131
+ def perform_query
132
+ @_cache = ActiveGraph::Node::Query::QueryProxyEagerLoading::IdentityMap.new
133
+ build_query
134
+ .map do |record, eager_data|
135
+ record = cache_and_init(record, with_associations_tree)
136
+ eager_data.zip(with_associations_tree.paths.map(&:last)).each do |eager_records, element|
137
+ eager_records.each do |eager_record|
138
+ next unless eager_record.first&.type&.to_s == element.association.relationship_type.to_s
139
+ add_to_cache(*eager_record, element)
140
+ end
141
+ end
142
+ record
143
+ end
144
+ end
145
+ end
146
+ end
147
+ end
148
+ end
@@ -0,0 +1,8 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ActiveGraphExtensions
4
+ module Node
5
+ module Query
6
+ end
7
+ end
8
+ end
@@ -0,0 +1,6 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ActiveGraphExtensions
4
+ module Node
5
+ end
6
+ end
@@ -0,0 +1,24 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ActiveGraphExtensions
4
+ module StringParsers
5
+ # Parsing relationships with length
6
+ class RelationParser < ::Parslet::Parser
7
+ rule(:asterix) { str('*') }
8
+ rule(:digit) { match('[\d]').repeat }
9
+ rule(:range) { str('..') }
10
+ rule(:dot) { str('.') }
11
+ rule(:zero) { str('0') }
12
+ rule(:length_1) { zero.as(:min) >> range >> digit.maybe.as(:max) }
13
+ rule(:length_2) { digit.maybe.as(:max) }
14
+ rule(:length) { asterix >> (length_1 | length_2) }
15
+ rule(:rel) { match('[a-z,_]').repeat.as(:rel_name) }
16
+ rule(:limit) { digit.as(:limit_digit) >> asterix }
17
+ rule(:key) { limit.maybe >> rel >> length.as(:length_part).maybe }
18
+ rule(:anything) { match('.').repeat }
19
+ rule(:root) { key >> dot.maybe >> anything.maybe.as(:rest_str) }
20
+
21
+ rule(:rel_sequence) { infix_expression(key, [dot, 1, :left]) }
22
+ end
23
+ end
24
+ end
@@ -0,0 +1,6 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ActiveGraphExtensions
4
+ module StringParsers
5
+ end
6
+ end
@@ -0,0 +1,3 @@
1
+ module ActiveGraphExtensions
2
+ VERSION = '0.0.1'
3
+ end
@@ -0,0 +1,15 @@
1
+ require 'active_graph'
2
+ require 'parslet'
3
+
4
+ module ActiveGraphExtensions
5
+ end
6
+
7
+ loader = Zeitwerk::Loader.for_gem
8
+ loader.inflector.inflect 'version' => 'VERSION'
9
+ loader.ignore(File.expand_path('activegraph-extensions.rb', __dir__))
10
+ loader.setup
11
+
12
+ ActiveGraph::Node::Query::QueryProxy.include ActiveGraphExtensions::Node::Query::QueryProxyEagerLoading
13
+ ActiveGraph::Node::Query::QueryProxy.prepend ActiveGraphExtensions::Node::Query::QueryProxy
14
+
15
+ ActiveGraph::Node.include ActiveGraphExtensions::Node::Query::QueryProxyEagerLoading::AssociationEagerLoad
metadata ADDED
@@ -0,0 +1,264 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: activegraph-extensions
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: java
6
+ authors:
7
+ - Amit Suryavanshi
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2022-01-17 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ requirement: !ruby/object:Gem::Requirement
15
+ requirements:
16
+ - - ">="
17
+ - !ruby/object:Gem::Version
18
+ version: '0'
19
+ name: parslet
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
+ - !ruby/object:Gem::Dependency
28
+ requirement: !ruby/object:Gem::Requirement
29
+ requirements:
30
+ - - ">="
31
+ - !ruby/object:Gem::Version
32
+ version: '0'
33
+ name: activegraph
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ requirement: !ruby/object:Gem::Requirement
43
+ requirements:
44
+ - - ">="
45
+ - !ruby/object:Gem::Version
46
+ version: '0'
47
+ name: guard
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
55
+ - !ruby/object:Gem::Dependency
56
+ requirement: !ruby/object:Gem::Requirement
57
+ requirements:
58
+ - - ">="
59
+ - !ruby/object:Gem::Version
60
+ version: '0'
61
+ name: guard-rspec
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - ">="
67
+ - !ruby/object:Gem::Version
68
+ version: '0'
69
+ - !ruby/object:Gem::Dependency
70
+ requirement: !ruby/object:Gem::Requirement
71
+ requirements:
72
+ - - ">="
73
+ - !ruby/object:Gem::Version
74
+ version: '0'
75
+ name: guard-rubocop
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - ">="
81
+ - !ruby/object:Gem::Version
82
+ version: '0'
83
+ - !ruby/object:Gem::Dependency
84
+ requirement: !ruby/object:Gem::Requirement
85
+ requirements:
86
+ - - ">="
87
+ - !ruby/object:Gem::Version
88
+ version: 0.3.0
89
+ name: neo4j-rake_tasks
90
+ type: :development
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - ">="
95
+ - !ruby/object:Gem::Version
96
+ version: 0.3.0
97
+ - !ruby/object:Gem::Dependency
98
+ requirement: !ruby/object:Gem::Requirement
99
+ requirements:
100
+ - - ">="
101
+ - !ruby/object:Gem::Version
102
+ version: '0'
103
+ name: os
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
+ - !ruby/object:Gem::Dependency
112
+ requirement: !ruby/object:Gem::Requirement
113
+ requirements:
114
+ - - ">="
115
+ - !ruby/object:Gem::Version
116
+ version: '0'
117
+ name: pry
118
+ type: :development
119
+ prerelease: false
120
+ version_requirements: !ruby/object:Gem::Requirement
121
+ requirements:
122
+ - - ">="
123
+ - !ruby/object:Gem::Version
124
+ version: '0'
125
+ - !ruby/object:Gem::Dependency
126
+ requirement: !ruby/object:Gem::Requirement
127
+ requirements:
128
+ - - ">="
129
+ - !ruby/object:Gem::Version
130
+ version: '4.0'
131
+ name: railties
132
+ type: :development
133
+ prerelease: false
134
+ version_requirements: !ruby/object:Gem::Requirement
135
+ requirements:
136
+ - - ">="
137
+ - !ruby/object:Gem::Version
138
+ version: '4.0'
139
+ - !ruby/object:Gem::Dependency
140
+ requirement: !ruby/object:Gem::Requirement
141
+ requirements:
142
+ - - ">="
143
+ - !ruby/object:Gem::Version
144
+ version: '0'
145
+ name: rake
146
+ type: :development
147
+ prerelease: false
148
+ version_requirements: !ruby/object:Gem::Requirement
149
+ requirements:
150
+ - - ">="
151
+ - !ruby/object:Gem::Version
152
+ version: '0'
153
+ - !ruby/object:Gem::Dependency
154
+ requirement: !ruby/object:Gem::Requirement
155
+ requirements:
156
+ - - ">="
157
+ - !ruby/object:Gem::Version
158
+ version: 0.56.0
159
+ name: rubocop
160
+ type: :development
161
+ prerelease: false
162
+ version_requirements: !ruby/object:Gem::Requirement
163
+ requirements:
164
+ - - ">="
165
+ - !ruby/object:Gem::Version
166
+ version: 0.56.0
167
+ - !ruby/object:Gem::Dependency
168
+ requirement: !ruby/object:Gem::Requirement
169
+ requirements:
170
+ - - ">="
171
+ - !ruby/object:Gem::Version
172
+ version: '0'
173
+ name: yard
174
+ type: :development
175
+ prerelease: false
176
+ version_requirements: !ruby/object:Gem::Requirement
177
+ requirements:
178
+ - - ">="
179
+ - !ruby/object:Gem::Version
180
+ version: '0'
181
+ - !ruby/object:Gem::Dependency
182
+ requirement: !ruby/object:Gem::Requirement
183
+ requirements:
184
+ - - ">="
185
+ - !ruby/object:Gem::Version
186
+ version: '0'
187
+ name: dryspec
188
+ type: :development
189
+ prerelease: false
190
+ version_requirements: !ruby/object:Gem::Requirement
191
+ requirements:
192
+ - - ">="
193
+ - !ruby/object:Gem::Version
194
+ version: '0'
195
+ - !ruby/object:Gem::Dependency
196
+ requirement: !ruby/object:Gem::Requirement
197
+ requirements:
198
+ - - "<"
199
+ - !ruby/object:Gem::Version
200
+ version: '3.10'
201
+ name: rspec
202
+ type: :development
203
+ prerelease: false
204
+ version_requirements: !ruby/object:Gem::Requirement
205
+ requirements:
206
+ - - "<"
207
+ - !ruby/object:Gem::Version
208
+ version: '3.10'
209
+ description: " Additional features to activegraph, like sideload limiting, authorizing\
210
+ \ sideloads etc.\n"
211
+ email: amitbsuryavabshi@mail.com
212
+ executables: []
213
+ extensions: []
214
+ extra_rdoc_files:
215
+ - README.md
216
+ files:
217
+ - CHANGELOG.md
218
+ - Gemfile
219
+ - README.md
220
+ - activegraph-extensions.gemspec
221
+ - lib/active_graph_extensions/node.rb
222
+ - lib/active_graph_extensions/node/query.rb
223
+ - lib/active_graph_extensions/node/query/query_proxy.rb
224
+ - lib/active_graph_extensions/node/query/query_proxy_eager_loading.rb
225
+ - lib/active_graph_extensions/node/query/query_proxy_eager_loading/association_eager_load.rb
226
+ - lib/active_graph_extensions/node/query/query_proxy_eager_loading/association_limiting.rb
227
+ - lib/active_graph_extensions/node/query/query_proxy_eager_loading/eager_loading_order.rb
228
+ - lib/active_graph_extensions/node/query/query_proxy_eager_loading/enhanced_tree.rb
229
+ - lib/active_graph_extensions/node/query/query_proxy_eager_loading/scope_eager_loading.rb
230
+ - lib/active_graph_extensions/string_parsers.rb
231
+ - lib/active_graph_extensions/string_parsers/relation_parser.rb
232
+ - lib/active_graph_extensions/version.rb
233
+ - lib/activegraph-extensions.rb
234
+ homepage: https://github.com/neo4jrb/activegraph-extensions/
235
+ licenses:
236
+ - MIT
237
+ metadata: {}
238
+ post_install_message:
239
+ rdoc_options:
240
+ - "--quiet"
241
+ - "--title"
242
+ - Neo4j.rb
243
+ - "--line-numbers"
244
+ - "--main"
245
+ - README.rdoc
246
+ - "--inline-source"
247
+ require_paths:
248
+ - lib
249
+ required_ruby_version: !ruby/object:Gem::Requirement
250
+ requirements:
251
+ - - ">="
252
+ - !ruby/object:Gem::Version
253
+ version: '2.5'
254
+ required_rubygems_version: !ruby/object:Gem::Requirement
255
+ requirements:
256
+ - - ">="
257
+ - !ruby/object:Gem::Version
258
+ version: '0'
259
+ requirements: []
260
+ rubygems_version: 3.0.6
261
+ signing_key:
262
+ specification_version: 4
263
+ summary: Additional features to activegraph
264
+ test_files: []