activegraph 10.0.0.pre.alpha.9 → 10.0.0.pre.alpha.10

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 878888811097ecc00e00aec51dd01ca61244b0717cc4e562aa3a30aa3c4721db
4
- data.tar.gz: 0f254663f8d1be115d4a728542f01984cb29f8bb40e501297afff27f19afd7de
3
+ metadata.gz: 39751bab802f72daa73a5fb59b5d356a26616b0547931021cdcc14130690ac3c
4
+ data.tar.gz: 347bbbd3f9e60fdff9dce58147e86ea8f959803a8e18b2788703964847cf285f
5
5
  SHA512:
6
- metadata.gz: 764844043ffd84ace94e417db4bc1de961ddc61f0a503b42ab55c387533417c4cfd569367be7d928d993d2a15168be8d5a6dfa35fefbae6bd47a392098b02dd3
7
- data.tar.gz: 7952ae963f7a7627422c773308e2b96615bcba97403ce4712d542cb62e568652019eb93d2336d5dfccf755a80c080325ac7d57f0144cc4207941707b27768db9
6
+ metadata.gz: 78fc78517a28af803822c2b5113ecd1db26cd03490e1f342d52c14af8bb15d740a3e4ea69fd7209a36eba7d69bb402cade0a374ba3c45c7da9d04b3b68b2e008
7
+ data.tar.gz: 38ade859a5ab61994676589a28484bea97da74d66d35cf0f8b3b6331eab28903bfd812e0162b7250b4f14a568d70db3b52e09c3fbf93a109a77a22f970b9b4a3
data/lib/neo4j.rb CHANGED
@@ -14,6 +14,8 @@ require 'active_support/core_ext/class/subclasses.rb'
14
14
  require 'active_support/core_ext/module/attribute_accessors'
15
15
  require 'json'
16
16
 
17
+ require 'neo4j/lazy_attribute_hash'
18
+ require 'neo4j/attribute_set'
17
19
  require 'neo4j/errors'
18
20
  require 'neo4j/config'
19
21
  require 'neo4j/wrapper'
@@ -9,17 +9,17 @@ module Neo4j
9
9
  class << self
10
10
  # private?
11
11
  def current_driver
12
- (@driver ||= establish_session).tap do |session|
13
- fail 'No session defined!' if session.nil?
12
+ (@driver ||= establish_driver).tap do |driver|
13
+ fail 'No driver defined!' if driver.nil?
14
14
  end
15
15
  end
16
16
 
17
- def on_establish_session(&block)
18
- @establish_session_block = block
17
+ def on_establish_driver(&block)
18
+ @establish_driver_block = block
19
19
  end
20
20
 
21
- def establish_session
22
- @establish_session_block.call if @establish_session_block
21
+ def establish_driver
22
+ @establish_driver_block.call if @establish_driver_block
23
23
  end
24
24
 
25
25
  def new_driver(url, options = {})
@@ -55,7 +55,7 @@ module Neo4j
55
55
 
56
56
  def new_query(options = {})
57
57
  validate_model_schema!
58
- Neo4j::Core::Query.new({session: current_driver}.merge(options))
58
+ Neo4j::Core::Query.new({driver: current_driver}.merge(options))
59
59
  end
60
60
 
61
61
  def magic_query(*args)
@@ -545,7 +545,7 @@ module Neo4j::ActiveNode
545
545
  query_proxy = previous_query_proxy || default_association_query_proxy
546
546
  Neo4j::ActiveNode::Query::QueryProxy.new(association_target_class(name),
547
547
  associations[name],
548
- {session: neo4j_session,
548
+ {driver: neo4j_driver,
549
549
  query_proxy: query_proxy,
550
550
  context: "#{query_proxy.context || self.name}##{name}",
551
551
  optional: query_proxy.optional?,
@@ -578,7 +578,7 @@ module Neo4j::ActiveNode
578
578
 
579
579
  def default_association_query_proxy
580
580
  Neo4j::ActiveNode::Query::QueryProxy.new("::#{self.name}".constantize, nil,
581
- session: neo4j_session, query_proxy: nil, context: self.name.to_s)
581
+ driver: neo4j_driver, query_proxy: nil, context: self.name.to_s)
582
582
  end
583
583
 
584
584
  def build_association(macro, direction, name, options)
@@ -5,7 +5,7 @@ module Neo4j::ActiveNode
5
5
 
6
6
  def initialize(attributes = nil)
7
7
  super(attributes)
8
- @attributes ||= Hash[self.class.attributes_nil_hash]
8
+ @attributes ||= Neo4j::AttributeSet.new(self.class.attributes_nil_hash, self.class.attributes.keys)
9
9
  end
10
10
 
11
11
  module ClassMethods
@@ -33,7 +33,7 @@ module Neo4j
33
33
  # @option options [String, Symbol] :rel_var Same as above but pertaining to a relationship identifier
34
34
  # @option options [Range, Integer, Symbol, Hash] :rel_length A Range, a Integer, a Hash or a Symbol to indicate the variable-length/fixed-length
35
35
  # qualifier of the relationship. See http://neo4jrb.readthedocs.org/en/latest/Querying.html#variable-length-relationships.
36
- # @option options [Neo4j::Session] :session The session to be used for this query
36
+ # @option options [Neo4j::Driver] :driver The driver to be used for this query
37
37
  # @option options [Neo4j::ActiveNode] :source_object The node instance at the start of the QueryProxy chain
38
38
  # @option options [QueryProxy] :query_proxy An existing QueryProxy chain upon which this new object should be built
39
39
  #
@@ -317,9 +317,9 @@ module Neo4j
317
317
  "result_#{(association || model).try(:name)}#{index}".downcase.tr(':', '').to_sym
318
318
  end
319
319
 
320
- def _session
321
- (@session || (@model && @model.neo4j_session)).tap do |session|
322
- fail 'No session found!' if session.nil?
320
+ def _driver
321
+ (@driver || (@model && @model.neo4j_driver)).tap do |driver|
322
+ fail 'No driver found!' if driver.nil?
323
323
  end
324
324
  end
325
325
 
@@ -357,9 +357,9 @@ module Neo4j
357
357
  private
358
358
 
359
359
  def instance_vars_from_options!(options)
360
- @node_var, @session, @source_object, @starting_query, @optional,
360
+ @node_var, @driver, @source_object, @starting_query, @optional,
361
361
  @start_object, @query_proxy, @chain_level, @association_labels,
362
- @rel_length = options.values_at(:node, :session, :source_object, :starting_query, :optional,
362
+ @rel_length = options.values_at(:node, :driver, :source_object, :starting_query, :optional,
363
363
  :start_object, :query_proxy, :chain_level, :association_labels, :rel_length)
364
364
  end
365
365
 
@@ -7,15 +7,15 @@ module Neo4j::ActiveRel
7
7
  module ClassMethods
8
8
  # Returns the object with the specified neo4j id.
9
9
  # @param [String,Integer] id of node to find
10
- # @param [Neo4j::Session] session optional
11
- def find(id, session = self.neo4j_session)
10
+ # @param [Neo4j::Driver] driver optional
11
+ def find(id, driver = self.neo4j_driver)
12
12
  fail "Unknown argument #{id.class} in find method (expected String or Integer)" if !(id.is_a?(String) || id.is_a?(Integer))
13
- find_by_id(id, session)
13
+ find_by_id(id, driver)
14
14
  end
15
15
 
16
16
  # Loads the relationship using its neo_id.
17
- def find_by_id(key, session = nil)
18
- options = session ? {session: session} : {}
17
+ def find_by_id(key, driver = nil)
18
+ options = driver ? {driver: driver} : {}
19
19
  query ||= Neo4j::ActiveBase.new_query(options)
20
20
  result = query.match('()-[r]-()').where('ID(r)' => key.to_i).limit(1).return(:r).first
21
21
  fail RecordNotFound.new("Couldn't find #{name} with 'id'=#{key.inspect}", name, key) if result.blank?
@@ -0,0 +1,32 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'active_model/attribute_set'
4
+
5
+ module Neo4j
6
+ class AttributeSet < ActiveModel::AttributeSet
7
+ def initialize(attr_hash, attr_list)
8
+ hashmap = Neo4j::LazyAttributeHash.new(attr_hash, attr_list)
9
+ super(hashmap)
10
+ end
11
+
12
+ def method_missing(name, *args, **kwargs, &block)
13
+ if defined?(name)
14
+ attributes.send(:materialize).send(name, *args, **kwargs, &block)
15
+ else
16
+ super
17
+ end
18
+ end
19
+
20
+ def respond_to_missing?(method, *)
21
+ attributes.send(:materialize).respond_to?(method) || super
22
+ end
23
+
24
+ def keys
25
+ attributes.send(:materialize).keys
26
+ end
27
+
28
+ def ==(other)
29
+ other.is_a?(Neo4j::AttributeSet) ? super : to_hash == other
30
+ end
31
+ end
32
+ end
@@ -21,8 +21,8 @@ module Neo4j
21
21
  # Creates a neo4j constraint on a property
22
22
  # See http://docs.neo4j.org/chunked/stable/query-constraints.html
23
23
  # @example
24
- # label = Neo4j::Label.create(:person, session)
25
- # label.create_constraint(:name, {type: :unique}, session)
24
+ # label = Neo4j::Label.create(:person, driver)
25
+ # label.create_constraint(:name, {type: :unique}, driver)
26
26
  #
27
27
  def create_constraint(property, constraints)
28
28
  cypher = case constraints[:type]
@@ -41,9 +41,9 @@ module Neo4j
41
41
  # Drops a neo4j constraint on a property
42
42
  # See http://docs.neo4j.org/chunked/stable/query-constraints.html
43
43
  # @example
44
- # label = Neo4j::Label.create(:person, session)
45
- # label.create_constraint(:name, {type: :unique}, session)
46
- # label.drop_constraint(:name, {type: :unique}, session)
44
+ # label = Neo4j::Label.create(:person, driver)
45
+ # label.create_constraint(:name, {type: :unique}, driver)
46
+ # label.drop_constraint(:name, {type: :unique}, driver)
47
47
  #
48
48
  def drop_constraint(property, constraint)
49
49
  cypher = case constraint[:type]
@@ -97,8 +97,8 @@ module Neo4j
97
97
 
98
98
  private
99
99
 
100
- # Store schema threads on the session so that we can easily wait for all
101
- # threads on a session regardless of label
100
+ # Store schema threads on the driver so that we can easily wait for all
101
+ # threads on a driver regardless of label
102
102
  def schema_threads
103
103
  self.class.schema_threads
104
104
  end
@@ -134,7 +134,7 @@ module Neo4j
134
134
 
135
135
  def wait_for_schema_changes
136
136
  schema_threads.map(&:join)
137
- set_schema_threads(session, [])
137
+ set_schema_threads(driver, [])
138
138
  end
139
139
 
140
140
  def schema_threads
@@ -68,7 +68,7 @@ module Neo4j
68
68
  end
69
69
 
70
70
  def initialize(options = {})
71
- @session = options[:session]
71
+ @driver = options[:driver]
72
72
 
73
73
  @options = options
74
74
  @clauses = []
@@ -374,7 +374,7 @@ module Neo4j
374
374
  end
375
375
 
376
376
  def &(other)
377
- self.class.new(session: @session).tap do |new_query|
377
+ self.class.new(driver: @driver).tap do |new_query|
378
378
  new_query.options = options.merge(other.options)
379
379
  new_query.clauses = clauses + other.clauses
380
380
  end.params(other._params)
@@ -396,7 +396,7 @@ module Neo4j
396
396
 
397
397
  protected
398
398
 
399
- attr_accessor :session, :options, :_params
399
+ attr_accessor :driver, :options, :_params
400
400
 
401
401
  def add_clauses(clauses)
402
402
  @clauses += clauses
@@ -23,9 +23,9 @@ module Neo4j
23
23
  end
24
24
 
25
25
  def query
26
- # `nil` sessions are just a workaround until
27
- # we phase out `Query` objects containing sessions
28
- Neo4j::Core::Query.new(session: nil)
26
+ # `nil` drivers are just a workaround until
27
+ # we phase out `Query` objects containing drivers
28
+ Neo4j::Core::Query.new(driver: nil)
29
29
  end
30
30
  end
31
31
  end
@@ -0,0 +1,38 @@
1
+ require 'active_model/attribute_set'
2
+
3
+ module Neo4j
4
+ class LazyAttributeHash < ActiveModel::LazyAttributeHash
5
+ def initialize(values, attr_list)
6
+ @types = {}
7
+ @values = {}
8
+ @additional_types = {}
9
+ @materialized = false
10
+ @delegate_hash = values
11
+
12
+ @default_attributes = process_default_attributes(attr_list)
13
+ end
14
+
15
+ private
16
+
17
+ def marshal_load(values)
18
+ initialize(values[4], values[3])
19
+ end
20
+
21
+ def process_default_attributes(attr_list)
22
+ if attr_list.is_a?(Hash)
23
+ attr_list
24
+ else
25
+ # initialize default attributes map with nil values
26
+ attr_list.each_with_object({}) do |name, map|
27
+ map[name] = nil
28
+ end
29
+ end
30
+ end
31
+
32
+ # we are using with_cast_value here because at the moment casting is being managed by
33
+ # Neo4j and not in ActiveModel
34
+ def assign_default_value(name)
35
+ delegate_hash[name] = ActiveModel::Attribute.with_cast_value(name, default_attributes[name].dup, nil)
36
+ end
37
+ end
38
+ end
@@ -2,28 +2,28 @@ module Neo4j
2
2
  module Migrations
3
3
  module Schema
4
4
  class << self
5
- def fetch_schema_data(session)
6
- {constraints: fetch_constraint_descriptions(session).sort,
7
- indexes: fetch_index_descriptions(session).sort}
5
+ def fetch_schema_data(driver)
6
+ {constraints: fetch_constraint_descriptions(driver).sort,
7
+ indexes: fetch_index_descriptions(driver).sort}
8
8
  end
9
9
 
10
- def synchronize_schema_data(session, schema_data, remove_missing)
10
+ def synchronize_schema_data(driver, schema_data, remove_missing)
11
11
  queries = []
12
- queries += drop_and_create_queries(fetch_constraint_descriptions(session), schema_data[:constraints], remove_missing)
13
- queries += drop_and_create_queries(fetch_index_descriptions(session), schema_data[:indexes], remove_missing)
14
- session.queries do
12
+ queries += drop_and_create_queries(fetch_constraint_descriptions(driver), schema_data[:constraints], remove_missing)
13
+ queries += drop_and_create_queries(fetch_index_descriptions(driver), schema_data[:indexes], remove_missing)
14
+ driver.queries do
15
15
  queries.each { |query| append query }
16
16
  end
17
17
  end
18
18
 
19
19
  private
20
20
 
21
- def fetch_constraint_descriptions(session)
22
- session.query('CALL db.constraints()').map(&:description)
21
+ def fetch_constraint_descriptions(driver)
22
+ driver.query('CALL db.constraints()').map(&:description)
23
23
  end
24
24
 
25
- def fetch_index_descriptions(session)
26
- result = session.query('CALL db.indexes()')
25
+ def fetch_index_descriptions(driver)
26
+ result = driver.query('CALL db.indexes()')
27
27
  if result.columns.include?(:description)
28
28
  v3_indexes(result)
29
29
  else
data/lib/neo4j/railtie.rb CHANGED
@@ -7,7 +7,7 @@ require 'neo4j/core/driver'
7
7
  module Neo4j
8
8
  class Railtie < ::Rails::Railtie
9
9
  def empty_config
10
- ActiveSupport::OrderedOptions.new.tap { |cfg| cfg.session = ActiveSupport::OrderedOptions.new }
10
+ ActiveSupport::OrderedOptions.new.tap { |cfg| cfg.driver = ActiveSupport::OrderedOptions.new }
11
11
  end
12
12
 
13
13
  config.neo4j = empty_config
@@ -48,7 +48,7 @@ module Neo4j
48
48
 
49
49
  Neo4j::Config.configuration.merge!(neo4j_config.to_h)
50
50
 
51
- Neo4j::ActiveBase.on_establish_session { setup! neo4j_config }
51
+ Neo4j::ActiveBase.on_establish_driver { setup! neo4j_config }
52
52
 
53
53
  Neo4j::Config[:logger] ||= Rails.logger
54
54
 
@@ -58,18 +58,18 @@ module Neo4j
58
58
  end
59
59
 
60
60
  def setup!(neo4j_config = empty_config)
61
- url, path, options = final_session_config!(neo4j_config).values_at(:url, :path, :options)
61
+ url, path, options = final_driver_config!(neo4j_config).values_at(:url, :path, :options)
62
62
  options ||= {}
63
63
  register_neo4j_cypher_logging
64
64
 
65
- Neo4j::ActiveBase.new_driver( url || path || default_session_path_or_url, options)
65
+ Neo4j::ActiveBase.new_driver( url || path || default_driver_path_or_url, options)
66
66
  end
67
67
 
68
- def final_session_config!(neo4j_config)
69
- (neo4j_config[:session].empty? ? yaml_config_data : neo4j_config[:session]).dup
68
+ def final_driver_config!(neo4j_config)
69
+ (neo4j_config[:driver].empty? ? yaml_config_data : neo4j_config[:driver]).dup
70
70
  end
71
71
 
72
- def default_session_path_or_url
72
+ def default_driver_path_or_url
73
73
  ENV['NEO4J_URL'] || ENV['NEO4J_PATH'] || 'bolt://localhost:7474'
74
74
  end
75
75
 
data/lib/neo4j/shared.rb CHANGED
@@ -10,10 +10,10 @@ module Neo4j
10
10
  include ActiveModel::Serializers::JSON
11
11
 
12
12
  module ClassMethods
13
- # TODO: Deprecate neo4j_session_name(name)
13
+ # TODO: Deprecate neo4j_driver_name(name)
14
14
 
15
15
  # remove?
16
- def neo4j_session
16
+ def neo4j_driver
17
17
  Neo4j::ActiveBase.current_driver
18
18
  end
19
19
 
@@ -23,7 +23,7 @@ module Neo4j
23
23
  end
24
24
 
25
25
  # This should be used everywhere. Should make it easy
26
- # to support a session-per-model system
26
+ # to support a driver-per-model system
27
27
  def neo4j_query(*args)
28
28
  Neo4j::ActiveBase.query(*args)
29
29
  end
@@ -77,14 +77,15 @@ module Neo4j::Shared
77
77
 
78
78
  # Read an attribute from the attributes hash
79
79
  def attribute(name)
80
- @attributes ||= {}
81
- @attributes[name]
80
+ @attributes ||= Neo4j::AttributeSet.new({}, self.class.attributes.keys)
81
+ @attributes.fetch_value(name.to_s)
82
82
  end
83
83
 
84
84
  # Write an attribute to the attributes hash
85
85
  def attribute=(name, value)
86
- @attributes ||= {}
87
- @attributes[name] = value
86
+ @attributes ||= Neo4j::AttributeSet.new({}, self.class.attributes.keys)
87
+ @attributes.write_cast_value(name, value)
88
+ value
88
89
  end
89
90
 
90
91
  # Maps all attributes using the given block
@@ -12,16 +12,17 @@ module Neo4j::Shared
12
12
  private
13
13
 
14
14
  def convert_and_assign_attributes(properties)
15
- @attributes ||= Hash[self.class.attributes_nil_hash]
15
+ @attributes ||= Neo4j::AttributeSet.new(self.class.attributes_nil_hash, self.class.attributes.keys)
16
16
  stringify_attributes!(@attributes, properties)
17
17
  self.default_properties = properties if respond_to?(:default_properties=)
18
18
  self.class.declared_properties.convert_properties_to(self, :ruby, @attributes)
19
+ @attributes
19
20
  end
20
21
 
21
22
  def stringify_attributes!(attr, properties)
22
23
  properties.each_pair do |k, v|
23
24
  key = self.class.declared_properties.string_key(k)
24
- attr[key.freeze] = v
25
+ attr.write_cast_value(key.freeze, v)
25
26
  end
26
27
  end
27
28
 
@@ -11,6 +11,9 @@ module Neo4j::Shared
11
11
 
12
12
  attr_reader :_persisted_obj
13
13
 
14
+ NEO4J_DRIVER_DATA_TYPES = [Date, Time, Hash, Neo4j::Driver::Types::Bytes, ActiveSupport::Duration, Neo4j::Driver::Types::Point,
15
+ Neo4j::Driver::Types::OffsetTime, Neo4j::Driver::Types::LocalTime, Neo4j::Driver::Types::LocalDateTime]
16
+
14
17
  # TODO: Set @attribute correctly using class ActiveModel::Attribute, and after that
15
18
  # remove mutations_from_database and other ActiveModel::Dirty overrided methods
16
19
  def mutations_from_database
@@ -28,6 +31,7 @@ module Neo4j::Shared
28
31
  end
29
32
 
30
33
  def initialize(attributes = nil)
34
+ @attributes ||= Neo4j::AttributeSet.new({}, self.class.attributes.keys)
31
35
  attributes = process_attributes(attributes)
32
36
  modded_attributes = inject_defaults!(attributes)
33
37
  validate_attributes!(modded_attributes)
@@ -212,7 +216,11 @@ module Neo4j::Shared
212
216
  define_attribute_methods([name]) unless attribute_names.include?(name)
213
217
  attributes[name.to_s] = declared_properties[name]
214
218
  define_method("#{name}=") do |value|
215
- typecast_value = typecast_attribute(_attribute_typecaster(name), value)
219
+ typecast_value = if NEO4J_DRIVER_DATA_TYPES.include?(_attribute_type(name))
220
+ value
221
+ else
222
+ typecast_attribute(_attribute_typecaster(name), value)
223
+ end
216
224
  send("#{name}_will_change!") unless typecast_value == read_attribute(name)
217
225
  super(value)
218
226
  end
@@ -25,7 +25,14 @@ module Neo4j::Shared
25
25
  end
26
26
 
27
27
  class IntegerConverter < BaseConverter
28
+ NEO4J_LARGEST_INT = 9223372036854775807
29
+ NEO4J_SMALLEST_INT = -9223372036854775808
28
30
  class << self
31
+
32
+ def converted?(value)
33
+ false
34
+ end
35
+
29
36
  def convert_type
30
37
  Integer
31
38
  end
@@ -35,55 +42,31 @@ module Neo4j::Shared
35
42
  end
36
43
 
37
44
  def to_db(value)
38
- value.to_i
45
+ val = value.to_i
46
+ val > NEO4J_LARGEST_INT || val < NEO4J_SMALLEST_INT ? val.to_s : val
39
47
  end
40
48
 
41
- alias to_ruby to_db
42
- end
43
- end
44
-
45
- class FloatConverter < BaseConverter
46
- class << self
47
- def convert_type
48
- Float
49
- end
50
-
51
- def db_type
52
- Float
53
- end
54
-
55
- def to_db(value)
56
- value.to_f
49
+ def to_ruby(value)
50
+ value.to_i
57
51
  end
58
- alias to_ruby to_db
59
52
  end
60
53
  end
61
54
 
62
- class BigDecimalConverter < BaseConverter
63
- class << self
64
- def convert_type
65
- BigDecimal
66
- end
67
-
68
- def db_type
69
- String
70
- end
71
-
72
- def to_db(value)
73
- case value
74
- when Rational
75
- value.to_f.to_d
76
- when respond_to?(:to_d)
77
- value.to_d
78
- else
79
- BigDecimal(value.to_s)
80
- end.to_s
81
- end
82
-
83
- def to_ruby(value)
84
- value.to_d
85
- end
86
- end
55
+ class FloatConverter < BaseConverter
56
+ class << self
57
+ def convert_type
58
+ Float
59
+ end
60
+
61
+ def db_type
62
+ Float
63
+ end
64
+
65
+ def to_db(value)
66
+ value.to_f
67
+ end
68
+ alias to_ruby to_db
69
+ end
87
70
  end
88
71
 
89
72
  class StringConverter < BaseConverter
@@ -103,62 +86,6 @@ module Neo4j::Shared
103
86
  end
104
87
  end
105
88
 
106
- class BooleanConverter < BaseConverter
107
- FALSE_VALUES = %w(n N no No NO false False FALSE off Off OFF f F).to_set
108
-
109
- class << self
110
- def converted?(value)
111
- converted_values.include?(value)
112
- end
113
-
114
- def converted_values
115
- [true, false]
116
- end
117
-
118
- def db_type
119
- Neo4j::Shared::Boolean
120
- end
121
-
122
- alias convert_type db_type
123
-
124
- def to_db(value)
125
- return false if FALSE_VALUES.include?(value)
126
- case value
127
- when TrueClass, FalseClass
128
- value
129
- when Numeric, /^\-?[0-9]/
130
- !value.to_f.zero?
131
- else
132
- value.present?
133
- end
134
- end
135
-
136
- alias to_ruby to_db
137
- end
138
- end
139
-
140
- # Converts Date objects to Java long types. Must be timezone UTC.
141
- class DateConverter < BaseConverter
142
- class << self
143
- def convert_type
144
- Date
145
- end
146
-
147
- def db_type
148
- Integer
149
- end
150
-
151
- def to_db(value)
152
- Time.utc(value.year, value.month, value.day).to_i
153
- end
154
-
155
- def to_ruby(value)
156
- value.respond_to?(:to_date) ? value.to_date : Time.at(value).utc.to_date
157
- end
158
- end
159
- end
160
-
161
- # Converts DateTime objects to and from Java long types. Must be timezone UTC.
162
89
  class DateTimeConverter < BaseConverter
163
90
  class << self
164
91
  def convert_type
@@ -167,7 +94,7 @@ module Neo4j::Shared
167
94
 
168
95
  def db_type
169
96
  Integer
170
- end
97
+ end
171
98
 
172
99
  # Converts the given DateTime (UTC) value to an Integer.
173
100
  # DateTime values are automatically converted to UTC.
@@ -198,29 +125,37 @@ module Neo4j::Shared
198
125
  end
199
126
  end
200
127
 
201
- class TimeConverter < BaseConverter
128
+ class BooleanConverter < BaseConverter
129
+ FALSE_VALUES = %w(n N no No NO false False FALSE off Off OFF f F).to_set
130
+
202
131
  class << self
203
- def convert_type
204
- Time
132
+ def converted?(value)
133
+ converted_values.include?(value)
134
+ end
135
+
136
+ def converted_values
137
+ [true, false]
205
138
  end
206
139
 
207
140
  def db_type
208
- Integer
141
+ Neo4j::Shared::Boolean
209
142
  end
210
143
 
211
- # Converts the given DateTime (UTC) value to an Integer.
212
- # Only utc times are supported !
144
+ alias convert_type db_type
145
+
213
146
  def to_db(value)
214
- if value.class == Date
215
- Time.utc(value.year, value.month, value.day, 0, 0, 0).to_i
147
+ return false if FALSE_VALUES.include?(value)
148
+ case value
149
+ when TrueClass, FalseClass
150
+ value
151
+ when Numeric, /^\-?[0-9]/
152
+ !value.to_f.zero?
216
153
  else
217
- value.utc.to_i
154
+ value.present?
218
155
  end
219
156
  end
220
157
 
221
- def to_ruby(value)
222
- Time.at(value).utc
223
- end
158
+ alias to_ruby to_db
224
159
  end
225
160
  end
226
161
 
@@ -240,7 +175,7 @@ module Neo4j::Shared
240
175
  end
241
176
 
242
177
  def to_ruby(value)
243
- Psych.load(value)
178
+ value.is_a?(Hash) ? value : Psych.load(value)
244
179
  end
245
180
  end
246
181
  end
@@ -327,16 +262,21 @@ module Neo4j::Shared
327
262
  end
328
263
  end
329
264
 
330
-
331
265
  # Modifies a hash's values to be of types acceptable to Neo4j or matching what the user defined using `type` in property definitions.
332
266
  # @param [Neo4j::Shared::Property] obj A node or rel that mixes in the Property module
333
267
  # @param [Symbol] medium Indicates the type of conversion to perform.
334
268
  # @param [Hash] properties A hash of symbol-keyed properties for conversion.
335
269
  def convert_properties_to(obj, medium, properties)
336
270
  direction = medium == :ruby ? :to_ruby : :to_db
337
- properties.each_pair do |key, value|
271
+ properties.to_h.each_pair do |key, value|
338
272
  next if skip_conversion?(obj, key, value)
339
- properties[key] = convert_property(key, value, direction)
273
+
274
+ converted_value = convert_property(key, value, direction)
275
+ if properties.is_a?(Neo4j::AttributeSet)
276
+ properties.write_cast_value(key, converted_value)
277
+ else
278
+ properties[key] = converted_value
279
+ end
340
280
  end
341
281
  end
342
282
 
@@ -39,15 +39,15 @@ module Neo4j::Shared
39
39
  #
40
40
  # @return [Object, nil] The attribute value before typecasting
41
41
  def attribute_before_type_cast(name)
42
- @attributes ||= {}
43
- @attributes[name.to_s]
42
+ @attributes ||= Neo4j::AttributeSet.new({}, self.class.attributes.keys)
43
+ @attributes.fetch_value(name.to_s)
44
44
  end
45
45
 
46
46
  private
47
47
 
48
48
  # Reads the attribute and typecasts the result
49
49
  def attribute(name)
50
- typecast_attribute(_attribute_typecaster(name), super)
50
+ Property::NEO4J_DRIVER_DATA_TYPES.include?(_attribute_type(name)) ? super : typecast_attribute(_attribute_typecaster(name), super)
51
51
  end
52
52
 
53
53
  def typecast_attribute(typecaster, value)
@@ -66,7 +66,8 @@ module Neo4j::Shared
66
66
  # @private
67
67
  def _attribute_typecaster(attribute_name)
68
68
  type = _attribute_type(attribute_name)
69
- caster = self.class.attributes[attribute_name].typecaster || Neo4j::Shared::TypeConverters.typecaster_for(type)
69
+ default_typecaster = self.class.attributes[attribute_name].typecaster
70
+ caster = default_typecaster || Neo4j::Shared::TypeConverters.typecaster_for(type)
70
71
  caster || fail(Neo4j::UnknownTypeConverterError, "Unable to cast to type #{type}")
71
72
  end
72
73
 
@@ -16,7 +16,7 @@ module Neo4j
16
16
  # Runs the given block in a new transaction.
17
17
  # @param [Boolean] run_in_tx if true a new transaction will not be created, instead if will simply yield to the given block
18
18
  # @@yield [Neo4j::Transaction::Instance]
19
- def run(driver, run_in_tx)
19
+ def run(_driver, run_in_tx)
20
20
  return yield(nil) unless run_in_tx
21
21
 
22
22
  tx = Neo4j::Transaction.new
data/lib/neo4j/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module Neo4j
2
- VERSION = '10.0.0-alpha.9'
2
+ VERSION = '10.0.0-alpha.10'
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: activegraph
3
3
  version: !ruby/object:Gem::Version
4
- version: 10.0.0.pre.alpha.9
4
+ version: 10.0.0.pre.alpha.10
5
5
  platform: ruby
6
6
  authors:
7
7
  - Andreas Ronge, Brian Underwood, Chris Grigg, Heinrich Klobuczek
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-02-12 00:00:00.000000000 Z
11
+ date: 2020-02-18 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activemodel
@@ -304,6 +304,7 @@ files:
304
304
  - lib/neo4j/active_rel/types.rb
305
305
  - lib/neo4j/active_rel/validations.rb
306
306
  - lib/neo4j/ansi.rb
307
+ - lib/neo4j/attribute_set.rb
307
308
  - lib/neo4j/class_arguments.rb
308
309
  - lib/neo4j/config.rb
309
310
  - lib/neo4j/core.rb
@@ -328,6 +329,7 @@ files:
328
329
  - lib/neo4j/core/schema_errors.rb
329
330
  - lib/neo4j/core/wrappable.rb
330
331
  - lib/neo4j/errors.rb
332
+ - lib/neo4j/lazy_attribute_hash.rb
331
333
  - lib/neo4j/migration.rb
332
334
  - lib/neo4j/migrations.rb
333
335
  - lib/neo4j/migrations/base.rb
@@ -415,7 +417,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
415
417
  - !ruby/object:Gem::Version
416
418
  version: 1.3.1
417
419
  requirements: []
418
- rubygems_version: 3.0.6
420
+ rubygems_version: 3.1.2
419
421
  signing_key:
420
422
  specification_version: 4
421
423
  summary: A graph database for Ruby