From 1ea8e38372a65c64dc47478b0653fcc4f87c2ad9 Mon Sep 17 00:00:00 2001 From: Jason Fischer Date: Wed, 28 Sep 2022 08:56:43 -0700 Subject: [PATCH] Fix Transmission proxy error with URL and CSRF caching --- src/widgets/transmission/proxy.js | 31 +++++++++++++++++++++++++------ 1 file changed, 25 insertions(+), 6 deletions(-) diff --git a/src/widgets/transmission/proxy.js b/src/widgets/transmission/proxy.js index 4ea10ccee..34bbd480d 100644 --- a/src/widgets/transmission/proxy.js +++ b/src/widgets/transmission/proxy.js @@ -1,21 +1,39 @@ +import cache from "memory-cache"; + import { httpProxy } from "utils/proxy/http"; import { formatApiCall } from "utils/proxy/api-helpers"; import getServiceWidget from "utils/config/service-helpers"; +import createLogger from "utils/logger"; +import widgets from "widgets/widgets"; + +const proxyName = "transmissionProxyHandler"; +const headerCacheKey = `${proxyName}__headers`; +const logger = createLogger(proxyName); export default async function transmissionProxyHandler(req, res) { const { group, service, endpoint } = req.query; if (!group || !service) { + logger.debug("Invalid or missing service '%s' or group '%s'", service, group); return res.status(400).json({ error: "Invalid proxy service type" }); } const widget = await getServiceWidget(group, service); if (!widget) { + logger.debug("Invalid or missing widget for service '%s' in group '%s'", service, group); return res.status(400).json({ error: "Invalid proxy service type" }); } - const url = new URL(formatApiCall(widget.type, { endpoint, ...widget })); + let headers = cache.get(headerCacheKey); + if (!headers) { + headers = { + "content-type": "application/json", + } + cache.put(headerCacheKey, headers); + } + + const url = new URL(formatApiCall(widgets[widget.type].api, { endpoint, ...widget })); const csrfHeaderName = "x-transmission-session-id"; const method = "POST"; @@ -27,10 +45,6 @@ export default async function transmissionProxyHandler(req, res) { }, }); - const headers = { - "content-type": "application/json", - }; - let [status, contentType, data, responseHeaders] = await httpProxy(url, { method, auth, @@ -39,8 +53,9 @@ export default async function transmissionProxyHandler(req, res) { }); if (status === 409) { - // Transmission is rejecting the request, but returning a CSRF token + logger.debug("Transmission is rejecting the request, but returning a CSRF token"); headers[csrfHeaderName] = responseHeaders[csrfHeaderName]; + cache.put(headerCacheKey, headers); // retry the request, now with the CSRF token [status, contentType, data, responseHeaders] = await httpProxy(url, { @@ -51,6 +66,10 @@ export default async function transmissionProxyHandler(req, res) { }); } + if (status !== 200) { + logger.error("Error getting data from Transmission: %d. Data: %s", status, data); + } + if (contentType) res.setHeader("Content-Type", contentType); return res.status(status).send(data); }