jsonize 0.1.0 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (4) hide show
  1. checksums.yaml +4 -4
  2. data/lib/jsonize/version.rb +1 -1
  3. data/lib/jsonize.rb +100 -58
  4. metadata +3 -3
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 787277d3b1f9c06c0e3df496dcb3402ceaf1643ee5048ac359bc7592a67487b9
4
- data.tar.gz: 1005708186a5a16ee757b5b4d0393a2af6403465c6377f4ef8defbf50d62df79
3
+ metadata.gz: d3227e59ca0f4826ae7a108ba9ab99419e2441fa7ca4182cd288000fe5caaa5b
4
+ data.tar.gz: 5d79a0a28100a90b628b96820d250a10fa9b70806203b078d68c7828a035d88a
5
5
  SHA512:
6
- metadata.gz: e469b13fd8e298a003d31438dfe78dba30cf0154732e44d3c31246c75417629383a4d6499d132a2b92c003682ccba9893ded343f2d8f241e81b8f6e678402c2c
7
- data.tar.gz: 8ac936e618c70b4eb5b14f6fec34754d2e4806225e23d0b9177f505b82efa91bbb6b66b87a38ca333b12f7026af0c36dce60700a3d892bb8956d3e77d7258afe
6
+ metadata.gz: e427382e3c42a97b5991c2d382a078a198562c1686c835e7039546de9ce360890c8cd6ada52bb3339c1835fd9422d686875631ecdad6bf30f312a5bac38480ab
7
+ data.tar.gz: e35614f1087c93893ee1dc739b4c2a85756f632afcb99a419b70afb605714b459f5b8bf3bc2b1e0435527d4ce24999993df61e6c39366eb5c53d01cbda81a7c8
@@ -1,3 +1,3 @@
1
1
  module Jsonize
2
- VERSION = "0.1.0"
2
+ VERSION = "0.2.0"
3
3
  end
data/lib/jsonize.rb CHANGED
@@ -3,7 +3,9 @@ require 'redisize'
3
3
  require "jsonize/version"
4
4
 
5
5
  module Jsonize
6
- JSON_ATTRS = {
6
+ DEFAULT_EXCEPT_ATTRS = [:created_at, :updated_at]
7
+
8
+ JSONIZE_ATTRS = {
7
9
  created_at: nil,
8
10
  updated_at: nil,
9
11
  }
@@ -12,26 +14,13 @@ module Jsonize
12
14
  ActiveRecord: 'active_record'
13
15
  }
14
16
 
15
- def external_attrs options = {}
16
- if externals = options[:externals]
17
- externals.keys.map {|k| [k.to_sym, k.to_sym] }.to_h
18
- else
19
- {}
20
- end
21
- end
22
-
23
- def instance_attrs
24
- self.attribute_names.map {|a| [a.to_sym, true] }.to_h
25
- end
17
+ JSON_TYPES = [String, Integer, TrueClass, FalseClass, NilClass, Hash, Array]
26
18
 
27
- def embed_attrs
28
- begin
29
- self.class.const_get("JSON_ATTRS")
30
- rescue
31
- {}
32
- end
19
+ def default_except_attributes
20
+ DEFAULT_EXCEPT_ATTRS
33
21
  end
34
22
 
23
+ # TODO where is the addtional sources for attributes
35
24
  def additional_attrs
36
25
  attributes = self.instance_variable_get(:@attributes).send(:attributes)
37
26
 
@@ -44,67 +33,120 @@ module Jsonize
44
33
  end
45
34
  end
46
35
 
47
- def generate_json propses, externals = {}
48
- propses.reduce({}) do |r, (name, props)|
36
+ def generate_relation rela, source_in, options
37
+ source = source_in.is_a?(Hash) ? source_in : source_in.polymorphic? ?
38
+ {} : required_attibutes(source_in.klass, {})
39
+
40
+ case rela
41
+ when Enumerable
42
+ rela.map do |rec|
43
+ generate_json(rec, source, options)
44
+ end
45
+ when NilClass
46
+ nil
47
+ when Object
48
+ generate_json(rela, source, options)
49
+ end
50
+ end
51
+
52
+ def generate_json flow, attr_props, options = {}
53
+ in_h = (options[:externals] || {}).map {|(x, y)| [x.to_s, y] }.to_h
54
+
55
+ attr_props.reduce(in_h) do |cr, (name, props)|
49
56
  value =
50
- if props["rule"].is_a?(Proc)
51
- props["rule"][self]
52
- elsif props["rule"].is_a?(String)
53
- externals.fetch(props["rule"].to_sym) { |x| externals[props["rule"]] }
54
- elsif props["real_name"] != name.to_s
55
- read_attribute(props["real_name"]).as_json
56
- elsif props["rule"].instance_variable_get(:@value)
57
- props["rule"].instance_variable_get(:@value)
58
- elsif props["rule"]
59
- read_attribute(props["real_name"] || props["rule"])
57
+ [props].flatten.reduce(nil) do |r, source|
58
+ case source
59
+ when UnboundMethod
60
+ r || source.bind(flow)[]
61
+ when Proc
62
+ r || source[flow]
63
+ when Hash, ActiveRecord::Reflection::AbstractReflection
64
+ generate_relation(r || flow.send(name), source, options)
65
+ else
66
+ raise
67
+ end
60
68
  end
61
69
 
62
- r.merge(name => value)
70
+ cr.merge(name.to_s => proceed_value(value))
63
71
  end
64
72
  end
65
73
 
66
- def prepare_json options = {}
67
- attr_hash = [
68
- instance_attrs,
69
- JSON_ATTRS,
70
- embed_attrs,
71
- additional_attrs,
72
- external_attrs(options),
73
- options[:map] || {}
74
- ].reduce { |r, hash| r.merge(hash.map {|k,v| [k.to_sym, v] }.to_h) }
75
- except = options.fetch(:except, [])
76
- only = options.fetch(:only, self.attributes.keys.map(&:to_sym) | (options[:map] || {}).keys | embed_attrs.keys | external_attrs(options).keys)
74
+ def proceed_value value_in
75
+ (value_in.class.ancestors & JSON_TYPES).any? ? value_in : value_in.to_s
76
+ end
77
77
 
78
- attr_hash.map do |(name_in, rule_in)|
79
- name = /^_(?<_name>.*)/ =~ name_in && _name || name_in.to_s
78
+ def prepare_attributes model, attrs
79
+ attrs.reduce({}) do |h, x|
80
+ if x.is_a?(Hash)
81
+ x.reduce(h) do |hh, (sub, subattrs)|
82
+ if submodel = model._reflections[sub]&.klass
83
+ hh.merge(sub.to_sym => prepare_attributes(submodel, subattrs))
84
+ else
85
+ hh
86
+ end
87
+ end
88
+ else
89
+ props = [
90
+ model._reflections[x.to_s],
91
+ model.instance_methods.include?(x.to_sym) ? model.instance_method(x.to_sym) : nil,
92
+ (self.class == model ? self.attribute_names : model.attribute_names).
93
+ include?(x.to_s) ? ->(this) { this.read_attribute(x) } : nil
94
+ ].compact
95
+
96
+ h.merge(x.to_s.sub(/^_/, '').to_sym => props)
97
+ end
98
+ end
99
+ end
100
+
101
+ def attibute_tree klass, options = {}
102
+ options[:only] ||
103
+ jsonize_attributes_except(self.class == klass ? self.attribute_names : klass.attribute_names,
104
+ options[:except] || default_except_attributes)
105
+ end
106
+
107
+ def jsonize_scheme_for klass, attr_tree
108
+ jsonize_schemes[attr_tree] ||= prepare_attributes(klass, attr_tree)
109
+ end
80
110
 
81
- next nil if except.include?(name.to_sym) || (only & [ name.to_sym, name_in.to_sym ].uniq).blank?
111
+ def jsonize_attributes_except a_in, except_in
112
+ except_in.reduce(a_in) do |res, name|
113
+ if res.include?(name)
114
+ res.delete(name)
115
+ end
82
116
 
83
- rule = parse_rule(rule_in)
84
- #binding.pry
85
- [name, { "rule" => rule, "real_name" => name_in.to_s }]
86
- end.compact.to_h
117
+ res
118
+ end
87
119
  end
88
120
 
89
- def parse_rule rule_in
90
- %w(TrueClass FalseClass NilClass Symbol).all? {|k| !rule_in.is_a?(k.constantize) } && true || rule_in.is_a?(Symbol) && rule_in.to_s || rule_in
121
+ def jsonize_schemes
122
+ schemes = self.class.instance_variable_get(:@jsonize_schemes) || {}
123
+ self.class.instance_variable_set(:@jsonize_schemes, schemes)
124
+
125
+ schemes
126
+ end
127
+
128
+ def primary_key
129
+ @primary_key
91
130
  end
92
131
 
93
132
  def jsonize options = {}
94
- attr_props = prepare_json(options)
95
- redisize_json(attr_props) do
96
- generate_json(attr_props, options[:externals])
133
+ attr_tree = attibute_tree(self.class, options)
134
+
135
+ redisize_json(attr_tree) do
136
+ attr_props = jsonize_scheme_for(self.class, attr_tree)
137
+ generate_json(self, attr_props, options)
97
138
  end
98
139
  end
99
140
 
100
141
  def dejsonize options = {}
101
- attr_props = prepare_json(options)
102
- deredisize_json(attr_props)
142
+ attr_tree = attibute_tree(self.class, options)
143
+ deredisize_json(attr_tree)
103
144
  end
104
145
 
105
146
  def as_json options = {}
106
- attr_props = prepare_json(options)
107
- generate_json(attr_props, options[:externals])
147
+ attr_props = jsonize_scheme_for(self.class, attibute_tree(self.class, options))
148
+
149
+ generate_json(self, attr_props, options)
108
150
  end
109
151
 
110
152
  module Relation
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: jsonize
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Pavel «Malo» Skrylev
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2022-07-26 00:00:00.000000000 Z
11
+ date: 2023-12-31 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: redisize
@@ -95,7 +95,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
95
95
  - !ruby/object:Gem::Version
96
96
  version: '0'
97
97
  requirements: []
98
- rubygems_version: 3.1.6
98
+ rubygems_version: 3.3.7
99
99
  signing_key:
100
100
  specification_version: 4
101
101
  summary: Act as as_json for active record model or as a jsonize