safestruct 1.2.2 → 1.3.0

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 45b65afeb50dbc59c31112c55d488a76b0de48b5
4
- data.tar.gz: 82b0e94423bfd55c11d4d4667d29017ec7e12cea
3
+ metadata.gz: e5b47433e234edeb8d8ddddfaa7d6eac51ce1845
4
+ data.tar.gz: 49d711cfbef0941d9cf91762c47858d790d96ef2
5
5
  SHA512:
6
- metadata.gz: 13400c0b1154a455baae1b46108186e1c5d8a6cc03608f0a924b21fb8656b61182b803e9c63c5a3fc2138c0b0ed1b516e0f5f1ae7ff252be6e39e9c313e8cb31
7
- data.tar.gz: 80f08cf43e05456ee749e5a2249191cfd74bb7149512c3169ae98db305b3caa3ae8ce60971184324c546f8a7f284d41c8b8e234b3b3819a97e9314f2843f116d
6
+ metadata.gz: 2ea81799da3ab6d4a4dca8468a5b7515c6ee64717b5350577ad0f8cad32cc2db423fe90ed7d69e018da40044a9d70fa9f643f8723214109d998507f11216dd57
7
+ data.tar.gz: c4e4388b63a6771fbd98c34aa4bd8599e7a0d70a7efa8400c30461409af833fba0e8bef75a7171fee0e19ea0285b680f8c45c0213c2086b87c68a274206db484
data/README.md CHANGED
@@ -94,11 +94,13 @@ Note: You can use `Struct` as an alias for `SafeStruct`
94
94
  class method macro:
95
95
 
96
96
  ``` ruby
97
- struct( 'Voter', weight: 0, voted: false, vote: 0, delegate: '0x0000')
97
+ struct( :Voter, weight: 0, voted: false, vote: 0, delegate: '0x0000')
98
98
  # or
99
- struct 'Voter', weight: 0, voted: false, vote: 0, delegate: '0x0000'
99
+ struct :Voter, { weight: 0, voted: false, vote: 0, delegate: '0x0000' }
100
100
  # or
101
- struct 'Voter',
101
+ struct :Voter, weight: 0, voted: false, vote: 0, delegate: '0x0000'
102
+ # or
103
+ struct :Voter,
102
104
  weight: 0,
103
105
  voted: false,
104
106
  vote: 0,
@@ -211,6 +213,57 @@ allowances['0x2222'].delete( '0xaaaa' )
211
213
  allowances['0x2222']['0xaaaa'] #=> 0
212
214
  ```
213
215
 
216
+ ### Bonus: Auto-Generated Unicode (UTF-8) Class Constants / Names for Pretty Printing
217
+
218
+ Did you know? Yes, you can use unicode characters in your identifiers.
219
+ The safe data structures library auto-generates unicode class constants / names
220
+ for pretty printing and more. Examples:
221
+
222
+ | Class Builder | Class Constant / Name |
223
+ |----------------------------------------|-----------------------|
224
+ | `Array.of( Integer )` | `Array‹Integer›` |
225
+ | `Array.of( Bool )` | `Array‹Bool›` |
226
+ | `Array.of( Bool, 2 )` | `Array‹Bool›×2` |
227
+ | `Array.of( Vote )` | `Array‹Vote›` |
228
+ | `Array.of( Array.of( Integer, 3), 3 )` | `Array‹Array‹Integer›×3›×3` |
229
+ | `Hash.of( String => Integer )` | `Hash‹String→Integer›` |
230
+ | `Hash.of( String => Vote )` | `Hash‹String→Vote›` |
231
+ | `Hash.of( String => Hash.of( String => Integer ))` | `Hash‹String→Hash‹String→Integer››` |
232
+ | ... | |
233
+
234
+
235
+ Note, and yes if the typing is not too much - you can use
236
+ the "magic" names in your code too. Example:
237
+
238
+ ``` ruby
239
+ ary = Array‹Integer›.new
240
+ ary.size #=> 0
241
+ ary[0] #=> IndexError: index 0 outside of array bounds
242
+ ary.size = 2 #=> [0,0]
243
+ ary[0] #=> 0
244
+
245
+ # or
246
+
247
+ another_ary = Array‹Bool›×2.new
248
+ another_ary.size #=> 2
249
+ another_ary[0] #=> false
250
+
251
+ # or
252
+
253
+ hash = Hash‹String→Integer›.new
254
+ hash['0x0000'] #=> 0
255
+ hash['0x0000'] += 42
256
+ hash['0x0000'] #=> 42
257
+
258
+ # or
259
+
260
+ allowances = Hash‹String→Hash‹String→Integer››.new
261
+ allowances['0x1111']['0xaaaa'] = 100
262
+ allowances['0x1111']['0xbbbb'] = 200
263
+ allowances['0x2222']['0xaaaa'] = 300
264
+ ```
265
+
266
+ and so on.
214
267
 
215
268
 
216
269
  ### What about Safe Enumeration (Integer) Types?
@@ -89,14 +89,15 @@ class Array
89
89
  end
90
90
 
91
91
 
92
- module Classic ## use/add Unsafe alias too - why? why not?
92
+ module Standard
93
93
  ############################
94
94
  # note: HACK redefine built in struct in module Safe "context"
95
95
  Struct = ::Struct ## save old classic struct class
96
-
97
- ### add Hash and Array too - why? why not?
96
+ Array = ::Array
97
+ Hash = ::Hash
98
98
  end
99
-
99
+ ## use/add Unsafe alias too - why? why not?
100
+ Std = Standard ## add alias lets use you use Std::Struct,Std::Array, Std::Hash etc.
100
101
 
101
102
 
102
103
 
@@ -40,12 +40,12 @@ class SafeArray
40
40
 
41
41
  ## note: also add a Constant to Safe for easy debugging and (re)use - will "auto"name class
42
42
  class_name = "Array"
43
- class_name << "#{size}" if size > 0 ## add size if non-zero
44
43
 
45
44
  name = klass_value.name
46
45
  name = name.sub( /\bSafe::/, '' ) ## remove safe module from name if present
47
46
  name = name.gsub( '::', '' ) ## remove module separator if present
48
- class_name << "_#{name}"
47
+ class_name << "‹#{name}"
48
+ class_name << "×#{size}" if size > 0 ## add size if non-zero
49
49
  Safe.const_set( class_name, klass )
50
50
  end
51
51
  klass
@@ -7,6 +7,12 @@ class SafeHash
7
7
  def self.debug?() @debug ||= false; end
8
8
  def self.debug=(value) @debug = value; end
9
9
 
10
+ ## let's you configure the class name used for auto-generation class constants
11
+ ## e.g. use SafeHash.klass_name = 'Mapping' to rename from (default) 'Hash'
12
+ def self.klass_name() @@klass_name ||= 'Hash'; end
13
+ def self.klass_name=(value) @@klass_name = value; end
14
+
15
+
10
16
 
11
17
  ## e.g.
12
18
  ## Hash.of( Address => Money )
@@ -22,9 +28,13 @@ class SafeHash
22
28
 
23
29
  ## note: keep a class cache
24
30
  cache = @@cache ||= {}
25
- klass = cache[ klass_value ]
31
+ cache_all_values = cache[ klass_key ] ||= {}
32
+ klass = cache_all_values[ klass_value ]
33
+
26
34
  if debug?
27
- puts "[debug] SafeHash - build_class klass_value:"
35
+ puts "[debug] SafeHash - build_class( klass_key, klass_value ):"
36
+ pp klass_key
37
+ pp klass_key.to_s ## note: for "anonymous" class something like #<Class:>
28
38
  pp klass_value
29
39
  pp klass_value.to_s ## note: for "anonymous" class something like #<Class:>
30
40
  end
@@ -54,16 +64,20 @@ class SafeHash
54
64
  # RUBY
55
65
 
56
66
  ## add to cache for later (re)use
57
- cache[ klass_value ] = klass
67
+ cache[ klass_key ][ klass_value ] = klass
58
68
 
59
69
  ## note: also add a Constant to Safe for easy debugging and (re)use - will "auto"name class
60
- ## note: use X for now for key class name
61
- class_name = "Hash_X"
70
+ class_name = "#{klass_name}"
71
+
72
+ key_name = klass_key.name
73
+ key_name = key_name.sub( /\bSafe::/, '' ) ## remove safe module from name if present
74
+ key_name = key_name.gsub( '::', '' ) ## remove module separator if present
75
+
76
+ value_name = klass_value.name
77
+ value_name = value_name.sub( /\bSafe::/, '' ) ## remove safe module from name if present
78
+ value_name = value_name.gsub( '::', '' ) ## remove module separator if present
62
79
 
63
- name = klass_value.name
64
- name = name.sub( /\bSafe::/, '' ) ## remove safe module from name if present
65
- name = name.gsub( '::', '' ) ## remove module separator if present
66
- class_name << "_#{name}"
80
+ class_name << "‹#{key_name}→#{value_name}›"
67
81
  if debug?
68
82
  puts "[debug] SafeHash - class_name >#{class_name}<"
69
83
  end
@@ -87,18 +101,18 @@ class SafeHash
87
101
 
88
102
  def initialize
89
103
  ## todo/check: if hash works if value is a (nested) hash
90
- @h = {}
104
+ @table = {}
91
105
  end
92
106
 
93
107
  def freeze
94
108
  super
95
- @h.freeze ## note: pass on freeze to "wrapped" hash
109
+ @table.freeze ## note: pass on freeze to "wrapped" hash
96
110
  self # return reference to self
97
111
  end
98
112
 
99
113
  def ==( other )
100
- if other.is_a?( self.class ) ## note: must be same hash class
101
- @h == other.instance_variable_get( '@h' ) ## compare "wrapped" hash
114
+ if other.is_a?( self.class ) ## note: must be same hash (table) class
115
+ @table == other.instance_variable_get( '@table' ) ## compare "wrapped" hash
102
116
  else
103
117
  false
104
118
  end
@@ -109,11 +123,11 @@ class SafeHash
109
123
 
110
124
 
111
125
  def []=(key, value)
112
- @h[key] = value
126
+ @table[key] = value
113
127
  end
114
128
 
115
129
  def [](key)
116
- item = @h[ key ]
130
+ item = @table[ key ]
117
131
  if item.nil?
118
132
  ## pp self.class.klass_value
119
133
  ## pp self.class.klass_value.zero
@@ -126,17 +140,17 @@ class SafeHash
126
140
  if self.class.klass_value.respond_to?( :new_zero )
127
141
  ## note: use a dup(licated) unfrozen copy of the zero object
128
142
  ## changes to the object MUST be possible (new "empty" modifable object expected)
129
- item = @h[ key ] = self.class.klass_value.new_zero
143
+ item = @table[ key ] = self.class.klass_value.new_zero
130
144
  else # assume value semantics e.g. Integer, Bool, etc. zero values gets replaced
131
145
  ## puts "use value semantics"
132
- item = @h[ key ] = self.class.klass_value.zero
146
+ item = @table[ key ] = self.class.klass_value.zero
133
147
  end
134
148
  end
135
149
  item
136
150
  end
137
151
 
138
152
  extend Forwardable
139
- def_delegators :@h, :has_key?, :key?, :delete, :clear
153
+ def_delegators :@table, :has_key?, :key?, :delete, :clear
140
154
 
141
155
  ## note: remove size and length for (safe) hash (for now) - follows solidity convention - why? why not?
142
156
  ## :size, :length,
@@ -11,8 +11,8 @@
11
11
  module SaferStruct
12
12
 
13
13
  MAJOR = 1
14
- MINOR = 2
15
- PATCH = 2
14
+ MINOR = 3
15
+ PATCH = 0
16
16
  VERSION = [MAJOR,MINOR,PATCH].join('.')
17
17
 
18
18
  def self.version
@@ -46,8 +46,8 @@ def test_integer
46
46
  assert_equal false, h.has_key?( '0x1111' )
47
47
 
48
48
  ## todo/fix: remove size and length for (safe) hash - why? why not?
49
- assert_equal 0, h.instance_variable_get('@h').size
50
- assert_equal 0, h.instance_variable_get('@h').length
49
+ assert_equal 0, h.instance_variable_get('@table').size
50
+ assert_equal 0, h.instance_variable_get('@table').length
51
51
 
52
52
  assert_equal true, Hash_X_Integer.zero == h
53
53
  assert_equal true, Hash_X_Integer.zero == Hash_X_Integer.new
@@ -3,17 +3,25 @@
3
3
 
4
4
  module Safe
5
5
 
6
- ## sig: [Integer, Bool, Integer, Address]
6
+ ##[sig(Integer, Bool, Integer, Address)]
7
+ ##
7
8
  ## Struct.new( :Voter,
8
9
  ## weight: 0,
9
10
  ## voted: false,
10
11
  ## vote: 0,
11
12
  ## delegate: '0x0000' )
12
13
 
13
- struct :Voter,
14
+ struct :Voter, {
14
15
  weight: 0,
15
16
  voted: false,
16
17
  vote: 0,
17
- delegate: '0x0000'
18
+ delegate: '0x0000' }
19
+
20
+ ### -or-
21
+ # struct :Voter,
22
+ # weight: 0,
23
+ # voted: false,
24
+ # vote: 0,
25
+ # delegate: '0x0000'
18
26
 
19
27
  end # module Safe
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: safestruct
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.2.2
4
+ version: 1.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Gerald Bauer
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2019-03-22 00:00:00.000000000 Z
11
+ date: 2019-03-23 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: enums