fm 0.0.1.rc1 → 0.0.1.rc2

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: 7d0f4d34c704b38b5d784fe3997b9091baf88a98
4
- data.tar.gz: 29584d1d119fb84b545ffbcdaef0b0cd8889e519
3
+ metadata.gz: 79737935b4d50e7abb22c6bb7dfb5eb7763c71c0
4
+ data.tar.gz: f46f80372be4fabd3d187954737f7fbcc9117e85
5
5
  SHA512:
6
- metadata.gz: cfa1ff8a82c72590c3107be92a483ac155478afe26a6d87ba3b6e99da42466faec71bd6f20e94e1fe4ba4c47eaae2207e9afc125242fb5d3c5468ce732e6471f
7
- data.tar.gz: c600dc7a08dcb26ace4c6f0886689e19fa35ea09b0e93116fb402bb924051f158bf1730ea80f02422d04ed0ef4c3497134dc8a857b5b079b7bb0bb56a93cc0dc
6
+ metadata.gz: 544af8ebb7d73431aa7bbd8b70c8c14e2705ccb5bc2815afeacb5a774b3f7bbf5e0f1e4dba94ab20984364d0f8fa4a37ba418c124e8eb06c6fa522cdc83b4eba
7
+ data.tar.gz: f10e15da4f1567374950598ad291c60d9f5a0c5dc78ed570ee9570fa037c81fa2195b64a50a90105af97a007c209d28d589973f6114321b99f5f78ea692d6b09
data/bin/fm CHANGED
@@ -6,9 +6,25 @@ require 'fm'
6
6
  def usage
7
7
  <<EOS
8
8
  fm #{FM::VERSION}
9
- EOS
10
9
 
10
+ usage: fm <command> [args]
11
+
12
+ Available fm commands:
13
+ index Update index of the storage.
14
+ EOS
11
15
  end
12
16
 
13
17
 
14
- puts usage
18
+ if ARGV.size == 0
19
+ $stderr << usage
20
+ exit
21
+ end
22
+
23
+ cmd = ARGV.shift
24
+ case cmd
25
+ when "index"
26
+ FM.cmd_index(ARGV.clone)
27
+ else
28
+ $stderr << "fm: '#{cmd}' is not a fm command.\n"
29
+ exit
30
+ end
data/lib/fm.rb CHANGED
@@ -1 +1,2 @@
1
1
  require 'fm/version'
2
+ require 'fm/index'
data/lib/fm/file.rb ADDED
@@ -0,0 +1,15 @@
1
+ module FM
2
+
3
+ class FMFile
4
+ attr_reader :fsize
5
+ attr_reader :digest
6
+ attr_reader :path
7
+
8
+ def initialize(fsize, path, digest)
9
+ @fsize = fsize
10
+ @digest = digest
11
+ @path = path
12
+ end
13
+ end
14
+
15
+ end
data/lib/fm/index.rb ADDED
@@ -0,0 +1,131 @@
1
+ require 'digest/md5'
2
+ require 'fileutils'
3
+ require 'optparse'
4
+ require 'yaml'
5
+
6
+ require 'fm/file'
7
+ require 'fm/match'
8
+
9
+
10
+ DBFILE = ENV['HOME'] + '/.fm/fdata.db'
11
+
12
+
13
+ module FM
14
+
15
+ def cmd_index(argv)
16
+
17
+ banner = "usage: fm index [options] <PATH>"
18
+ options = {
19
+ dbfile: DBFILE,
20
+ }
21
+ OptionParser.new do |opts|
22
+ opts.banner = banner
23
+
24
+ opts.on "-h", "--help", "Show this message." do
25
+ puts opts
26
+ exit
27
+ end
28
+ end.parse!(argv)
29
+
30
+ if argv.size != 1
31
+ $stderr << "#{banner}\n"
32
+ exit
33
+ end
34
+
35
+
36
+ puts "Loading DB #{options[:dbfile]} ..."
37
+ t0 = Time.now
38
+ h = {}
39
+ needupdate = true
40
+ if File.exists?(options[:dbfile])
41
+ obj = YAML::load(File.read(options[:dbfile]))
42
+ if obj.is_a?(Hash)
43
+ h = obj
44
+ needupdate = false
45
+ end
46
+ end
47
+ t1 = Time.now
48
+ puts "Loaded DB in #{(t1-t0).round(2)}s."
49
+
50
+ indexpath = argv[0]
51
+ nnewfiles = 0
52
+ nskipfiles = 0
53
+ ndupfiles = 0
54
+ nfailfiles = 0
55
+ puts "Indexing #{indexpath} ..."
56
+ t0 = Time.now
57
+
58
+ for fpath in Dir.glob("#{indexpath}/**/*", File::FNM_DOTMATCH).select { |e| e.force_encoding("binary"); File.ftype(e) == "file" && has_folder?(".git", e) == false && has_folder?(".hg", e) == false }
59
+ begin
60
+ fpath = File.realpath(fpath).force_encoding("binary")
61
+ fsize = File.size(fpath)
62
+
63
+ if fsize == 0
64
+ nskipfiles += 1
65
+ puts "[SKIP]: #{fpath}"
66
+ next
67
+ end
68
+
69
+ # Lazy index the file.
70
+ if h[fsize].nil?
71
+ h[fsize] = fpath
72
+ needupdate = true
73
+ nnewfiles += 1
74
+ puts "[NEW]: #{fpath} nil"
75
+ else
76
+ if h[fsize].is_a?(String)
77
+ p = h[fsize]
78
+ if p == fpath
79
+ ndupfiles += 1
80
+ puts "[DUP]: #{fpath}"
81
+ puts " #{p}"
82
+ next
83
+ end
84
+
85
+ d = Digest::MD5.hexdigest(File.read(p))
86
+ h[fsize] = { d => FMFile.new(fsize, p, d) }
87
+ needupdate = true
88
+ end
89
+ digest = Digest::MD5.hexdigest(File.read(fpath))
90
+ if h[fsize][digest].nil?
91
+ h[fsize][digest] = FMFile.new(fsize, fpath, digest)
92
+ needupdate = true
93
+ nnewfiles += 1
94
+ puts "[NEW]: #{fpath} #{digest}"
95
+ else
96
+ ndupfiles += 1
97
+ puts "[DUP]: #{fpath}"
98
+ puts " #{h[fsize][digest].path}"
99
+ end
100
+ end
101
+ rescue StandardError => e
102
+ nfailfiles += 1
103
+ puts "[FAIL]: file=\"#{fpath}\" #{e.message}"
104
+ end
105
+ end
106
+ t1 = Time.now
107
+ puts "Indexing completed in #{(t1-t0).round(2)}s."
108
+
109
+ puts "Indexed:"
110
+ puts " NEW: #{nnewfiles}"
111
+ puts " DUP: #{ndupfiles}"
112
+ puts " SKIP: #{nskipfiles}"
113
+ puts " FAIL: #{nfailfiles}"
114
+
115
+ if needupdate
116
+ puts "Updating DB #{options[:dbfile]} ..."
117
+ t0 = Time.now
118
+ FileUtils.mkdir_p(File.dirname(options[:dbfile]))
119
+ File.write(options[:dbfile], YAML::dump(h))
120
+ t1 = Time.now
121
+ puts "Updated DB in #{(t1-t0).round(2)}s."
122
+ else
123
+ puts "Skip updating DB."
124
+ end
125
+
126
+ end
127
+
128
+
129
+ module_function :cmd_index
130
+
131
+ end
data/lib/fm/match.rb ADDED
@@ -0,0 +1,11 @@
1
+ module FM
2
+
3
+ def has_folder?(folder, path)
4
+ pos = (path =~ /^#{folder}\/|^#{folder}$|\/#{folder}\/|\/#{folder}$/)
5
+ pos != nil
6
+ end
7
+
8
+
9
+ module_function :has_folder?
10
+
11
+ end
data/lib/fm/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module FM
2
- VERSION = '0.0.1.rc1'
2
+ VERSION = '0.0.1.rc2'
3
3
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: fm
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.1.rc1
4
+ version: 0.0.1.rc2
5
5
  platform: ruby
6
6
  authors:
7
7
  - ShinYee
@@ -53,6 +53,9 @@ files:
53
53
  - bin/fm
54
54
  - fm.gemspec
55
55
  - lib/fm.rb
56
+ - lib/fm/file.rb
57
+ - lib/fm/index.rb
58
+ - lib/fm/match.rb
56
59
  - lib/fm/version.rb
57
60
  homepage: http://github.com/xman/ruby-fm
58
61
  licenses: