Files
indiekit-endpoint-youtube/lib/controllers/videos.js
Ricardo 43090ce8af fix: dashboard controller support for multi-channel mode
The Indiekit backend UI was broken when using channels array
because the dashboard controller only checked for channelId/channelHandle.

Now uses getPrimaryChannel() helper to extract the first channel
from either single-channel or multi-channel configuration.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-01-24 13:59:25 +01:00

94 lines
2.8 KiB
JavaScript

import { YouTubeClient } from "../youtube-client.js";
import { getChannelsFromConfig } from "./channel.js";
/**
* Videos controller
*/
export const videosController = {
/**
* Get latest videos (JSON API)
* Returns videos from all configured channels
* @type {import("express").RequestHandler}
*/
async api(request, response) {
try {
const { youtubeConfig } = request.app.locals.application;
if (!youtubeConfig) {
return response.status(500).json({ error: "Not configured" });
}
const { apiKey, cacheTtl, limits } = youtubeConfig;
const channelConfigs = getChannelsFromConfig(youtubeConfig);
if (!apiKey || channelConfigs.length === 0) {
return response.status(500).json({ error: "Invalid configuration" });
}
const maxResults = Math.min(
parseInt(request.query.limit, 10) || limits?.videos || 10,
50
);
// Fetch videos from all channels in parallel
const videosPromises = channelConfigs.map(async (channelConfig) => {
const client = new YouTubeClient({
apiKey,
channelId: channelConfig.id,
channelHandle: channelConfig.handle,
cacheTtl,
});
try {
const videos = await client.getLatestVideos(maxResults);
// Add channel info to each video
return videos.map((video) => ({
...video,
channelConfigName: channelConfig.name,
}));
} catch (error) {
console.error(
`[YouTube] Failed to fetch videos for ${channelConfig.name || channelConfig.handle}:`,
error.message
);
return [];
}
});
const videosArrays = await Promise.all(videosPromises);
// For single channel, return flat array (backward compatible)
if (channelConfigs.length === 1) {
const videos = videosArrays[0] || [];
response.json({
videos,
count: videos.length,
cached: true,
});
} else {
// For multiple channels, return grouped by channel
const videosByChannel = {};
channelConfigs.forEach((config, index) => {
videosByChannel[config.name || config.handle] = videosArrays[index] || [];
});
// Also provide flat array sorted by date
const allVideos = videosArrays
.flat()
.sort((a, b) => new Date(b.publishedAt) - new Date(a.publishedAt))
.slice(0, maxResults);
response.json({
videos: allVideos, // Backward compat: flat array
videosByChannel,
count: allVideos.length,
cached: true,
});
}
} catch (error) {
console.error("[YouTube] Videos API error:", error);
response.status(500).json({ error: error.message });
}
},
};