33 lines
2.1 KiB
JavaScript
33 lines
2.1 KiB
JavaScript
// Per-project video asset library from media/videos/videos.json.
|
|
// Includes both local clips and references to shared assets (is_shared=true).
|
|
// minio_object_key is null today; populated when assets migrate to MinIO.
|
|
exports.up = (pgm) => {
|
|
pgm.createTable('video_assets', {
|
|
id: 'id',
|
|
project_id: { type: 'integer', notNull: true, references: 'videos', onDelete: 'CASCADE' },
|
|
asset_key: { type: 'varchar(200)', notNull: true }, // key in videos.json
|
|
description: { type: 'text' },
|
|
source_file: { type: 'varchar(500)' }, // original local path
|
|
output_file: { type: 'varchar(500)' }, // rendered output path
|
|
minio_object_key: { type: 'varchar(500)' }, // future MinIO key
|
|
is_shared: { type: 'boolean', notNull: true, default: false },
|
|
cutout_name: { type: 'varchar(50)' }, // talkinghead | square | fullscreen
|
|
duration_seconds: { type: 'numeric' },
|
|
has_audio: { type: 'boolean', notNull: true, default: false },
|
|
volume: { type: 'numeric', default: 1.0 },
|
|
always_visible: { type: 'boolean', notNull: true, default: false },
|
|
pause_narration_seconds: { type: 'numeric' },
|
|
skip_seconds: { type: 'numeric' },
|
|
take_seconds: { type: 'numeric' },
|
|
filters: { type: 'jsonb' }, // per-asset filter overrides
|
|
raw_json: { type: 'jsonb' }, // full original entry
|
|
created_at: { type: 'timestamptz', notNull: true, default: pgm.func('NOW()') },
|
|
updated_at: { type: 'timestamptz', notNull: true, default: pgm.func('NOW()') },
|
|
});
|
|
pgm.addConstraint('video_assets', 'video_assets_project_key_unique', 'UNIQUE (project_id, asset_key)');
|
|
pgm.createIndex('video_assets', 'project_id', { name: 'idx_video_assets_project_id' });
|
|
pgm.createIndex('video_assets', 'is_shared', { name: 'idx_video_assets_is_shared' });
|
|
};
|
|
|
|
exports.down = (pgm) => { pgm.dropTable('video_assets'); };
|