filerenamer 0.0.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.
File without changes
@@ -0,0 +1,252 @@
1
+ #! /usr/bin/env ruby
2
+ # coding: utf-8
3
+
4
+ require "fileutils"
5
+ require "optparse"
6
+ require "filerenamer/filerenameroptionparser.rb"
7
+
8
+ require "rubygems"
9
+ gem "builtinextension"
10
+ require "string_escape_zsh.rb"
11
+ require "string_width.rb"
12
+
13
+ class FileRenamerNoRenameRuleError < Exception; end
14
+ class FileRenamerOptionError < Exception; end
15
+
16
+ # ファイル群の名前変更を一括して行うためのクラス。
17
+ #
18
+ # MEMO:
19
+ # 一度 temporary directory にリネームして格納し、
20
+ # これをカレントディレクトリからのパスに移動する形を取ると、
21
+ # ディレクトリをまたぐリネームが非常に面倒なことになる。
22
+ # - 他のリネームに依存する場合に順序問題。
23
+ # - 相互依存のデッドロック
24
+ # gem などで提供される temporary directory は
25
+ # 基本的に 抜けたときに削除される筈なので、
26
+ # 途中まで変換してから interrupt されたときに
27
+ # 中にあるファイルごと消される可能性がありそう。
28
+ # そのため、メソッド内で自分で temporary directory を作成する。
29
+ #
30
+ # 没案
31
+ # rename_rule メソッドをデフォルトで例外にしておいて、
32
+ # コマンドスクリプト側で定義するという方法は、
33
+ # メソッドの引数で ArgumentError のもとになり、
34
+ # 自由度が少なくなる。
35
+ # たとえば old_str, new_str を渡したい時と、
36
+ # 更新時刻でリネームしたいときでは必要な引数の数が異なる。
37
+ class FileRenamer
38
+
39
+ #:yes と :no が両方 true ならば例外。
40
+ #:copy, :move, :hardlink, :symlink のうち、1つ以下が true。
41
+ #全て nil ならば :move が true になる。
42
+ #:quiet が true ならば自動的に :yes が立てられる。
43
+ #:quiet が true で :no も true ならば例外。
44
+ def initialize(options)
45
+ @options = options
46
+
47
+ if (@options[:yes] && @options[:no])
48
+ raise FileRenamerOptionError,
49
+ "Conflict options: --yes and --no."
50
+ end
51
+
52
+ fileProcessModes = []
53
+ [:move, :copy, :hardlink, :symlink].each do |mode|
54
+ fileProcessModes << mode if @options[mode]
55
+ end
56
+ # 1つもなければ :move に。
57
+ @options[:move] = true if fileProcessModes == []
58
+ # 2つ以上あれば例外。
59
+ if fileProcessModes.size > 1
60
+ raise FileRenamerOptionError,
61
+ "File process modes duplicate: #{fileProcessModes.join(", ")}"
62
+ end
63
+ @command = "mv" if @options[:move]
64
+ @command = "cp -r" if @options[:copy]
65
+ @command = "ln" if @options[:hardlink]
66
+ @command = "ln -s" if @options[:symlink]
67
+
68
+ # :quiet ならば自動的に :yes
69
+ @options[:yes] = true if @options[:quiet]
70
+
71
+ # :quiet と同時に :no なら例外
72
+ if @options[:quiet] && @options[:no]
73
+ raise FileRenamerOptionError,
74
+ "Conflict options: --quiet and --no"
75
+ end
76
+ end
77
+
78
+ # 変更される名前のリストを表示し、ユーザの指示に従って実行する。
79
+ # ユーザの入力は [y|Y] で始まる文字列ならば実行、
80
+ # それ以外なら実行しない。
81
+ # files は対象のファイル名のリスト。
82
+ # 新しい名前の生成方法をブロックで渡す。
83
+ # ブロックがなければ例外 FileRenamerNoRenameRuleError
84
+ def execute(files, &block)
85
+ files = Dir::glob("*").sort if files.empty?
86
+
87
+ new_names = make_new_names(files, &block)
88
+
89
+ ok_files, ng_files = check_new_names(new_names)
90
+
91
+ unless @options[:quiet]
92
+ if ok_files.size > 0
93
+ puts "Enable files:"
94
+ max_width = ok_files.keys.max_by{|file| file.width}.width
95
+ ok_files.keys.sort.each do |old|
96
+ printf(" %s %s%s %s\n",
97
+ @command, old, " " * (max_width - old.width), ok_files[old]
98
+ )
99
+ end
100
+ end
101
+
102
+ if ng_files.size > 0
103
+ puts "Unable files:"
104
+ max_width = ng_files.keys.max_by{|file| file.width}.width
105
+ ng_files.keys.sort.each do |old|
106
+ printf(" %s %s%s %s\n",
107
+ @command, old, " " * (max_width - old.width), ng_files[old]
108
+ )
109
+ end
110
+ puts
111
+ end
112
+ end
113
+
114
+ if ok_files.empty?
115
+ puts "Done. No executable files." unless @options[:quiet]
116
+ return
117
+ elsif @options[:no]
118
+ puts "Execute? no"
119
+ return
120
+ end
121
+
122
+ if @options[:yes]
123
+ puts "Execute? yes" unless @options[:quiet]
124
+ elsif (! ask_yes?)
125
+ return
126
+ end
127
+ ok_files.each do |old, new|
128
+ run(old, new)
129
+ end
130
+ end
131
+
132
+ private
133
+
134
+ def make_new_names(files, &block)
135
+ results = {}
136
+ files.each { |i| results[i] = yield i }
137
+ return results
138
+ end
139
+
140
+ # 新しい名前リストを受け取り、問題なくリネームできるものと
141
+ # できないものを選別する。
142
+ # OK, NG の順に2つの配列を返す。
143
+ #
144
+ # 判断基準は、以下の AND 条件。
145
+ # - 新しい名前が古い名前リストに含まれないこと。
146
+ # - 新しい名前が新しい名前リストに1つ(自分)のみしかないこと。
147
+ # - 新しい名前のファイルが既に存在しないこと。
148
+ #
149
+ # 没案
150
+ # 新しい名前が変換されない古い名前であれば、
151
+ # これも NG リストに追加する。(表示用)
152
+ # このルールにすると、変換に順序依存が生じる可能性があり、
153
+ # temporary directory を経由する必要ができる。
154
+ # その結果、リネーム過程で深い temporary directory を
155
+ # 作成したり削除したりしなければならなくなる。
156
+ def check_new_names(old_new_hash)
157
+ ok_files = {}
158
+ ng_files = {}
159
+
160
+ old_new_hash.each do |old, new|
161
+ # 変化がない場合はスルー
162
+ next if old == new
163
+
164
+ # 新しい名前に nil が定義されていてもスルー
165
+ next if new == nil
166
+
167
+ # 既に存在していれば、既に存在するファイルごと NG に登録。
168
+ if FileTest.exist?(new)
169
+ ng_files[old] = new
170
+ ng_files[new] = new
171
+ next
172
+ end
173
+
174
+ # new が複数 重複していれば、 NG。
175
+ if (old_new_hash.values.select{|name| name == new}.size > 1)
176
+ ng_files[old] = new
177
+ next
178
+ end
179
+
180
+ # new が old に含まれていれば、NG。
181
+ if (old_new_hash.keys.include?(new))
182
+ ng_files[old] = new
183
+ next
184
+ end
185
+
186
+ # 上記以外の場合ならば OK
187
+
188
+ ok_files[old] = new
189
+ end
190
+ return ok_files, ng_files
191
+ end
192
+
193
+ # ユーザに判断を求める。
194
+ # 標準入力から文字列を受け取り、
195
+ # [y|Y] から始まる文字列なら true を、
196
+ # それ以外なら false を返す。
197
+ def ask_yes?
198
+ puts "Execute?"
199
+ str = $stdin.gets
200
+ if /^y/i =~ str
201
+ return true
202
+ else
203
+ return false
204
+ end
205
+ end
206
+
207
+ # コマンドを表示しつつ実行。
208
+ # 既にファイルチェックされているはずなので、チェックはしない。
209
+ # 少なくとも当面は。
210
+ # ディレクトリが必要ならここで作成。
211
+ # ディレクトリが不要になればここで削除。
212
+ # 本来ここでない方が分かり易い気もするのだが、ここに追加するのが一番簡単なので。
213
+ def run(old, new)
214
+ # 変換先のディレクトリがなければ生成
215
+ #pp old, new; exit
216
+ paths(new).each do |directory|
217
+ unless FileTest.exist?(directory)
218
+ puts " make directory: #{directory}" unless @options[:quiet]
219
+ FileUtils.mkdir_p(directory)
220
+ end
221
+ end
222
+
223
+ # 変換の実行
224
+ command = " #{@command} #{old.escape_zsh} #{new.escape_zsh}"
225
+ puts command unless @options[:quiet]
226
+ system(command)
227
+
228
+ # 変換元のディレクトリが空になっていれば削除
229
+ dirs = paths(old)
230
+ dirs.reverse.each do |directory|
231
+ if Dir.entries(directory).size == 2 # . と .. のみ
232
+ puts " remove directory: #{directory}" unless @options[:quiet]
233
+ Dir.rmdir(directory)
234
+ end
235
+ end
236
+ end
237
+
238
+ # パスに含まれるディレクトリ名を、階層ごとに切り分けたソート済配列にして返す。
239
+ # 最後の要素は含まない。
240
+ # e.g. foo/bar/baz.txt => ["foo", "foo/bar"]
241
+ # e.g. /foo/bar/baz.txt => ["/foo", "foo/bar"]
242
+ def paths(path)
243
+ dirs = path.split("/")
244
+ results = []
245
+ (dirs.size - 1).times do |i|
246
+ results << dirs[0..i].join("/")
247
+ end
248
+ results.delete_at(0) if results[0] == ""
249
+ return results
250
+ end
251
+ end
252
+
@@ -0,0 +1,36 @@
1
+ #! /usr/bin/env ruby
2
+ # coding: utf-8
3
+
4
+ require "optparse"
5
+
6
+ # FileRenamer 用のオプション解析器。
7
+ # ユーザはこれに任意のオプションを追加できる。
8
+ #
9
+ # 通常の OptionParser と異なり、インスタンス変数 @options に情報を格納する。
10
+ # @options は attr_reader に指定されているので、外部から読み取れる。
11
+ # @options は Hash であるので、ユーザが on で追加するブロックで
12
+ # そのまま鍵と値を追加できる。
13
+ # また、@options に追加せずに自前で何か適当な処理をしても良い。
14
+ class FileRenamerOptionParser < OptionParser
15
+
16
+ attr_reader :options
17
+
18
+ def initialize
19
+ @options = {}
20
+ super
21
+ on("-y", "--yes" , "Yes for all questions."){@options[:yes] = true}
22
+ on("-n", "--no" , "No for all questions."){@options[:no] = true}
23
+ on("-c", "--copy" , "Copy mode." ){@options[:copy] = true}
24
+ on("-m", "--move" , "Move mode.(default)" ){@options[:move] = true}
25
+ on("-h", "--hardlink", "Hardlink mode." ){@options[:hardlink]= true}
26
+ on("-s", "--symlink" , "Symlink mode." ){@options[:symlink] = true}
27
+ on("-q", "--quiet" , "Quiet mode. Forced non-interactive."){
28
+ @options[:quiet] = true
29
+ #このオプションが設定されているときは強制的に --yes として扱われる。
30
+ #non_interactive_mode になる。
31
+ }
32
+ end
33
+
34
+ end
35
+
36
+
File without changes
File without changes
data/test/helper.rb ADDED
@@ -0,0 +1,17 @@
1
+ require 'rubygems'
2
+ require 'bundler'
3
+ begin
4
+ Bundler.setup(:default, :development)
5
+ rescue Bundler::BundlerError => e
6
+ $stderr.puts e.message
7
+ $stderr.puts "Run `bundle install` to install missing gems"
8
+ exit e.status_code
9
+ end
10
+ require 'test/unit'
11
+
12
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
13
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
14
+ require 'filerenamer'
15
+
16
+ class Test::Unit::TestCase
17
+ end
@@ -0,0 +1,404 @@
1
+ #! /usr/bin/env ruby
2
+ # coding: utf-8
3
+
4
+ require 'helper'
5
+
6
+ require "test/unit"
7
+ require "filerenamer/filerenamer.rb"
8
+ require "stringio"
9
+ require "rubygems"
10
+ gem "capture_stdout"
11
+ require "capture_stdout"
12
+
13
+ class FileRenamer
14
+ public :check_new_names
15
+ public :ask_yes?
16
+ public :run
17
+ public :make_new_names
18
+ public :paths
19
+ attr_reader :options
20
+ end
21
+
22
+ class TC_FileRenamer < Test::Unit::TestCase
23
+ EXIST_FILE = "test/filerenamer/dummy.txt"
24
+
25
+ A_0 = "test/filerenamer/a0.txt"
26
+ A_1 = "test/filerenamer/a1.txt"
27
+
28
+ def setup
29
+ options = {}
30
+ @fr00 = FileRenamer.new(options)
31
+
32
+ options = {:copy => true, :yes => true}
33
+ @fr01 = FileRenamer.new(options)
34
+ end
35
+
36
+ def test_initialize
37
+ # yes and no
38
+ options = {
39
+ :yes => true,
40
+ :no => true,
41
+ }
42
+ assert_raise(FileRenamerOptionError){ FileRenamer.new(options) }
43
+
44
+ # ファイル操作モードがどれか1つのみ true なら OK。
45
+ options = { :copy => true, }
46
+ assert_nothing_raised{ FileRenamer.new(options) }
47
+
48
+ options = { :move => true, }
49
+ assert_nothing_raised{ FileRenamer.new(options) }
50
+
51
+ options = { :hardlink => true, }
52
+ assert_nothing_raised{ FileRenamer.new(options) }
53
+
54
+ options = { :symlink => true, }
55
+ assert_nothing_raised{ FileRenamer.new(options) }
56
+
57
+ # ファイル操作モードが空でも OK で、その場合は :move が true として扱われる。
58
+ options = { }
59
+ fr00 = FileRenamer.new(options)
60
+ assert_equal( {:move => true}, fr00.options )
61
+
62
+ # ファイル操作モードで矛盾する2つ以上が true なら例外。
63
+ options = {
64
+ :move => true,
65
+ :copy => true,
66
+ }
67
+ assert_raise(FileRenamerOptionError){ FileRenamer.new(options) }
68
+
69
+ options = {
70
+ :move => true,
71
+ :hardlink => true,
72
+ }
73
+ assert_raise(FileRenamerOptionError){ FileRenamer.new(options) }
74
+
75
+ options = {
76
+ :move => true,
77
+ :symlink => true,
78
+ }
79
+ assert_raise(FileRenamerOptionError){ FileRenamer.new(options) }
80
+
81
+ # :quiet が立てられれば、自動的に :yes も true になる。
82
+ options = {:quiet => true}
83
+ fr00 = FileRenamer.new(options)
84
+ assert_equal( {:quiet => true, :yes => true, :move => true}, fr00.options )
85
+
86
+ # :quiet が立てられれば、:yes が明示的に立っていても問題なし。
87
+ options = {:quiet => true, :yes => true}
88
+ fr00 = FileRenamer.new(options)
89
+ assert_equal( {:quiet => true, :yes => true, :move => true}, fr00.options )
90
+
91
+ # :quiet が立てられれば、:no が立っていれば例外。
92
+ options = {:quiet => true, :no => true}
93
+ assert_raise(FileRenamerOptionError){ FileRenamer.new(options) }
94
+ end
95
+
96
+ def test_execute
97
+ # :yes
98
+ # pre-process
99
+ FileUtils.rm(A_1) if FileTest.exist?(A_1)
100
+ #
101
+ options = {:copy => true, :yes => true}
102
+ fr01 = FileRenamer.new(options)
103
+ str = capture_stdout{fr01.execute([A_0]){ A_1 }}
104
+ assert_equal(true, FileTest.exist?(A_0))
105
+ assert_equal(true, FileTest.exist?(A_1))
106
+ FileUtils.rm(A_1)
107
+ #
108
+ correct =
109
+ "Enable files:\n" +
110
+ " cp -r #{A_0} #{A_1}\n" +
111
+ "Execute? yes\n" +
112
+ " cp -r #{A_0} #{A_1}\n"
113
+ t = str
114
+ assert_equal(correct[0], t[0])
115
+ assert_equal(correct[1], t[1])
116
+ assert_equal(correct[2], t[2])
117
+ assert_equal(correct[3], t[3])
118
+ assert_equal(correct[4], t[4])
119
+
120
+ # :no
121
+ FileUtils.rm(A_1) if FileTest.exist?(A_1)
122
+ #
123
+ options = {:copy => true, :no => true}
124
+ fr01 = FileRenamer.new(options)
125
+ str = capture_stdout{ fr01.execute([A_0]){ A_1 }}
126
+ assert_equal(true , FileTest.exist?(A_0))
127
+ assert_equal(false, FileTest.exist?(A_1))
128
+ #
129
+ correct =
130
+ "Enable files:\n" +
131
+ " cp -r #{A_0} #{A_1}\n" +
132
+ "Execute? no\n"
133
+ t = str
134
+ assert_equal(correct[0], t[0])
135
+ assert_equal(correct[1], t[1])
136
+ assert_equal(correct[2], t[2])
137
+
138
+ #:quiet
139
+ FileUtils.rm(A_1) if FileTest.exist?(A_1)
140
+ io = StringIO.new
141
+ #
142
+ options = {:copy => true, :quiet => true}
143
+ fr01 = FileRenamer.new(options)
144
+ str = capture_stdout{fr01.execute([A_0]){ A_1 }}
145
+ assert_equal(true, FileTest.exist?(A_0))
146
+ assert_equal(true, FileTest.exist?(A_1))
147
+ FileUtils.rm(A_1)
148
+ #
149
+ assert_equal( "", str)
150
+
151
+ #ask
152
+ FileUtils.rm(A_1) if FileTest.exist?(A_1)
153
+ $stdin = StringIO.new
154
+ $stdin.puts "yes"
155
+ $stdin.rewind
156
+ output = StringIO.new
157
+ #
158
+ options = {:copy => true}
159
+ fr01 = FileRenamer.new(options)
160
+ str = capture_stdout{fr01.execute([A_0]){ A_1 }}
161
+ assert_equal(true, FileTest.exist?(A_0))
162
+ assert_equal(true, FileTest.exist?(A_1))
163
+ FileUtils.rm(A_1)
164
+ #
165
+ correct =
166
+ "Enable files:\n" +
167
+ " cp -r #{A_0} #{A_1}\n" +
168
+ "Execute?\n" +
169
+ " cp -r #{A_0} #{A_1}\n"
170
+ t = str
171
+ assert_equal(correct[0], t[0])
172
+ assert_equal(correct[1], t[1])
173
+ assert_equal(correct[2], t[2])
174
+ assert_equal(correct[3], t[3])
175
+
176
+ $stdin = STDIN
177
+
178
+ #ask
179
+ #NG ファイルが存在するときの表示
180
+ FileUtils.rm(A_1) if FileTest.exist?(A_1)
181
+ $stdin = StringIO.new
182
+ $stdin.puts "yes"
183
+ $stdin.rewind
184
+ output = StringIO.new
185
+ #
186
+ options = {:copy => true}
187
+ fr01 = FileRenamer.new(options)
188
+ str = capture_stdout{fr01.execute([A_1]){ A_0 }}
189
+ assert_equal(true , FileTest.exist?(A_0))
190
+ assert_equal(false, FileTest.exist?(A_1))
191
+ #
192
+ correct =
193
+ "Unable files:\n" +
194
+ " cp -r #{A_0} #{A_0}\n" +
195
+ " cp -r #{A_1} #{A_0}\n" +
196
+ "\n" +
197
+ "Done. No executable files.\n"
198
+ t = str
199
+ assert_equal(correct[0], t[0])
200
+ assert_equal(correct[1], t[1])
201
+ assert_equal(correct[2], t[2])
202
+ assert_equal(correct[3], t[3])
203
+ assert_equal(correct[4], t[4])
204
+ $stdin = STDIN
205
+
206
+ ## ファイルリストを与えないときはカレントディレクトリの全ファイルが対象。
207
+ #FileUtils.rm(A_1) if FileTest.exist?(A_1)
208
+ ##
209
+ #options = {:copy => true, :no => true}
210
+ #fr01 = FileRenamer.new(options)
211
+ #str = capture_stdout{ fr01.execute([]){|name| name + ".00"}}
212
+ ##
213
+ #correct =
214
+ # "Enable files:\n" +
215
+ # " cp -r Gemfile Gemfile.00\n" +
216
+ # " cp -r Gemfile.lock Gemfile.lock.00\n" +
217
+ # " cp -r LICENSE.txt LICENSE.txt.00\n" +
218
+ # " cp -r README.rdoc README.rdoc.00\n" +
219
+ # " cp -r Rakefile Rakefile.00\n" +
220
+ # " cp -r VERSION VERSION.00\n" +
221
+ # " cp -r lib lib.00\n" +
222
+ # " cp -r test test.00\n" +
223
+ # "Execute? no\n"
224
+ #assert_equal( correct, str)
225
+ end
226
+
227
+ def test_make_new_names
228
+ assert_equal(
229
+ {
230
+ A_0 => A_0 + "00",
231
+ A_1 => A_1 + "00",
232
+ },
233
+ @fr00.make_new_names([A_0, A_1]){ |old|
234
+ old.sub(/$/, "00")
235
+ }
236
+ )
237
+ end
238
+
239
+ def test_check_new_names
240
+ files = {
241
+ "alice.txt" => EXIST_FILE,
242
+ "bcdefgh.txt" => EXIST_FILE,
243
+ "charly.txt" => "C.txt",
244
+ "david.txt" => "D.txt",
245
+ EXIST_FILE => EXIST_FILE,
246
+ "eva.txt" => "alice.txt",
247
+ "f.txt" => "f.txt",
248
+ "g.txt" => nil,
249
+ }
250
+ ok_list, ng_list = @fr00.check_new_names(files)
251
+ assert_equal(
252
+ { "charly.txt" => "C.txt",
253
+ "david.txt" => "D.txt",
254
+ },
255
+ ok_list
256
+ )
257
+ assert_equal(
258
+ { "alice.txt" => EXIST_FILE,
259
+ "bcdefgh.txt" => EXIST_FILE,
260
+ EXIST_FILE => EXIST_FILE,
261
+ "eva.txt" => "alice.txt",
262
+ },
263
+ ng_list
264
+ )
265
+
266
+ end
267
+
268
+ def test_ask_yes?
269
+ $stdin = StringIO.new
270
+ $stdin.puts "Y"
271
+ $stdin.rewind
272
+ result = Object.new
273
+ str = capture_stdout{ result = @fr00.ask_yes?}
274
+ assert_equal(true , result)
275
+ assert_equal("Execute?\n" , str)
276
+
277
+ $stdin = StringIO.new
278
+ $stdin.puts "y"
279
+ $stdin.rewind
280
+ io = capture_stdout{ result = @fr00.ask_yes?}
281
+ assert_equal(true , result)
282
+
283
+ $stdin = StringIO.new
284
+ $stdin.puts "Yreqwj"
285
+ $stdin.rewind
286
+ io = capture_stdout{ result = @fr00.ask_yes?}
287
+ assert_equal(true , result)
288
+
289
+ $stdin = StringIO.new
290
+ $stdin.puts "yrqewv"
291
+ $stdin.rewind
292
+ io = capture_stdout{ result = @fr00.ask_yes?}
293
+ assert_equal(true , result)
294
+
295
+ $stdin = StringIO.new
296
+ $stdin.puts "n"
297
+ $stdin.rewind
298
+ io = capture_stdout{ result = @fr00.ask_yes?}
299
+ assert_equal(false, result)
300
+
301
+ $stdin = StringIO.new
302
+ $stdin.puts "N"
303
+ $stdin.rewind
304
+ io = capture_stdout{ result = @fr00.ask_yes?}
305
+ assert_equal(false, result)
306
+
307
+ $stdin = StringIO.new
308
+ $stdin.puts ""
309
+ $stdin.rewind
310
+ io = capture_stdout{ result = @fr00.ask_yes?}
311
+ assert_equal(false, result)
312
+ end
313
+
314
+ def test_run
315
+ # # ディレクトリ管理不要の場合
316
+ # FileUtils.rm(A_1) if FileTest.exist?(A_1)
317
+ # #
318
+ # @fr01.run(A_0, A_1)
319
+ # io = capture_stdout{ @fr01.run(A_0, A_1) }
320
+ # io.rewind
321
+ # assert_equal([" cp -r #{A_0} #{A_1}\n"], io.readlines)
322
+ # #
323
+ # assert_equal(true, FileTest.exist?(A_0))
324
+ # assert_equal(true, FileTest.exist?(A_1))
325
+ # #
326
+ # # あとかたづけ
327
+ # FileUtils.rm(A_1)
328
+ #
329
+ # # ディレクトリ生成が必要な場合
330
+ # FileUtils.rm("tmp/#{A_1}") if FileTest.exist?("tmp/#{A_1}")
331
+ # FileUtils.rmdir("tmp/test/FileRenamer") if FileTest.exist?("tmp/test/FileRenamer")
332
+ # FileUtils.rmdir("tmp/test") if FileTest.exist?("tmp/test")
333
+ # FileUtils.rmdir("tmp") if FileTest.exist?("tmp")
334
+ # #
335
+ # io = capture_stdout{ @fr01.run(A_0, "tmp/"+A_1) }
336
+ # io.rewind
337
+ # t = io.readlines
338
+ # assert_equal(" make directory: tmp\n", t[0])
339
+ # assert_equal(" make directory: tmp/test\n", t[1])
340
+ # assert_equal(" make directory: tmp/test/FileRenamer\n", t[2])
341
+ # assert_equal(" cp -r #{A_0} tmp/#{A_1}\n", t[3])
342
+ # assert_equal(4, t.size)
343
+ # #
344
+ # assert_equal(true, FileTest.exist?(A_0))
345
+ # assert_equal(true, FileTest.exist?("tmp/#{A_1}"))
346
+ # assert_equal(true, FileTest.exist?("tmp/test/FileRenamer"))
347
+ # assert_equal(true, FileTest.exist?("tmp/test" ))
348
+ # assert_equal(true, FileTest.exist?("tmp" ))
349
+ # #
350
+ # # あとかたづけ
351
+ # FileUtils.rm("tmp/#{A_1}")
352
+ # FileUtils.rmdir("tmp/test/FileRenamer")
353
+ # FileUtils.rmdir("tmp/test" )
354
+ # FileUtils.rmdir("tmp" )
355
+
356
+ # ディレクトリ消去が必要な場合
357
+ FileUtils.rm("tmp1/dir/a1.txt") if FileTest.exist?("tmp1/dir/a1.txt")
358
+ FileUtils.rm("tmp2/dir/a1.txt") if FileTest.exist?("tmp2/dir/a1.txt")
359
+ FileUtils.rmdir("tmp1/dir") if FileTest.exist?("tmp1")
360
+ FileUtils.rmdir("tmp2/dir") if FileTest.exist?("tmp2")
361
+ FileUtils.rmdir("tmp1") if FileTest.exist?("tmp1")
362
+ FileUtils.rmdir("tmp2") if FileTest.exist?("tmp2")
363
+ #
364
+ FileUtils.mkdir("tmp1")
365
+ FileUtils.mkdir("tmp1/dir")
366
+ FileUtils.cp(A_0, "tmp1/dir/a1.txt")
367
+ #
368
+ assert_equal(false, FileTest.exist?("tmp2/dir/a2")) #実行前に変換先が存在しないことを確認。
369
+ #@fr00.run("tmp1/dir/a1.txt", "tmp2/dir/a1.txt")
370
+ str = capture_stdout{ @fr00.run("tmp1/dir/a1.txt", "tmp2/dir/a1.txt") }
371
+ t = str
372
+ correct = " make directory: tmp2\n" +
373
+ " make directory: tmp2/dir\n" +
374
+ " mv tmp1/dir/a1.txt tmp2/dir/a1.txt\n" +
375
+ " remove directory: tmp1/dir\n" +
376
+ " remove directory: tmp1\n"
377
+ assert_equal(correct, t)
378
+ #
379
+ assert_equal(false, FileTest.exist?("tmp1"))
380
+ assert_equal(true , FileTest.exist?("tmp2/dir/a1.txt")) #実行後に変換先が存在することを確認。
381
+ #
382
+ # あとかたづけ
383
+ FileUtils.rmdir("tmp1/dir")
384
+ FileUtils.rmdir("tmp1")
385
+ FileUtils.rm("tmp2/dir/a1.txt")
386
+ FileUtils.rmdir("tmp2/dir")
387
+ FileUtils.rmdir("tmp2")
388
+ end
389
+
390
+ def test_paths
391
+ assert_equal(["foo", "foo/bar"], @fr00.paths("foo/bar/baz.txt"))
392
+ assert_equal([], @fr00.paths("baz.txt"))
393
+ assert_equal(["/foo", "/foo/bar"], @fr00.paths("/foo/bar/baz.txt"))
394
+ end
395
+
396
+ #undef test_initialize
397
+ #undef test_make_new_names
398
+ #undef test_check_new_names
399
+ #undef test_ask_yes?
400
+ #undef test_execute
401
+ #undef test_run
402
+
403
+ end
404
+