feat(channel): add auto-schedule feature to channels with background scheduler
This commit is contained in:
@@ -72,6 +72,7 @@ const channelFormSchema = z.object({
|
||||
cooldown_generations: z.number().int().min(0).nullable().optional(),
|
||||
min_available_ratio: z.number().min(0, "Must be ≥ 0").max(1, "Must be ≤ 1"),
|
||||
}),
|
||||
auto_schedule: z.boolean(),
|
||||
});
|
||||
|
||||
type FieldErrors = Record<string, string | undefined>;
|
||||
@@ -676,6 +677,7 @@ interface EditChannelSheetProps {
|
||||
timezone: string;
|
||||
schedule_config: { blocks: ProgrammingBlock[] };
|
||||
recycle_policy: RecyclePolicy;
|
||||
auto_schedule: boolean;
|
||||
},
|
||||
) => void;
|
||||
isPending: boolean;
|
||||
@@ -699,6 +701,7 @@ export function EditChannelSheet({
|
||||
cooldown_generations: null,
|
||||
min_available_ratio: 0.1,
|
||||
});
|
||||
const [autoSchedule, setAutoSchedule] = useState(false);
|
||||
const [selectedBlockId, setSelectedBlockId] = useState<string | null>(null);
|
||||
const [fieldErrors, setFieldErrors] = useState<FieldErrors>({});
|
||||
|
||||
@@ -709,6 +712,7 @@ export function EditChannelSheet({
|
||||
setTimezone(channel.timezone);
|
||||
setBlocks(channel.schedule_config.blocks);
|
||||
setRecyclePolicy(channel.recycle_policy);
|
||||
setAutoSchedule(channel.auto_schedule);
|
||||
setSelectedBlockId(null);
|
||||
setFieldErrors({});
|
||||
}
|
||||
@@ -719,7 +723,7 @@ export function EditChannelSheet({
|
||||
if (!channel) return;
|
||||
|
||||
const result = channelFormSchema.safeParse({
|
||||
name, description, timezone, blocks, recycle_policy: recyclePolicy,
|
||||
name, description, timezone, blocks, recycle_policy: recyclePolicy, auto_schedule: autoSchedule,
|
||||
});
|
||||
|
||||
if (!result.success) {
|
||||
@@ -734,6 +738,7 @@ export function EditChannelSheet({
|
||||
timezone,
|
||||
schedule_config: { blocks },
|
||||
recycle_policy: recyclePolicy,
|
||||
auto_schedule: autoSchedule,
|
||||
});
|
||||
};
|
||||
|
||||
@@ -799,6 +804,24 @@ export function EditChannelSheet({
|
||||
className="w-full resize-none rounded-md border border-zinc-700 bg-zinc-800 px-3 py-2 text-sm text-zinc-100 placeholder:text-zinc-600 focus:border-zinc-500 focus:outline-none"
|
||||
/>
|
||||
</Field>
|
||||
|
||||
<label className="flex items-center justify-between gap-3 cursor-pointer rounded-md border border-zinc-700 bg-zinc-800/50 px-3 py-2.5">
|
||||
<div>
|
||||
<p className="text-sm text-zinc-200">Auto-generate schedule</p>
|
||||
<p className="text-[11px] text-zinc-600">Automatically regenerate when the schedule is about to expire</p>
|
||||
</div>
|
||||
<button
|
||||
type="button"
|
||||
role="switch"
|
||||
aria-checked={autoSchedule}
|
||||
onClick={() => setAutoSchedule((v) => !v)}
|
||||
className={`relative inline-flex h-5 w-9 shrink-0 rounded-full border-2 border-transparent transition-colors focus:outline-none ${autoSchedule ? "bg-zinc-300" : "bg-zinc-700"}`}
|
||||
>
|
||||
<span
|
||||
className={`pointer-events-none inline-block h-4 w-4 rounded-full bg-white shadow-sm transition-transform ${autoSchedule ? "translate-x-4" : "translate-x-0"}`}
|
||||
/>
|
||||
</button>
|
||||
</label>
|
||||
</section>
|
||||
|
||||
{/* Programming blocks */}
|
||||
|
||||
Reference in New Issue
Block a user