eirtube/api/channels.js
2024-12-18 17:55:05 -06:00

91 lines
3.4 KiB
JavaScript
Executable File

const fetch = require("node-fetch")
const {render} = require("pinski/plugins")
const {fetchChannel} = require("../utils/youtube")
const {getUser} = require("../utils/getuser")
const {request} = require("../utils/request")
const converters = require("../utils/converters")
const dearrow = require("../eirtubeMods/sb")
module.exports = [
{
route: `/(c|channel|user)/([^/]+)/?([^?]+)?`, methods: ["GET"], code: async ({req, fill, url}) => {
const path = fill[0]
const id = fill[1]
const subpage = fill[2]
const user = getUser(req)
const settings = user.getSettingsOrDefaults()
const data = await fetchChannel(path, id, settings.instance)
const instanceOrigin = settings.instance
// problem with the channel? fetchChannel has collected the necessary information for us.
// we can render a skeleton page, display the message, and provide the option to unsubscribe.
if (data.error) {
const statusCode = data.missing ? 410 : 500
const subscribed = user.isSubscribed(id)
return render(statusCode, "pug/channel-error.pug", {req, settings, data, subscribed})
}
// normalise info
if (!data.second__subCountText && data.subCount)
data.second__subCountText = converters.subscriberCountToText(data.subCount)
if (!data.second__totalViewText && data.totalViews)
data.second__totalViewText = converters.viewCountToText(data.totalViews)
// subpages...
if (subpage) { // Get all videos
const fetchURL = `${instanceOrigin}/api/v1/channels/${id}/${subpage}${url.href.split(`${id}/${subpage}`)[1]}`
let q = await request(fetchURL.toString())
if (!q.ok) {
// Has error
if (q.result.message) {
// TODO
if (q.result instanceof fetch.FetchError)
return render(500, "pug/errors/fetch-error.pug", { instanceOrigin, error: q.result })
else
return render(500, "pug/errors/message-error.pug", { instanceOrigin, error: q.result })
// Just didn't return json
} else {
// TODO
const out = await q.result.text()
// html
if (out.indexOf("<head>") != -1)
return render(q.result.status, `pug/errors/substitute-html-error.pug`, { content: out })
// just text
else
return render(q.result.status, "pugs/errors/message-error.pug", { instanceOrigin, error: new Error(out) })
}
}
// Retrieve data
if (subpage == "videos" || subpage == "shorts" || subpage == "streams" || subpage == "playlists") {
data.latestVideos = q.result.videos || q.result.playlists || []
data.continuation = q.result.continuation
}
}
// apply watched status + dearrow data
let toasts = []
const watchedVideos = user.getWatchedVideos()
if (data.latestVideos) {
for (const video of data.latestVideos) {
converters.normaliseVideoInfo(video)
video.watched = watchedVideos.includes(video.videoId)
}
// Apply DeArrow data
if (settings.dearrow > 0) {
if (settings.dearrow_preload == 1) {
const dearrowOut = await dearrow.applyToAllDeArrow(data.latestVideos)
if (Object.keys(dearrowOut.errors).length > 0)
for (const deE of Object.keys(dearrowOut.errors))
toasts.push({ color: "red", icon: "x", text: dearrowOut.errors[deE] })
} else
dearrow.getAllDeArrowNoBlock(data.latestVideos)
}
}
const subscribed = user.isSubscribed(data.authorId)
return render(200, "pug/channel.pug", {req, settings, data, subscribed, subpage, url, toasts})
}
}
]