bitferry 0.0.6 → 0.0.8
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/CHANGES.md +39 -28
- data/README.md +231 -231
- data/bin/bitferry +2 -2
- data/bin/bitferryfx +2 -2
- data/lib/bitferry/cli.rb +376 -375
- data/lib/bitferry/fx.rb +131 -63
- data/lib/bitferry.rb +1502 -1424
- metadata +38 -14
data/lib/bitferry/fx.rb
CHANGED
@@ -1,63 +1,131 @@
|
|
1
|
-
require 'fox16'
|
2
|
-
require '
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
@
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
@
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
1
|
+
require 'fox16'
|
2
|
+
require 'stringio'
|
3
|
+
require 'bitferry'
|
4
|
+
|
5
|
+
|
6
|
+
include Fox
|
7
|
+
|
8
|
+
|
9
|
+
class Output < StringIO
|
10
|
+
|
11
|
+
def initialize(app, output)
|
12
|
+
super('rw+')
|
13
|
+
@app = app
|
14
|
+
@output = output
|
15
|
+
@output.text = nil
|
16
|
+
end
|
17
|
+
|
18
|
+
def write(*args) = @app.runOnUiThread { @output.appendText(args.join) }
|
19
|
+
|
20
|
+
def flush = nil
|
21
|
+
|
22
|
+
end
|
23
|
+
|
24
|
+
|
25
|
+
class UI < FXMainWindow
|
26
|
+
|
27
|
+
def initialize(app)
|
28
|
+
super(@app = app, 'BitferryFX', width: 400, height: 300)
|
29
|
+
top_frame = FXVerticalFrame.new(self, opts: LAYOUT_FILL)
|
30
|
+
tabs = FXTabBook.new(top_frame, opts: LAYOUT_FILL)
|
31
|
+
output_tab = FXTabItem.new(tabs, 'Output')
|
32
|
+
@output = FXText.new(tabs)
|
33
|
+
tasks_tab = FXTabItem.new(tabs, 'Tasks')
|
34
|
+
@tasks = FXTable.new(tabs)
|
35
|
+
@tasks.tableStyle |= TABLE_COL_SIZABLE | TABLE_NO_COLSELECT | TABLE_READONLY
|
36
|
+
@tasks.rowHeaderMode = LAYOUT_FIX_WIDTH
|
37
|
+
@tasks.rowHeaderWidth = 0
|
38
|
+
volumes_tab = FXTabItem.new(tabs, 'Volumes')
|
39
|
+
@volumes = FXTable.new(tabs)
|
40
|
+
@volumes.tableStyle |= TABLE_COL_SIZABLE | TABLE_NO_COLSELECT | TABLE_READONLY
|
41
|
+
@volumes.rowHeaderMode = LAYOUT_FIX_WIDTH
|
42
|
+
@volumes.rowHeaderWidth = 0
|
43
|
+
@progress = FXProgressBar.new(top_frame, height: 16, opts: LAYOUT_FILL_X | LAYOUT_FIX_HEIGHT)
|
44
|
+
controls = FXPacker.new(top_frame, opts: LAYOUT_FILL_X)
|
45
|
+
@simulate = FXCheckButton.new(controls, "&Simulation mode (dry run)\tPrevent operations from making any on-disk changes")
|
46
|
+
@simulate.checkState = Bitferry.simulate?
|
47
|
+
@verbose = FXCheckButton.new(controls, "&Verbose mode\tOutput internal logging information")
|
48
|
+
@verbose.checkState = false
|
49
|
+
buttons = FXPacker.new(top_frame, opts: LAYOUT_FILL_X | PACK_UNIFORM_WIDTH | FRAME_SUNKEN)
|
50
|
+
@process = FXButton.new(buttons, "&Process\tProcess all intact tasks", opts: BUTTON_NORMAL | BUTTON_INITIAL | BUTTON_DEFAULT | LAYOUT_SIDE_LEFT)
|
51
|
+
@process.connect(SEL_COMMAND) { process }
|
52
|
+
@process.setFocus
|
53
|
+
@quit = FXButton.new(buttons, "&Quit\tStop any pending operations and exit", opts: BUTTON_NORMAL | LAYOUT_SIDE_RIGHT)
|
54
|
+
@quit.connect(SEL_COMMAND) { exit }
|
55
|
+
@reload = FXButton.new(buttons, "&Reload\tReread volumes and tasks to capture volume changes", opts: BUTTON_NORMAL | LAYOUT_SIDE_RIGHT)
|
56
|
+
@reload.connect(SEL_COMMAND) { reset }
|
57
|
+
@sensible = [@process, @reload] # Controls which must be disabled during processing
|
58
|
+
reset
|
59
|
+
end
|
60
|
+
|
61
|
+
def process
|
62
|
+
Bitferry.simulate = @simulate.checked?
|
63
|
+
Bitferry.verbosity = @verbose.checked? ? :verbose : :default
|
64
|
+
@progress.setBarColor(:blue)
|
65
|
+
@progress.progress = 0
|
66
|
+
@output.text = nil
|
67
|
+
Thread.new {
|
68
|
+
@app.runOnUiThread { @sensible.each(&:disable) }
|
69
|
+
begin
|
70
|
+
Bitferry.process { |total, processed, failed|
|
71
|
+
@app.runOnUiThread {
|
72
|
+
@progress.setBarColor(:red) if failed > 0
|
73
|
+
@progress.progress = processed
|
74
|
+
@progress.total = total
|
75
|
+
}
|
76
|
+
}
|
77
|
+
ensure
|
78
|
+
@app.runOnUiThread { @sensible.each(&:enable) }
|
79
|
+
end
|
80
|
+
}
|
81
|
+
end
|
82
|
+
|
83
|
+
def reset
|
84
|
+
Bitferry.restore
|
85
|
+
@progress.progress = 0
|
86
|
+
$stdout = Output.new(@app, @output)
|
87
|
+
Bitferry::Logging.log = log = Logger.new($stdout)
|
88
|
+
log.progname = :bitferryfx
|
89
|
+
log.level = Logger::WARN
|
90
|
+
#
|
91
|
+
@volumes.setTableSize(Bitferry::Volume.intact.size, 2)
|
92
|
+
@volumes.setColumnText(0, 'Volume')
|
93
|
+
@volumes.setColumnText(1, 'Root')
|
94
|
+
i = 0
|
95
|
+
Bitferry::Volume.intact.each do |v|
|
96
|
+
@volumes.setItemText(i, 0, v.tag)
|
97
|
+
@volumes.setItemText(i, 1, v.root.to_s)
|
98
|
+
i += 1
|
99
|
+
end
|
100
|
+
#
|
101
|
+
@tasks.setTableSize(Bitferry::Task.intact.size, 4)
|
102
|
+
@tasks.setColumnText(0, 'Task')
|
103
|
+
@tasks.setColumnText(1, 'Operation')
|
104
|
+
@tasks.setColumnText(2, 'Source')
|
105
|
+
@tasks.setColumnText(3, 'Destination')
|
106
|
+
i = 0
|
107
|
+
Bitferry::Task.intact.each do |t|
|
108
|
+
@tasks.setItemText(i, 0, t.tag)
|
109
|
+
@tasks.setItemText(i, 1, t.show_operation)
|
110
|
+
@tasks.setItemText(i, 2, t.source.show_status)
|
111
|
+
@tasks.setItemText(i, 3, t.destination.show_status)
|
112
|
+
i += 1
|
113
|
+
end
|
114
|
+
#
|
115
|
+
end
|
116
|
+
|
117
|
+
def create
|
118
|
+
super
|
119
|
+
show(PLACEMENT_SCREEN)
|
120
|
+
end
|
121
|
+
|
122
|
+
end
|
123
|
+
|
124
|
+
|
125
|
+
FXApp.new do |app|
|
126
|
+
Bitferry.verbosity = :verbose
|
127
|
+
Bitferry.ui = :gui
|
128
|
+
UI.new(app)
|
129
|
+
app.create
|
130
|
+
app.run
|
131
|
+
end
|