Implement asynchronous bumper rendering and add integration tests: refactor BumperAsset to support async rendering, introduce BumperRenderBackgroundService for processing, and create TeleWave.Integration.Tests with Testcontainers-Postgres for comprehensive testing of scheduling and bumper generation scenarios. Update documentation and ensure tests skip if Docker is not available.
This commit is contained in:
@@ -1,10 +1,12 @@
|
||||
namespace TeleWave.Domain.Broadcast;
|
||||
|
||||
/// <summary>
|
||||
/// Кэш отрендеренной ТВ-заставки перехода. Один сгенерированный <see cref="MediaAssetId"/> на
|
||||
/// уникальную комбинацию (<see cref="FromShowId"/> → <see cref="ToShowId"/>) при данной
|
||||
/// <see cref="Signature"/> (хэш названий шоу и версии шаблона). Переиспользуется между днями и
|
||||
/// каналами; при смене названий/шаблона <see cref="Signature"/> меняется и рендерится новый ассет.
|
||||
/// Кэш ТВ-заставки перехода. Один сгенерированный <see cref="MediaAssetId"/> на уникальную комбинацию
|
||||
/// (<see cref="FromShowId"/> → <see cref="ToShowId"/>) при данной <see cref="Signature"/> (хэш названий
|
||||
/// шоу и версии шаблона). Ассет создаётся в статусе Pending и рендерится ffmpeg'ом асинхронно фоновым
|
||||
/// сервисом — поэтому здесь же храним, ЧЕМ его рендерить (<see cref="ChannelId"/>/<see cref="TemplateId"/>/
|
||||
/// <see cref="VariantId"/>), чтобы фоновый рендерер восстановил спецификацию без участия планировщика.
|
||||
/// Переиспользуется между днями и каналами; при смене названий/шаблона сигнатура меняется — новый ассет.
|
||||
/// </summary>
|
||||
public class BumperAsset
|
||||
{
|
||||
@@ -12,10 +14,15 @@ public class BumperAsset
|
||||
public Guid FromShowId { get; private set; }
|
||||
public Guid ToShowId { get; private set; }
|
||||
|
||||
/// <summary>Канал/блок/подблок, по которым фоновый рендерер восстановит спецификацию заставки.</summary>
|
||||
public Guid ChannelId { get; private set; }
|
||||
public Guid TemplateId { get; private set; }
|
||||
public Guid VariantId { get; private set; }
|
||||
|
||||
/// <summary>Хэш входных данных рендера (названия «из/в» + версия шаблона).</summary>
|
||||
public string Signature { get; private set; } = string.Empty;
|
||||
|
||||
/// <summary>Сгенерированный ассет-заставка (нарезан в assets/{id}, статус Ready).</summary>
|
||||
/// <summary>Сгенерированный ассет-заставка (нарезается в assets/{id} фоновым рендерером).</summary>
|
||||
public Guid MediaAssetId { get; private set; }
|
||||
|
||||
public DateTimeOffset CreatedAt { get; private set; }
|
||||
@@ -23,6 +30,9 @@ public class BumperAsset
|
||||
private BumperAsset() { }
|
||||
|
||||
public static BumperAsset Create(
|
||||
Guid channelId,
|
||||
Guid templateId,
|
||||
Guid variantId,
|
||||
Guid fromShowId,
|
||||
Guid toShowId,
|
||||
string signature,
|
||||
@@ -31,6 +41,9 @@ public class BumperAsset
|
||||
new()
|
||||
{
|
||||
Id = Guid.NewGuid(),
|
||||
ChannelId = channelId,
|
||||
TemplateId = templateId,
|
||||
VariantId = variantId,
|
||||
FromShowId = fromShowId,
|
||||
ToShowId = toShowId,
|
||||
Signature = signature,
|
||||
|
||||
@@ -56,8 +56,9 @@ public class MediaAsset
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Ассет, сгенерированный системой (ТВ-заставка). Нарезку делает не общий пайплайн обработки, а
|
||||
/// специализированный рендерер, поэтому сразу помечаем <see cref="MarkReady"/> после создания.
|
||||
/// Ассет, сгенерированный системой (ТВ-заставка). Создаётся в <see cref="MediaAssetStatus.Pending"/>
|
||||
/// и нарезается не общим пайплайном обработки, а специализированным фоновым рендерером
|
||||
/// (BumperRenderBackgroundService), который по готовности вызывает <see cref="MarkReady"/>.
|
||||
/// </summary>
|
||||
public static MediaAsset RegisterGenerated(string displayName)
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user