rbfind 2.4 → 2.5

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/bin/rbfind +19 -5
  3. data/lib/rbfind.rb +111 -96
  4. metadata +2 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: cc576c9c24d5acd2c31b95e55bfd40b306c1510060c06c2a5d00140c1fca77dd
4
- data.tar.gz: e2a95604bf31b4290d71b0c93da8bff1cde417407cf6c22c79872cf4132c6de3
3
+ metadata.gz: 7bee921838a5b4d93f5483295e8c7e6b263e144e8d52e5ca53a464a222a5d055
4
+ data.tar.gz: 03f0b19f70747dbb152011ecc8f414d99764ad9052c82f9b0b1715939fb7a3dd
5
5
  SHA512:
6
- metadata.gz: 671c10d123f2a025f4ee3b0f0b08cbe2a74ef830a0b8f56cd7485470c68051902db9ace56b00a5f479d36ceefb802d133ddd43aa5cc025286a49405ce4860e79
7
- data.tar.gz: 39a4b9cd0565455b010228a68fefd7d021e81953cdd23c150555a83fef577a342282f42b6476c6f1e97287d9e99b659349284eae55244fbfff01edf40a2d724c
6
+ metadata.gz: 3de28232b6d9b842ced7ff2880e4d80938c194c13c93fd6a69e5265d3f6999276129bc1469eae62a121776222d27836c95cc208ae2d656080875345d342d471e
7
+ data.tar.gz: d979151e81e3eaf660304c2072550f857957e9c08c4da74af67afc5d23e498021b546c33920ba20099fcb2248a2a621eccf51b9732b34212a1273188ec4d6c73
data/bin/rbfind CHANGED
@@ -34,8 +34,8 @@ module RbFind
34
34
  [ %w(--maxdepth -m), :num, "maxium step depth"],
35
35
  [ %w(--follow -y), nil, "follow symbolic links"],
36
36
  [ %w(--nosort -S), nil, "unsorted"],
37
- [ %w(--sort-by -s), :str, "sort expression ('n' is name)"],
38
- [ %w(--reverse -R), :str, "reverse sort"],
37
+ [ %w(--sort-by -s), :str, "sort expression"],
38
+ [ %w(--reverse -R), nil, "reverse the sort"],
39
39
  [ %w(--require -r), :rb, "require library"],
40
40
  [ %w(--puts-path -p), nil, "do 'puts path/cpath' on true block"],
41
41
  [ %w(--ls-l -P), nil, "do 'ls -l' style output on true block"],
@@ -48,14 +48,14 @@ module RbFind
48
48
  [ %w(--binary -b), nil, "grep even binary files"],
49
49
  [ %w(--no-vcs -C), nil, "prune version control dirs (CVS/.svn/.git)"],
50
50
  [ %w(--no-swap -W), nil, "ignore Vim swapfiles"],
51
- [ %w(--skip -k), :lst, "filenames to skip"],
52
- [ %w(--demand -D), :lst, "skip all filenames but these"],
51
+ [ %w(--skip -k), :rgx, "filenames to skip"],
52
+ [ %w(--demand -D), :rgx, "skip all filenames but these"],
53
53
  [ %w(--ext -e), :lst, "skip all filename extensions but these"],
54
54
  [ %w(--visible -I), nil, "skip all hidden (starting with .dot)"],
55
55
  [ %w(--nodirs -N), nil, "skip directories"],
56
56
  [ %w(--begin -B), :blk, "eval block before begin"],
57
57
  [ %w(--end -E), :blk, "eval block after end"],
58
- [ %w(--file -f), :blk, "read block expression from file"],
58
+ [ %w(--file -f), :nam, "read block expression from file"],
59
59
  [ %w(--encoding -K), :str, "encoding extern[:intern] (same as ruby -E)"],
60
60
  ]
61
61
 
@@ -483,6 +483,20 @@ class NilClass
483
483
  end
484
484
  end
485
485
 
486
+ class TrueClass
487
+ def <=> oth
488
+ oth == true ? 0 : oth == false ? 1 : nil
489
+ end
490
+ include Enumerable
491
+ end
492
+
493
+ class FalseClass
494
+ def <=> oth
495
+ oth == false ? 0 : oth == true ? -1 : nil
496
+ end
497
+ include Enumerable
498
+ end
499
+
486
500
  class Proc
487
501
  def to_s
488
502
  "#<%s:0x%08x>" % [ self.class, object_id]
data/lib/rbfind.rb CHANGED
@@ -8,7 +8,7 @@ require "rbfind/csv"
8
8
 
9
9
  module RbFind
10
10
 
11
- VERSION = "2.4".freeze
11
+ VERSION = "2.5".freeze
12
12
 
13
13
  =begin rdoc
14
14
 
@@ -241,7 +241,7 @@ Reverse sort:
241
241
 
242
242
  Sort without case sensitivity and preceding dot:
243
243
 
244
- s = proc { |x| x =~ /^\.?/ ; $'.downcase }
244
+ s = proc { name =~ /^\.?/ ; $'.downcase }
245
245
  RbFind.run sort: s do
246
246
  puts path
247
247
  end
@@ -270,36 +270,28 @@ Sort without case sensitivity and preceding dot:
270
270
 
271
271
  private
272
272
 
273
+ Params = Struct.new :max_depth, :depth_first, :follow,
274
+ :sort, :reverse, :error, :block
275
+
273
276
  def initialize max_depth: nil, depth_first: nil, follow: nil,
274
277
  sort: true, reverse: false, error: nil, &block
275
- @max_depth = max_depth
276
- @depth_first = depth_first
277
- @follow = follow
278
- @sort = sort_parser sort, reverse
279
- @error = error
280
- @block = block
281
-
282
- ostat = $stdout.stat
283
- @ostat = ostat if ostat.file?
284
-
285
- @wd, @start, @count = Dir.getwd, Time.now, 0
278
+ @params = Params.new max_depth, depth_first, follow,
279
+ (sort_parser sort), reverse, error, block
280
+ @start, @count, @depth = Time.now, 0, 0
286
281
  end
287
282
 
288
- def sort_parser st, rev
289
- r = case st
290
- when Proc then proc { |l| l.sort_by! &st }
291
- when nil, false, nil, "" then proc { }
292
- else proc { |l| l.sort! }
283
+ def sort_parser st
284
+ case st
285
+ when Proc then proc { |l| l.sort_by! { |e| e.instance_eval &st } }
286
+ when String then proc { |l| l.sort_by! { |e| e.instance_eval st } }
287
+ when nil, false then proc { }
288
+ else proc { |l| l.sort_by! { |e| e.name } }
293
289
  end
294
- rev ? proc { |l| r.call l ; l.reverse! } : r
295
290
  end
296
291
 
297
292
  public
298
293
 
299
- attr_reader :wd, :start, :count, :depth
300
-
301
294
  def run *args
302
- @levels, @depth = [], 0
303
295
  args.flatten!
304
296
  args.compact!
305
297
  if args.empty? then
@@ -308,93 +300,68 @@ Sort without case sensitivity and preceding dot:
308
300
  args.each { |base|
309
301
  handle_error do
310
302
  File.lstat base rescue raise "`#{base}` doesn't exist."
311
- visit_depth base
303
+ e = Entry.new base, self
304
+ enter e
312
305
  end
313
306
  }
314
307
  end
315
- ensure
316
- @levels = @depth = nil
317
308
  end
318
309
 
310
+ attr_reader :start, :count
311
+ attr_reader :depth
312
+ attr_reader :current
313
+
319
314
  private
320
315
 
321
- def join_path
322
- (File.join @levels).freeze
316
+ def enter elem
317
+ c_, @current = @current, elem
318
+ @count += 1
319
+ visit_depth
320
+ ensure
321
+ @current = c_
323
322
  end
324
323
 
325
- def visit filename
326
- @depth += 1
327
- visit_depth filename
328
- ensure
329
- @depth -= 1
324
+ def visit_dir dir
325
+ return if @params.max_depth and @params.max_depth == @depth
326
+ list = (Dir.new dir).children
327
+ list = list.map { |f| Entry.new f, self }
328
+ @params.sort.call list
329
+ list.reverse! if @params.reverse
330
+ begin
331
+ @depth += 1
332
+ list.each { |e| enter e }
333
+ ensure
334
+ @depth -= 1
335
+ end
330
336
  end
331
337
 
332
- def visit_depth filename
333
- @levels.push filename.dup.freeze
334
- p_, @path = @path, join_path
335
- if @depth_first then
338
+ def visit_depth
339
+ if @params.depth_first then
336
340
  enter_dir
337
- call_block or raise "#{self.class}: prune doesn't work with :depth_first."
341
+ call_block
338
342
  else
339
343
  call_block and enter_dir
340
344
  end
341
- @count += 1
342
- ensure
343
- @path = p_
344
- @levels.pop
345
345
  end
346
346
 
347
347
  def enter_dir
348
- return unless File.directory? @path
349
- if File.symlink? @path then
350
- return unless @follow and handle_error do
351
- d = @path.dup
352
- while d != Dir::CUR_DIR do
353
- d, = File.split d
354
- raise "cyclic recursion in #@path" if File.identical? d, @path
355
- end
356
- true
357
- end
358
- end
348
+ return unless @current.stat.directory? || (@params.follow &&
349
+ @current.symlink? && @current.rstat.directory?)
359
350
  handle_error do
360
- visit_dir @path
351
+ @current.cyclic? and
352
+ raise "Cyclic recursion in #{@current.path}"
353
+ visit_dir @current.path
361
354
  end
362
355
  end
363
356
 
364
- def visit_dir dir
365
- return if @max_depth and @max_depth == @depth
366
- list = (Dir.new dir).children
367
- @sort.call list
368
- list.each { |f| visit f }
369
- ensure
370
- end
371
-
372
357
  def call_block
373
- e = Entry.new @levels.last, @path, self
374
358
  handle_error do
375
- $_, $. = e.name, count
376
359
  begin
377
- e.instance_eval &@block
360
+ $_, $. = @current.name, @count
361
+ @current.instance_eval &@params.block
378
362
  rescue Done
379
363
  end
380
- if !(e.name.equal? @levels.last) && e.name != @levels.last then
381
- if e.name then
382
- e.name == (File.basename e.name) or
383
- raise "#{self.class}: rename to `#{e.name}' may not be a path."
384
- e.name.freeze
385
- @levels.pop
386
- @levels.push e.name
387
- p, @path = @path, join_path
388
- File.rename p, @path
389
- else
390
- if e.dir? then
391
- Dir.rmdir @path
392
- else
393
- File.unlink @path
394
- end
395
- end
396
- end
397
- true
364
+ @current.path
398
365
  end
399
366
  rescue Prune
400
367
  end
@@ -402,9 +369,9 @@ Sort without case sensitivity and preceding dot:
402
369
  def handle_error
403
370
  yield
404
371
  rescue
405
- case @error
406
- when Proc then @error.call
407
- when String then instance_eval @error
372
+ case @params.error
373
+ when Proc then @params.error.call
374
+ when String then instance_eval @params.error
408
375
  else raise
409
376
  end
410
377
  nil
@@ -417,21 +384,35 @@ Sort without case sensitivity and preceding dot:
417
384
 
418
385
  attr_reader :path, :name
419
386
 
420
- def initialize name, path, walk
421
- @name, @path, @walk = name, path, walk
387
+ def initialize filename, walk
388
+ @walk = walk
389
+ @prev, @name = walk.current, filename.dup.freeze
390
+ @path = join_path @name
422
391
  end
423
392
 
393
+ protected
394
+ attr_reader :prev
395
+ private
396
+ def join_path name
397
+ @prev ? (File.join @prev.path, name).freeze : name
398
+ end
399
+ def reset
400
+ @fullpath = @stat = @rstat = @ostat = @colors = nil
401
+ end
402
+ public
403
+
404
+ def count ; @walk.count ; end
424
405
  def depth ; @walk.depth ; end
425
406
  def now ; @walk.start ; end
426
407
 
427
- def fullpath ; @fullpath ||= File.absolute_path @path, @walk.wd ; end
408
+ def fullpath ; @fullpath ||= File.absolute_path @path ; end
428
409
 
429
410
  def stat ; @stat ||= File.lstat @path ; end
430
411
  def rstat ; @rstat ||= File.stat @path ; end
431
412
 
432
413
 
433
414
  private
434
- def append_slash s ; (File.directory? s) ? (File.join s, "") : s ; end
415
+ def append_slash s ; directory? ? (File.join s, "") : s ; end
435
416
  public
436
417
 
437
418
  def path! ; append_slash path ; end
@@ -461,7 +442,23 @@ Sort without case sensitivity and preceding dot:
461
442
  end
462
443
  public
463
444
 
464
- def dir? ; stat.directory? ; end
445
+ def directory? ; stat.directory? ; end
446
+ alias dir? directory?
447
+
448
+ def symlink? ; stat.symlink? ; end
449
+
450
+ def cyclic?
451
+ e = self
452
+ loop do
453
+ e = e.prev
454
+ e or break
455
+ if File.identical? e.path, @path then
456
+ return true
457
+ end
458
+ end
459
+ false
460
+ end
461
+
465
462
 
466
463
  def aage ; @walk.start - stat.atime ; end
467
464
  def mage ; @walk.start - stat.mtime ; end
@@ -516,10 +513,10 @@ Sort without case sensitivity and preceding dot:
516
513
  end
517
514
 
518
515
 
519
- def readlink ; File.readlink @path if stat.symlink? ; end
516
+ def readlink ; File.readlink @path if symlink? ; end
520
517
 
521
518
  def broken_link?
522
- return unless stat.symlink?
519
+ return unless symlink?
523
520
  rstat
524
521
  false
525
522
  rescue
@@ -529,7 +526,7 @@ Sort without case sensitivity and preceding dot:
529
526
 
530
527
  ARROW = " -> "
531
528
  def arrow
532
- ARROW + (File.readlink @path) if stat.symlink?
529
+ ARROW + (File.readlink @path) if symlink?
533
530
  end
534
531
 
535
532
 
@@ -584,7 +581,8 @@ Sort without case sensitivity and preceding dot:
584
581
  # nothing will be done.
585
582
  #
586
583
  def open &block
587
- @ostat and @ostat.identical? @path and
584
+ @ostat ||= $stdout.stat
585
+ @ostat.identical? @path and
588
586
  raise "Refusing to open output file."
589
587
  File.open @path, &block if file?
590
588
  end
@@ -694,10 +692,27 @@ Sort without case sensitivity and preceding dot:
694
692
  include Csv
695
693
 
696
694
 
697
- def rename newname ; @name = newname ; end
695
+ def rename newname
696
+ @name = newname
697
+ newname == (File.basename newname) or
698
+ raise "Rename to `#{newname}' may not be a path."
699
+ p = join_path newname
700
+ (File.exist? p) and raise "Rename to `#{p}` would overwrite."
701
+ File.rename @path, p
702
+ @name, @path = newname.dup.freeze, p
703
+ reset
704
+ end
698
705
  alias mv rename
699
706
 
700
- def rm ; @name = nil ; end
707
+ def rm
708
+ if directory? then
709
+ Dir.rmdir @path
710
+ else
711
+ File.unlink @path
712
+ end
713
+ @name = @path = nil
714
+ reset
715
+ end
701
716
 
702
717
 
703
718
  def cname ; color name ; end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rbfind
3
3
  version: !ruby/object:Gem::Version
4
- version: '2.4'
4
+ version: '2.5'
5
5
  platform: ruby
6
6
  authors:
7
7
  - Bertram Scharpf
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-11-07 00:00:00.000000000 Z
11
+ date: 2021-02-24 00:00:00.000000000 Z
12
12
  dependencies: []
13
13
  description: |
14
14
  A replacement for the standard UNIX command find.