epitools 0.5.43 → 0.5.44
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 +4 -4
- data/VERSION +1 -1
- data/lib/epitools/core_ext/hash.rb +64 -0
- data/lib/epitools/core_ext/numbers.rb +1 -1
- data/lib/epitools/path.rb +16 -1
- data/spec/core_ext_spec.rb +26 -14
- data/spec/path_spec.rb +7 -0
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: c0522a13977563b564bdb275aeadf28428699aef
|
4
|
+
data.tar.gz: b0cdb112d922ea85c3a08f3ce56c44a58b2bfc12
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: de0eff660c20c27c0769628ae29452e04832a3b7a279dfcde50b365984fca0a3057f692f83ce0f7b60e7ff76fcc49c8fbb2bdc88ff170098ddc879b1dc64e02f
|
7
|
+
data.tar.gz: da662e207de10d2f5a6f79492d18423114ec853e7dfd5694048128fa6690e72635f45160b0d4e4746d26830c926e2fa439e780bffe7fc031ae4a89ada4651aed
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.5.
|
1
|
+
0.5.44
|
@@ -224,5 +224,69 @@ class Hash
|
|
224
224
|
end
|
225
225
|
alias_method :mql, :query
|
226
226
|
|
227
|
+
|
228
|
+
#
|
229
|
+
# Return all the changes necessary to transform `self` into `other`. (Works on nested hashes.) The result is a hash of {:key => [old value, new value]} pairs.
|
230
|
+
#
|
231
|
+
# (NOTE: Since "nil" is used to denote a value was removed, you can't use this method to diff hashes where a value is "nil".)
|
232
|
+
#
|
233
|
+
def diff(other)
|
234
|
+
(self.keys + other.keys).uniq.inject({}) do |memo, key|
|
235
|
+
unless self[key] == other[key]
|
236
|
+
if self[key].kind_of?(Hash) && other[key].kind_of?(Hash)
|
237
|
+
memo[key] = self[key].diff(other[key])
|
238
|
+
else
|
239
|
+
memo[key] = [self[key], other[key]]
|
240
|
+
end
|
241
|
+
end
|
242
|
+
memo
|
243
|
+
end
|
244
|
+
end
|
245
|
+
|
246
|
+
#
|
247
|
+
# Applies a Hash#diff changeset to this hash.
|
248
|
+
#
|
249
|
+
def apply_diff!(changes)
|
250
|
+
path = [[self, changes]]
|
251
|
+
pos, local_changes = path.pop
|
252
|
+
|
253
|
+
while local_changes
|
254
|
+
local_changes.each_pair do |key, change|
|
255
|
+
if change.kind_of?(Array)
|
256
|
+
if change[1].nil?
|
257
|
+
pos.delete key
|
258
|
+
else
|
259
|
+
pos[key] = change[1]
|
260
|
+
end
|
261
|
+
else
|
262
|
+
path.push([pos[key], change])
|
263
|
+
end
|
264
|
+
end
|
265
|
+
|
266
|
+
pos, local_changes = path.pop
|
267
|
+
end
|
268
|
+
|
269
|
+
self
|
270
|
+
end
|
271
|
+
|
272
|
+
#
|
273
|
+
# Applies a Hash#diff changeset and returns the transformed hash.
|
274
|
+
#
|
275
|
+
def apply_diff(changes)
|
276
|
+
deep_dup.apply_diff!(changes)
|
277
|
+
end
|
278
|
+
|
279
|
+
#
|
280
|
+
# Duplicate this hash, including hashes nested inside of it.
|
281
|
+
#
|
282
|
+
def deep_dup
|
283
|
+
duplicate = self.dup
|
284
|
+
duplicate.each_pair do |k,v|
|
285
|
+
tv = duplicate[k]
|
286
|
+
duplicate[k] = tv.is_a?(Hash) && v.is_a?(Hash) ? tv.deep_dup : v
|
287
|
+
end
|
288
|
+
duplicate
|
289
|
+
end
|
290
|
+
|
227
291
|
end
|
228
292
|
|
@@ -182,7 +182,7 @@ class Numeric
|
|
182
182
|
result = "%0.2d:%0.2d" % [minutes,seconds]
|
183
183
|
result = ("%0.2d:" % hours) + result if hours > 0 or days > 0
|
184
184
|
result = ("%0.2d:" % days) + result if days > 0
|
185
|
-
result += ("." + frac.round(2).to_s.split(".").last
|
185
|
+
result += ("." + frac.round(2).to_s.split(".").last) if frac > 0
|
186
186
|
|
187
187
|
result
|
188
188
|
end
|
data/lib/epitools/path.rb
CHANGED
@@ -492,6 +492,22 @@ class Path
|
|
492
492
|
end
|
493
493
|
alias_method :xattrs, :attrs
|
494
494
|
|
495
|
+
#
|
496
|
+
# Set this file's xattrs. (Optimized so that only changed attrs are written to disk.)
|
497
|
+
#
|
498
|
+
def attrs=(new_attrs)
|
499
|
+
changes = attrs.diff(new_attrs)
|
500
|
+
|
501
|
+
changes.each do |key, (old, new)|
|
502
|
+
case new
|
503
|
+
when String, Numeric, Boolean, nil
|
504
|
+
self[key] = new
|
505
|
+
else
|
506
|
+
raise "Error: Can't use a #{new.class} as an xattr value. Try passing a String."
|
507
|
+
end
|
508
|
+
end
|
509
|
+
end
|
510
|
+
|
495
511
|
#
|
496
512
|
# Retrieve one of this file's xattrs
|
497
513
|
#
|
@@ -507,7 +523,6 @@ class Path
|
|
507
523
|
@attrs = nil
|
508
524
|
end
|
509
525
|
|
510
|
-
|
511
526
|
###############################################################################
|
512
527
|
# Opening/Reading files
|
513
528
|
###############################################################################
|
data/spec/core_ext_spec.rb
CHANGED
@@ -412,24 +412,24 @@ end
|
|
412
412
|
|
413
413
|
describe Enumerable do
|
414
414
|
|
415
|
-
it "maps deeply" do
|
416
|
-
|
415
|
+
# it "maps deeply" do
|
416
|
+
# [["a\n", "b\n"], ["c\n", "d\n"]].map_recursively(&:strip).should == [ %w[a b], %w[c d] ]
|
417
417
|
|
418
|
-
|
419
|
-
|
420
|
-
|
418
|
+
# [[1,2],[3,4]].deep_map {|e| e ** 2}.should == [[1,4],[9,16]]
|
419
|
+
# [1,2,3,4].deep_map {|e| e ** 2}.should == [1,4,9,16]
|
420
|
+
# [[],[],1,2,3,4].deep_map {|e| e ** 2}.should == [[], [], 1, 4, 9, 16]
|
421
421
|
|
422
|
-
|
423
|
-
end
|
422
|
+
# {1=>2, 3=>{4=>5, 6=>7}}.deep_map {|k,v| [k, v**2] }.should == [ [1,4], [3, [[4,25], [6,49]]] ]
|
423
|
+
# end
|
424
424
|
|
425
|
-
it "selects deeply" do
|
426
|
-
|
427
|
-
|
425
|
+
# it "selects deeply" do
|
426
|
+
# [[1,2],[3,4]].deep_select {|e| e % 2 == 0 }.should == [[2],[4]]
|
427
|
+
# puts
|
428
428
|
|
429
|
-
|
430
|
-
|
431
|
-
|
432
|
-
end
|
429
|
+
# {1=>2, 3=>{4=>5, 6=>7}}.deep_select {|k,v| k == 1 }.should == {1=>2}
|
430
|
+
# #[1,2,3,4].deep_select {|e| e ** 2}.should == [1,4,9,16]
|
431
|
+
# #[[],[],1,2,3,4].deep_select {|e| e ** 2}.should == [[], [], 1, 4, 9, 16]
|
432
|
+
# end
|
433
433
|
|
434
434
|
it "splits" do
|
435
435
|
[1,2,3,4,5].split_at {|e| e == 3}.should == [ [1,2], [4,5] ]
|
@@ -568,6 +568,18 @@ describe Hash do
|
|
568
568
|
@h.key?("key1").should == true
|
569
569
|
@h.includes?("key1").should == true
|
570
570
|
end
|
571
|
+
|
572
|
+
it "diffs" do
|
573
|
+
a = {a: {c: 1, b: 2}, b: 2}
|
574
|
+
b = {a: {c: 2, b: 2}}
|
575
|
+
|
576
|
+
changes = a.diff(b)
|
577
|
+
changes.should == {:a=>{:c=>[1, 2]}, :b=>[2, nil]}
|
578
|
+
a.apply_diff(changes).should == b
|
579
|
+
|
580
|
+
a.apply_diff!(changes)
|
581
|
+
a.should == b
|
582
|
+
end
|
571
583
|
|
572
584
|
end
|
573
585
|
|
data/spec/path_spec.rb
CHANGED
@@ -504,6 +504,7 @@ describe Path do
|
|
504
504
|
end
|
505
505
|
|
506
506
|
it "xattrs" do
|
507
|
+
|
507
508
|
file = Path["~/test"]
|
508
509
|
file.touch
|
509
510
|
file["nothing"].should == nil
|
@@ -518,6 +519,12 @@ describe Path do
|
|
518
519
|
Path.getfattr(file)["user.test"].should == nil
|
519
520
|
|
520
521
|
lambda { file["blahblahblah"] = "whee" }.should raise_error
|
522
|
+
|
523
|
+
# Test assigning an entire hash of attributes, using diffing
|
524
|
+
attrs = file.attrs
|
525
|
+
attrs["user.diff_element"] = "newtest"
|
526
|
+
file.attrs = attrs
|
527
|
+
file["user.newtest"].should == "newtest"
|
521
528
|
end
|
522
529
|
|
523
530
|
it "changes mtime/atime" do
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: epitools
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.5.
|
4
|
+
version: 0.5.44
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- epitron
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2013-12-
|
11
|
+
date: 2013-12-23 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rspec
|