appydave-tools 0.17.1 → 0.18.1
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/CHANGELOG.md +14 -0
- data/CLAUDE.md +44 -7
- data/README.md +8 -5
- data/bin/{vat → dam} +210 -99
- data/docs/{vat → dam}/dam-vision.md +13 -13
- data/docs/{vat → dam}/session-summary-2025-11-09.md +79 -79
- data/docs/{vat → dam}/usage.md +118 -93
- data/docs/{vat → dam}/vat-testing-plan.md +94 -94
- data/docs/development/CODEX-recommendations.md +11 -0
- data/lib/appydave/tools/configuration/models/brands_config.rb +18 -3
- data/lib/appydave/tools/{vat → dam}/config.rb +32 -13
- data/lib/appydave/tools/{vat → dam}/config_loader.rb +1 -1
- data/lib/appydave/tools/{vat → dam}/manifest_generator.rb +7 -4
- data/lib/appydave/tools/{vat → dam}/project_listing.rb +1 -1
- data/lib/appydave/tools/{vat → dam}/project_resolver.rb +1 -1
- data/lib/appydave/tools/{vat → dam}/s3_operations.rb +3 -3
- data/lib/appydave/tools/dam/sync_from_ssd.rb +241 -0
- data/lib/appydave/tools/version.rb +1 -1
- data/lib/appydave/tools.rb +7 -6
- data/package.json +1 -1
- metadata +13 -12
data/bin/{vat → dam}
RENAMED
|
@@ -7,7 +7,7 @@ $LOAD_PATH.unshift(File.expand_path('../lib', __dir__))
|
|
|
7
7
|
|
|
8
8
|
require 'appydave/tools'
|
|
9
9
|
|
|
10
|
-
#
|
|
10
|
+
# DAM (Video Asset Tools) - CLI for video project management
|
|
11
11
|
class VatCLI
|
|
12
12
|
def initialize
|
|
13
13
|
@commands = {
|
|
@@ -20,6 +20,7 @@ class VatCLI
|
|
|
20
20
|
's3-cleanup-local' => method(:s3_cleanup_local_command),
|
|
21
21
|
'archive' => method(:archive_command),
|
|
22
22
|
'manifest' => method(:manifest_command),
|
|
23
|
+
'sync-ssd' => method(:sync_ssd_command),
|
|
23
24
|
# Deprecated aliases (for backward compatibility)
|
|
24
25
|
's3-cleanup' => method(:s3_cleanup_remote_command),
|
|
25
26
|
'cleanup-local' => method(:s3_cleanup_local_command)
|
|
@@ -30,9 +31,9 @@ class VatCLI
|
|
|
30
31
|
command, *args = ARGV
|
|
31
32
|
|
|
32
33
|
if command.nil?
|
|
33
|
-
puts '
|
|
34
|
-
puts 'Usage:
|
|
35
|
-
puts "Run '
|
|
34
|
+
puts 'DAM - Video Asset Tools'
|
|
35
|
+
puts 'Usage: dam [command] [options]'
|
|
36
|
+
puts "Run 'dam help' for more information."
|
|
36
37
|
exit
|
|
37
38
|
end
|
|
38
39
|
|
|
@@ -40,7 +41,7 @@ class VatCLI
|
|
|
40
41
|
@commands[command].call(args)
|
|
41
42
|
else
|
|
42
43
|
puts "Unknown command: #{command}"
|
|
43
|
-
puts "Run '
|
|
44
|
+
puts "Run 'dam help' for available commands."
|
|
44
45
|
exit 1
|
|
45
46
|
end
|
|
46
47
|
end
|
|
@@ -61,7 +62,7 @@ class VatCLI
|
|
|
61
62
|
show_config_help
|
|
62
63
|
when 'list'
|
|
63
64
|
show_list_help
|
|
64
|
-
when 's3-up', 's3-down', 's3-status', 's3-cleanup-remote', 's3-cleanup-local', 'archive', 'manifest'
|
|
65
|
+
when 's3-up', 's3-down', 's3-status', 's3-cleanup-remote', 's3-cleanup-local', 'archive', 'manifest', 'sync-ssd'
|
|
65
66
|
show_s3_help(topic)
|
|
66
67
|
when 's3-cleanup', 'cleanup-local'
|
|
67
68
|
# Deprecated command names - show deprecation notice and new help
|
|
@@ -83,13 +84,13 @@ class VatCLI
|
|
|
83
84
|
|
|
84
85
|
if brand_arg.nil?
|
|
85
86
|
# List all brands with summary
|
|
86
|
-
Appydave::Tools::
|
|
87
|
+
Appydave::Tools::Dam::ProjectListing.list_brands_with_counts
|
|
87
88
|
elsif pattern_arg
|
|
88
89
|
# Pattern matching
|
|
89
|
-
Appydave::Tools::
|
|
90
|
+
Appydave::Tools::Dam::ProjectListing.list_with_pattern(brand_arg, pattern_arg)
|
|
90
91
|
else
|
|
91
92
|
# Specific brand
|
|
92
|
-
Appydave::Tools::
|
|
93
|
+
Appydave::Tools::Dam::ProjectListing.list_brand_projects(brand_arg)
|
|
93
94
|
end
|
|
94
95
|
rescue StandardError => e
|
|
95
96
|
puts "❌ Error: #{e.message}"
|
|
@@ -99,7 +100,7 @@ class VatCLI
|
|
|
99
100
|
# S3 Upload
|
|
100
101
|
def s3_up_command(args)
|
|
101
102
|
options = parse_s3_args(args, 's3-up')
|
|
102
|
-
s3_ops = Appydave::Tools::
|
|
103
|
+
s3_ops = Appydave::Tools::Dam::S3Operations.new(options[:brand], options[:project])
|
|
103
104
|
s3_ops.upload(dry_run: options[:dry_run])
|
|
104
105
|
rescue StandardError => e
|
|
105
106
|
puts "❌ Error: #{e.message}"
|
|
@@ -109,7 +110,7 @@ class VatCLI
|
|
|
109
110
|
# S3 Download
|
|
110
111
|
def s3_down_command(args)
|
|
111
112
|
options = parse_s3_args(args, 's3-down')
|
|
112
|
-
s3_ops = Appydave::Tools::
|
|
113
|
+
s3_ops = Appydave::Tools::Dam::S3Operations.new(options[:brand], options[:project])
|
|
113
114
|
s3_ops.download(dry_run: options[:dry_run])
|
|
114
115
|
rescue StandardError => e
|
|
115
116
|
puts "❌ Error: #{e.message}"
|
|
@@ -119,7 +120,7 @@ class VatCLI
|
|
|
119
120
|
# S3 Status
|
|
120
121
|
def s3_status_command(args)
|
|
121
122
|
options = parse_s3_args(args, 's3-status')
|
|
122
|
-
s3_ops = Appydave::Tools::
|
|
123
|
+
s3_ops = Appydave::Tools::Dam::S3Operations.new(options[:brand], options[:project])
|
|
123
124
|
s3_ops.status
|
|
124
125
|
rescue StandardError => e
|
|
125
126
|
puts "❌ Error: #{e.message}"
|
|
@@ -129,7 +130,7 @@ class VatCLI
|
|
|
129
130
|
# S3 Cleanup Remote
|
|
130
131
|
def s3_cleanup_remote_command(args)
|
|
131
132
|
options = parse_s3_args(args, 's3-cleanup-remote')
|
|
132
|
-
s3_ops = Appydave::Tools::
|
|
133
|
+
s3_ops = Appydave::Tools::Dam::S3Operations.new(options[:brand], options[:project])
|
|
133
134
|
s3_ops.cleanup(force: options[:force], dry_run: options[:dry_run])
|
|
134
135
|
rescue StandardError => e
|
|
135
136
|
puts "❌ Error: #{e.message}"
|
|
@@ -139,7 +140,7 @@ class VatCLI
|
|
|
139
140
|
# S3 Cleanup Local
|
|
140
141
|
def s3_cleanup_local_command(args)
|
|
141
142
|
options = parse_s3_args(args, 's3-cleanup-local')
|
|
142
|
-
s3_ops = Appydave::Tools::
|
|
143
|
+
s3_ops = Appydave::Tools::Dam::S3Operations.new(options[:brand], options[:project])
|
|
143
144
|
s3_ops.cleanup_local(force: options[:force], dry_run: options[:dry_run])
|
|
144
145
|
rescue StandardError => e
|
|
145
146
|
puts "❌ Error: #{e.message}"
|
|
@@ -149,7 +150,7 @@ class VatCLI
|
|
|
149
150
|
# Archive project to SSD
|
|
150
151
|
def archive_command(args)
|
|
151
152
|
options = parse_s3_args(args, 'archive')
|
|
152
|
-
s3_ops = Appydave::Tools::
|
|
153
|
+
s3_ops = Appydave::Tools::Dam::S3Operations.new(options[:brand], options[:project])
|
|
153
154
|
s3_ops.archive(force: options[:force], dry_run: options[:dry_run])
|
|
154
155
|
rescue StandardError => e
|
|
155
156
|
puts "❌ Error: #{e.message}"
|
|
@@ -157,49 +158,109 @@ class VatCLI
|
|
|
157
158
|
end
|
|
158
159
|
|
|
159
160
|
# Generate manifest
|
|
160
|
-
# rubocop:disable Metrics/MethodLength
|
|
161
161
|
def manifest_command(args)
|
|
162
162
|
all_brands = args.include?('--all')
|
|
163
163
|
args = args.reject { |arg| arg.start_with?('--') }
|
|
164
164
|
brand_arg = args[0]
|
|
165
165
|
|
|
166
166
|
if all_brands
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
167
|
+
generate_all_manifests
|
|
168
|
+
elsif brand_arg
|
|
169
|
+
generate_single_manifest(brand_arg)
|
|
170
|
+
else
|
|
171
|
+
show_manifest_usage
|
|
172
|
+
end
|
|
173
|
+
rescue StandardError => e
|
|
174
|
+
puts "❌ Error: #{e.message}"
|
|
175
|
+
exit 1
|
|
176
|
+
end
|
|
175
177
|
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
178
|
+
def generate_all_manifests
|
|
179
|
+
Appydave::Tools::Configuration::Config.configure
|
|
180
|
+
brands_config = Appydave::Tools::Configuration::Config.brands
|
|
179
181
|
|
|
182
|
+
results = []
|
|
183
|
+
brands_config.brands.each do |brand_info|
|
|
184
|
+
brand_key = brand_info.key
|
|
180
185
|
puts ''
|
|
181
186
|
puts '=' * 60
|
|
182
|
-
puts '✅ All brand manifests generated!'
|
|
183
|
-
elsif brand_arg
|
|
184
|
-
# Generate manifest for specific brand
|
|
185
|
-
brand = Appydave::Tools::Vat::Config.expand_brand(brand_arg)
|
|
186
|
-
ENV['BRAND_PATH'] = Appydave::Tools::Vat::Config.brand_path(brand)
|
|
187
187
|
|
|
188
|
-
generator = Appydave::Tools::
|
|
189
|
-
generator.generate
|
|
188
|
+
generator = Appydave::Tools::Dam::ManifestGenerator.new(brand_key)
|
|
189
|
+
result = generator.generate
|
|
190
|
+
results << result if result
|
|
191
|
+
end
|
|
192
|
+
|
|
193
|
+
display_manifest_summary(results)
|
|
194
|
+
end
|
|
195
|
+
|
|
196
|
+
def generate_single_manifest(brand_arg)
|
|
197
|
+
Appydave::Tools::Dam::Config.expand_brand(brand_arg)
|
|
198
|
+
ENV['BRAND_PATH'] = Appydave::Tools::Dam::Config.brand_path(brand_arg)
|
|
199
|
+
|
|
200
|
+
generator = Appydave::Tools::Dam::ManifestGenerator.new(brand_arg)
|
|
201
|
+
generator.generate
|
|
202
|
+
end
|
|
203
|
+
|
|
204
|
+
def show_manifest_usage
|
|
205
|
+
puts 'Usage: dam manifest <brand> [--all]'
|
|
206
|
+
puts ''
|
|
207
|
+
puts 'Examples:'
|
|
208
|
+
puts ' dam manifest appydave # Generate manifest for AppyDave brand'
|
|
209
|
+
puts ' dam manifest --all # Generate manifests for all brands'
|
|
210
|
+
exit 1
|
|
211
|
+
end
|
|
212
|
+
|
|
213
|
+
def display_manifest_summary(results)
|
|
214
|
+
puts ''
|
|
215
|
+
puts '=' * 60
|
|
216
|
+
puts '📋 Summary - Generated Manifests:'
|
|
217
|
+
puts ''
|
|
218
|
+
|
|
219
|
+
successful = results.select { |r| r[:success] }
|
|
220
|
+
failed = results.reject { |r| r[:success] }
|
|
221
|
+
|
|
222
|
+
successful.each do |result|
|
|
223
|
+
brand_display = result[:brand].ljust(15)
|
|
224
|
+
puts "✅ #{brand_display} #{result[:path]}"
|
|
225
|
+
end
|
|
226
|
+
|
|
227
|
+
failed.each do |result|
|
|
228
|
+
brand_display = result[:brand].ljust(15)
|
|
229
|
+
puts "❌ #{brand_display} No projects found"
|
|
230
|
+
end
|
|
231
|
+
|
|
232
|
+
puts ''
|
|
233
|
+
puts "Total manifests generated: #{successful.size}"
|
|
234
|
+
end
|
|
235
|
+
|
|
236
|
+
# Sync light files from SSD to local
|
|
237
|
+
def sync_ssd_command(args)
|
|
238
|
+
dry_run = args.include?('--dry-run')
|
|
239
|
+
args = args.reject { |arg| arg.start_with?('--') }
|
|
240
|
+
brand_arg = args[0]
|
|
241
|
+
|
|
242
|
+
if brand_arg
|
|
243
|
+
# Sync specific brand
|
|
244
|
+
Appydave::Tools::Dam::Config.expand_brand(brand_arg)
|
|
245
|
+
ENV['BRAND_PATH'] = Appydave::Tools::Dam::Config.brand_path(brand_arg)
|
|
246
|
+
|
|
247
|
+
syncer = Appydave::Tools::Dam::SyncFromSsd.new(brand_arg)
|
|
248
|
+
syncer.sync(dry_run: dry_run)
|
|
190
249
|
else
|
|
191
|
-
puts 'Usage:
|
|
250
|
+
puts 'Usage: dam sync-ssd <brand> [--dry-run]'
|
|
251
|
+
puts ''
|
|
252
|
+
puts 'Sync light files (subtitles, images, docs) from SSD to local for archived projects.'
|
|
253
|
+
puts 'Does NOT sync heavy video files (MP4, MOV, etc.).'
|
|
192
254
|
puts ''
|
|
193
255
|
puts 'Examples:'
|
|
194
|
-
puts '
|
|
195
|
-
puts '
|
|
256
|
+
puts ' dam sync-ssd appydave # Sync all AppyDave projects from SSD'
|
|
257
|
+
puts ' dam sync-ssd appydave --dry-run # Preview what would be synced'
|
|
196
258
|
exit 1
|
|
197
259
|
end
|
|
198
260
|
rescue StandardError => e
|
|
199
261
|
puts "❌ Error: #{e.message}"
|
|
200
262
|
exit 1
|
|
201
263
|
end
|
|
202
|
-
# rubocop:enable Metrics/MethodLength
|
|
203
264
|
|
|
204
265
|
# Parse S3 command arguments
|
|
205
266
|
def parse_s3_args(args, command)
|
|
@@ -212,21 +273,21 @@ class VatCLI
|
|
|
212
273
|
|
|
213
274
|
if brand_arg.nil?
|
|
214
275
|
# Auto-detect from PWD
|
|
215
|
-
brand, project_id = Appydave::Tools::
|
|
276
|
+
brand, project_id = Appydave::Tools::Dam::ProjectResolver.detect_from_pwd
|
|
216
277
|
if brand.nil? || project_id.nil?
|
|
217
278
|
puts '❌ Could not auto-detect brand/project from current directory'
|
|
218
|
-
puts "Usage:
|
|
279
|
+
puts "Usage: dam #{command} <brand> <project> [--dry-run]"
|
|
219
280
|
exit 1
|
|
220
281
|
end
|
|
221
282
|
brand_key = brand # Already detected, use as-is
|
|
222
283
|
else
|
|
223
284
|
brand_key = brand_arg # Use the shortcut/key (e.g., 'appydave')
|
|
224
|
-
brand = Appydave::Tools::
|
|
225
|
-
project_id = Appydave::Tools::
|
|
285
|
+
brand = Appydave::Tools::Dam::Config.expand_brand(brand_arg) # Expand for path resolution
|
|
286
|
+
project_id = Appydave::Tools::Dam::ProjectResolver.resolve(brand_arg, project_arg)
|
|
226
287
|
end
|
|
227
288
|
|
|
228
289
|
# Set ENV for compatibility with ConfigLoader
|
|
229
|
-
ENV['BRAND_PATH'] = Appydave::Tools::
|
|
290
|
+
ENV['BRAND_PATH'] = Appydave::Tools::Dam::Config.brand_path(brand)
|
|
230
291
|
|
|
231
292
|
{ brand: brand_key, project: project_id, dry_run: dry_run, force: force }
|
|
232
293
|
end
|
|
@@ -235,9 +296,9 @@ class VatCLI
|
|
|
235
296
|
# rubocop:disable Metrics/MethodLength
|
|
236
297
|
def show_main_help
|
|
237
298
|
puts <<~HELP
|
|
238
|
-
|
|
299
|
+
DAM (Video Asset Tools) - Unified CLI for video project management
|
|
239
300
|
|
|
240
|
-
Usage:
|
|
301
|
+
Usage: dam [command] [options]
|
|
241
302
|
|
|
242
303
|
Available Commands:
|
|
243
304
|
help [command] Show help information
|
|
@@ -253,23 +314,24 @@ class VatCLI
|
|
|
253
314
|
Archive Commands:
|
|
254
315
|
archive <brand> <project> Copy project to SSD backup
|
|
255
316
|
manifest <brand> [--all] Generate project manifest
|
|
317
|
+
sync-ssd <brand> Restore light files from SSD
|
|
256
318
|
|
|
257
319
|
List Modes:
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
320
|
+
dam list All brands with counts/sizes
|
|
321
|
+
dam list appydave All projects for brand
|
|
322
|
+
dam list appydave 'b6*' Pattern matching
|
|
261
323
|
|
|
262
324
|
Help Topics:
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
325
|
+
dam help brands List available brands
|
|
326
|
+
dam help workflows Explain FliVideo vs Storyline workflows
|
|
327
|
+
dam help config Configuration file details
|
|
266
328
|
|
|
267
329
|
Examples:
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
330
|
+
dam list
|
|
331
|
+
dam s3-up appydave b65
|
|
332
|
+
dam s3-down voz boy-baker --dry-run
|
|
333
|
+
dam s3-status appydave b65
|
|
334
|
+
dam s3-cleanup appydave b65 --force
|
|
273
335
|
|
|
274
336
|
For more information: https://github.com/appydave/appydave-tools
|
|
275
337
|
HELP
|
|
@@ -279,7 +341,7 @@ class VatCLI
|
|
|
279
341
|
puts <<~HELP
|
|
280
342
|
Available Brands
|
|
281
343
|
|
|
282
|
-
|
|
344
|
+
DAM supports multi-tenant video project management with brand shortcuts:
|
|
283
345
|
|
|
284
346
|
Brand Shortcuts:
|
|
285
347
|
appydave → v-appydave (AppyDave brand videos)
|
|
@@ -290,10 +352,10 @@ class VatCLI
|
|
|
290
352
|
ss → v-supportsignal (SupportSignal client)
|
|
291
353
|
|
|
292
354
|
Usage:
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
355
|
+
dam list # Show all brands
|
|
356
|
+
dam list --summary # Show brands with project counts
|
|
357
|
+
dam list appydave # List all AppyDave projects
|
|
358
|
+
dam s3-up voz boy-baker # Upload VOZ project
|
|
297
359
|
HELP
|
|
298
360
|
end
|
|
299
361
|
|
|
@@ -301,7 +363,7 @@ class VatCLI
|
|
|
301
363
|
puts <<~HELP
|
|
302
364
|
Video Workflows
|
|
303
365
|
|
|
304
|
-
|
|
366
|
+
DAM supports two primary video content workflows:
|
|
305
367
|
|
|
306
368
|
1. FliVideo Workflow (AppyDave)
|
|
307
369
|
- Sequential chapter-based recording
|
|
@@ -335,7 +397,7 @@ class VatCLI
|
|
|
335
397
|
puts <<~HELP
|
|
336
398
|
Configuration
|
|
337
399
|
|
|
338
|
-
|
|
400
|
+
DAM uses two configuration levels:
|
|
339
401
|
|
|
340
402
|
1. System Configuration (settings.json)
|
|
341
403
|
Location: ~/.config/appydave/settings.json
|
|
@@ -381,23 +443,23 @@ class VatCLI
|
|
|
381
443
|
puts <<~HELP
|
|
382
444
|
List Command
|
|
383
445
|
|
|
384
|
-
Usage:
|
|
446
|
+
Usage: dam list [brand] [pattern]
|
|
385
447
|
|
|
386
448
|
Modes:
|
|
387
449
|
1. List all brands with summary:
|
|
388
|
-
|
|
450
|
+
dam list
|
|
389
451
|
|
|
390
452
|
2. List projects for specific brand:
|
|
391
|
-
|
|
453
|
+
dam list appydave
|
|
392
454
|
|
|
393
455
|
3. Pattern matching:
|
|
394
|
-
|
|
395
|
-
|
|
456
|
+
dam list appydave 'b6*' # All projects b60-b69
|
|
457
|
+
dam list appydave 'b4*' # All projects b40-b49
|
|
396
458
|
|
|
397
459
|
Examples:
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
460
|
+
dam list # Tabular: brand, project count, size, modified
|
|
461
|
+
dam list voz # Tabular: all VOZ projects with size/date
|
|
462
|
+
dam list appydave 'b6*' # Tabular: b60-b69 projects with size/date
|
|
401
463
|
HELP
|
|
402
464
|
end
|
|
403
465
|
|
|
@@ -410,7 +472,7 @@ class VatCLI
|
|
|
410
472
|
|
|
411
473
|
Upload files from local s3-staging/ directory to S3 for collaboration.
|
|
412
474
|
|
|
413
|
-
Usage:
|
|
475
|
+
Usage: dam s3-up <brand> <project> [--dry-run]
|
|
414
476
|
|
|
415
477
|
Features:
|
|
416
478
|
- Smart sync: Skips unchanged files (MD5 comparison)
|
|
@@ -418,9 +480,9 @@ class VatCLI
|
|
|
418
480
|
- Dry-run support: Preview changes without uploading
|
|
419
481
|
|
|
420
482
|
Examples:
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
|
|
483
|
+
dam s3-up appydave b65 # Upload b65 project
|
|
484
|
+
dam s3-up voz boy-baker --dry-run # Preview upload
|
|
485
|
+
dam s3-up # Auto-detect from PWD
|
|
424
486
|
|
|
425
487
|
Notes:
|
|
426
488
|
- Files must be in project's s3-staging/ directory
|
|
@@ -433,7 +495,7 @@ class VatCLI
|
|
|
433
495
|
|
|
434
496
|
Download files from S3 to local s3-staging/ directory.
|
|
435
497
|
|
|
436
|
-
Usage:
|
|
498
|
+
Usage: dam s3-down <brand> <project> [--dry-run]
|
|
437
499
|
|
|
438
500
|
Features:
|
|
439
501
|
- Smart sync: Skips unchanged files (MD5 comparison)
|
|
@@ -441,9 +503,9 @@ class VatCLI
|
|
|
441
503
|
- Dry-run support: Preview changes without downloading
|
|
442
504
|
|
|
443
505
|
Examples:
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
506
|
+
dam s3-down appydave b65 # Download b65 project
|
|
507
|
+
dam s3-down voz boy-baker --dry-run # Preview download
|
|
508
|
+
dam s3-down # Auto-detect from PWD
|
|
447
509
|
|
|
448
510
|
Notes:
|
|
449
511
|
- Creates s3-staging/ directory if needed
|
|
@@ -455,7 +517,7 @@ class VatCLI
|
|
|
455
517
|
|
|
456
518
|
Check sync status between local and S3 files.
|
|
457
519
|
|
|
458
|
-
Usage:
|
|
520
|
+
Usage: dam s3-status <brand> [project]
|
|
459
521
|
|
|
460
522
|
Features:
|
|
461
523
|
- Shows all files (S3 and local)
|
|
@@ -464,8 +526,8 @@ class VatCLI
|
|
|
464
526
|
- Shows file counts for both S3 and local
|
|
465
527
|
|
|
466
528
|
Examples:
|
|
467
|
-
|
|
468
|
-
|
|
529
|
+
dam s3-status appydave b65 # Check b65 status
|
|
530
|
+
dam s3-status # Auto-detect from PWD
|
|
469
531
|
|
|
470
532
|
Status Indicators:
|
|
471
533
|
✓ [synced] - Local and S3 match (MD5)
|
|
@@ -479,7 +541,7 @@ class VatCLI
|
|
|
479
541
|
|
|
480
542
|
Delete all S3 files for a project (use with caution).
|
|
481
543
|
|
|
482
|
-
Usage:
|
|
544
|
+
Usage: dam s3-cleanup-remote <brand> <project> --force [--dry-run]
|
|
483
545
|
|
|
484
546
|
Features:
|
|
485
547
|
- Requires --force flag for safety
|
|
@@ -487,9 +549,9 @@ class VatCLI
|
|
|
487
549
|
- Shows deleted/failed counts
|
|
488
550
|
|
|
489
551
|
Examples:
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
|
|
552
|
+
dam s3-cleanup-remote appydave b65 --dry-run # Preview deletion
|
|
553
|
+
dam s3-cleanup-remote appydave b65 --force # Actually delete
|
|
554
|
+
dam s3-cleanup-remote --force # Auto-detect from PWD
|
|
493
555
|
|
|
494
556
|
⚠️ WARNING: This permanently deletes files from S3.
|
|
495
557
|
Ensure you have local backups before running.
|
|
@@ -502,7 +564,7 @@ class VatCLI
|
|
|
502
564
|
|
|
503
565
|
Delete all local files in the s3-staging/ directory for a project.
|
|
504
566
|
|
|
505
|
-
Usage:
|
|
567
|
+
Usage: dam s3-cleanup-local <brand> <project> --force [--dry-run]
|
|
506
568
|
|
|
507
569
|
Features:
|
|
508
570
|
- Requires --force flag for safety
|
|
@@ -511,9 +573,9 @@ class VatCLI
|
|
|
511
573
|
- Shows deleted/failed counts
|
|
512
574
|
|
|
513
575
|
Examples:
|
|
514
|
-
|
|
515
|
-
|
|
516
|
-
|
|
576
|
+
dam s3-cleanup-local appydave b65 --dry-run # Preview deletion
|
|
577
|
+
dam s3-cleanup-local appydave b65 --force # Actually delete
|
|
578
|
+
dam s3-cleanup-local --force # Auto-detect from PWD
|
|
517
579
|
|
|
518
580
|
Use Cases:
|
|
519
581
|
- Free up disk space after uploading to S3
|
|
@@ -531,7 +593,7 @@ class VatCLI
|
|
|
531
593
|
|
|
532
594
|
Copy completed video project to SSD for long-term backup.
|
|
533
595
|
|
|
534
|
-
Usage:
|
|
596
|
+
Usage: dam archive <brand> <project> [--force] [--dry-run]
|
|
535
597
|
|
|
536
598
|
Features:
|
|
537
599
|
- Copies entire project directory to SSD backup location
|
|
@@ -541,10 +603,10 @@ class VatCLI
|
|
|
541
603
|
- Dry-run support: Preview archive operation
|
|
542
604
|
|
|
543
605
|
Examples:
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
|
|
547
|
-
|
|
606
|
+
dam archive appydave b63 --dry-run # Preview archive
|
|
607
|
+
dam archive appydave b63 # Copy to SSD only
|
|
608
|
+
dam archive appydave b63 --force # Copy and delete local
|
|
609
|
+
dam archive # Auto-detect from PWD
|
|
548
610
|
|
|
549
611
|
Storage Strategy:
|
|
550
612
|
Local → S3 (90-day collaboration) → SSD (long-term archive)
|
|
@@ -567,7 +629,7 @@ class VatCLI
|
|
|
567
629
|
|
|
568
630
|
Generate a JSON manifest of all video projects for a brand.
|
|
569
631
|
|
|
570
|
-
Usage:
|
|
632
|
+
Usage: dam manifest <brand> [--all]
|
|
571
633
|
|
|
572
634
|
Features:
|
|
573
635
|
- Scans local and SSD storage locations
|
|
@@ -578,9 +640,9 @@ class VatCLI
|
|
|
578
640
|
- Outputs projects.json in brand directory
|
|
579
641
|
|
|
580
642
|
Examples:
|
|
581
|
-
|
|
582
|
-
|
|
583
|
-
|
|
643
|
+
dam manifest appydave # Generate manifest for AppyDave
|
|
644
|
+
dam manifest voz # Generate manifest for VOZ
|
|
645
|
+
dam manifest --all # Generate manifests for all brands
|
|
584
646
|
|
|
585
647
|
Output Location:
|
|
586
648
|
- Single brand: <brand-path>/projects.json
|
|
@@ -613,6 +675,55 @@ class VatCLI
|
|
|
613
675
|
- Validate project naming conventions
|
|
614
676
|
- Prepare for sync-ssd operations
|
|
615
677
|
HELP
|
|
678
|
+
when 'sync-ssd'
|
|
679
|
+
puts <<~HELP
|
|
680
|
+
Sync from SSD Command
|
|
681
|
+
|
|
682
|
+
Restore light files (subtitles, images, docs) from SSD to local for archived projects.
|
|
683
|
+
Does NOT sync heavy video files (MP4, MOV, etc.).
|
|
684
|
+
|
|
685
|
+
Usage: dam sync-ssd <brand> [--dry-run]
|
|
686
|
+
|
|
687
|
+
Features:
|
|
688
|
+
- Syncs ALL projects for a brand from manifest (projects.json)
|
|
689
|
+
- Only copies light files: .srt, .vtt, .jpg, .png, .md, .txt, .json
|
|
690
|
+
- Excludes heavy files: .mp4, .mov, .avi, .mkv, .webm
|
|
691
|
+
- Smart skip: Skips files already synced (size comparison)
|
|
692
|
+
- Creates archived/{range}/{project}/ directory structure
|
|
693
|
+
- Dry-run support: Preview what will be synced
|
|
694
|
+
|
|
695
|
+
Examples:
|
|
696
|
+
dam sync-ssd appydave # Sync all AppyDave projects
|
|
697
|
+
dam sync-ssd appydave --dry-run # Preview sync
|
|
698
|
+
dam sync-ssd voz # Sync all VOZ projects
|
|
699
|
+
|
|
700
|
+
Requirements:
|
|
701
|
+
- Must have projects.json manifest (run: dam manifest <brand>)
|
|
702
|
+
- SSD must be mounted
|
|
703
|
+
- Projects must exist on SSD
|
|
704
|
+
|
|
705
|
+
Behavior:
|
|
706
|
+
- Only syncs projects that exist on SSD but NOT in local flat structure
|
|
707
|
+
- Creates archived/{range}/{project}/ structure for restored files
|
|
708
|
+
- Skips projects already in local flat structure
|
|
709
|
+
- Skips files with same size (already synced)
|
|
710
|
+
|
|
711
|
+
Use Cases:
|
|
712
|
+
- Restore supporting files for archived projects
|
|
713
|
+
- Get subtitles and images without huge video files
|
|
714
|
+
- Prepare project for re-editing (download videos separately)
|
|
715
|
+
- Access project documentation and metadata
|
|
716
|
+
|
|
717
|
+
Storage Strategy:
|
|
718
|
+
SSD (archive) → Local archived/{range}/{project}/ (light files only)
|
|
719
|
+
|
|
720
|
+
⚠️ NOTE: This only syncs LIGHT files. Heavy video files remain on SSD.
|
|
721
|
+
If you need video files, copy them manually from SSD.
|
|
722
|
+
|
|
723
|
+
Configuration:
|
|
724
|
+
- SSD backup path configured per brand in brands.json
|
|
725
|
+
- Manifest file: <brand-path>/projects.json
|
|
726
|
+
HELP
|
|
616
727
|
end
|
|
617
728
|
end
|
|
618
729
|
# rubocop:enable Metrics/CyclomaticComplexity
|