feat: add media requests widget (#774)

Co-authored-by: SeDemal <Tagaishi@hotmail.ch>
Co-authored-by: SeDemal <demal.sebastien@bluewin.ch>
Co-authored-by: Meier Lukas <meierschlumpf@gmail.com>
This commit is contained in:
Manuel
2024-08-24 15:23:16 +02:00
committed by GitHub
parent 7ec4adcb24
commit acbb834889
30 changed files with 1106 additions and 29 deletions

View File

@@ -126,7 +126,7 @@ export const createManyIntegrationMiddleware = <TKind extends IntegrationKind>(
if (offset !== 0) {
throw new TRPCError({
code: "NOT_FOUND",
message: `${offset} of the specified integrations not found or not of kinds ${kinds.join(",")}`,
message: `${offset} of the specified integrations not found or not of kinds ${kinds.join(",")}: ([${input.integrationIds.join(",")}] compared to [${dbIntegrations.join(",")}])`,
});
}
@@ -205,7 +205,7 @@ export const createManyIntegrationOfOneItemMiddleware = <TKind extends Integrati
if (dbIntegrationWithItem.length === 0) {
throw new TRPCError({
code: "NOT_FOUND",
message: "Integration for item was not found",
message: "Integrations for item were not found",
});
}

View File

@@ -48,6 +48,7 @@ export const testConnectionAsync = async (
return secrets.find((secret) => secret.source === "form") ?? secrets[0]!;
});
// @ts-expect-error - For now we expect an error here as not all integerations have been implemented
const integrationInstance = integrationCreatorByKind(integration.kind, {
id: integration.id,
name: integration.name,

View File

@@ -2,6 +2,7 @@ import { createTRPCRouter } from "../../trpc";
import { appRouter } from "./app";
import { calendarRouter } from "./calendar";
import { dnsHoleRouter } from "./dns-hole";
import { mediaRequestsRouter } from "./media-requests";
import { mediaServerRouter } from "./media-server";
import { notebookRouter } from "./notebook";
import { rssFeedRouter } from "./rssFeed";
@@ -16,5 +17,6 @@ export const widgetRouter = createTRPCRouter({
smartHome: smartHomeRouter,
mediaServer: mediaServerRouter,
calendar: calendarRouter,
mediaRequests: mediaRequestsRouter,
rssFeed: rssFeedRouter,
});

View File

@@ -0,0 +1,48 @@
import type { MediaRequestList, MediaRequestStats } from "@homarr/integrations";
import { integrationCreatorByKind } from "@homarr/integrations";
import { createItemAndIntegrationChannel } from "@homarr/redis";
import { z } from "@homarr/validation";
import {
createManyIntegrationOfOneItemMiddleware,
createOneIntegrationMiddleware,
} from "../../middlewares/integration";
import { createTRPCRouter, protectedProcedure, publicProcedure } from "../../trpc";
export const mediaRequestsRouter = createTRPCRouter({
getLatestRequests: publicProcedure
.unstable_concat(createManyIntegrationOfOneItemMiddleware("query", "overseerr", "jellyseerr"))
.query(async ({ input }) => {
return await Promise.all(
input.integrationIds.map(async (integrationId) => {
const channel = createItemAndIntegrationChannel<MediaRequestList>("mediaRequests-requestList", integrationId);
return await channel.getAsync();
}),
);
}),
getStats: publicProcedure
.unstable_concat(createManyIntegrationOfOneItemMiddleware("query", "overseerr", "jellyseerr"))
.query(async ({ input }) => {
return await Promise.all(
input.integrationIds.map(async (integrationId) => {
const channel = createItemAndIntegrationChannel<MediaRequestStats>(
"mediaRequests-requestStats",
integrationId,
);
return await channel.getAsync();
}),
);
}),
answerRequest: protectedProcedure
.unstable_concat(createOneIntegrationMiddleware("interact", "overseerr", "jellyseerr"))
.input(z.object({ requestId: z.number(), answer: z.enum(["approve", "decline"]) }))
.mutation(async ({ ctx, input }) => {
const integration = integrationCreatorByKind(ctx.integration.kind, ctx.integration);
if (input.answer === "approve") {
await integration.approveRequestAsync(input.requestId);
return;
}
await integration.declineRequestAsync(input.requestId);
}),
});