mirror of
https://github.com/seerr-team/seerr.git
synced 2026-04-17 22:07:59 -04:00
chore(deps): upgrade dependencies
This commit is contained in:
149
package.json
149
package.json
@@ -34,96 +34,92 @@
|
||||
},
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"@dr.pogodin/csurf": "^1.16.6",
|
||||
"@dr.pogodin/csurf": "^1.16.9",
|
||||
"@fontsource-variable/inter": "^5.2.8",
|
||||
"@formatjs/intl": "^4.1.4",
|
||||
"@formatjs/intl-displaynames": "6.8.13",
|
||||
"@formatjs/intl-locale": "3.1.1",
|
||||
"@formatjs/intl-pluralrules": "5.4.6",
|
||||
"@formatjs/intl-utils": "3.8.4",
|
||||
"@headlessui/react": "1.7.12",
|
||||
"@formatjs/intl-displaynames": "7.3.2",
|
||||
"@formatjs/intl-locale": "5.3.2",
|
||||
"@formatjs/intl-pluralrules": "6.3.2",
|
||||
"@headlessui/react": "1.7.19",
|
||||
"@heroicons/react": "2.2.0",
|
||||
"@seerr-team/react-tailwindcss-datepicker": "^1.3.4",
|
||||
"@supercharge/request-ip": "1.2.0",
|
||||
"@svgr/webpack": "8.1.0",
|
||||
"@tanem/react-nprogress": "5.0.56",
|
||||
"@types/ua-parser-js": "^0.7.36",
|
||||
"@types/wink-jaro-distance": "^2.0.2",
|
||||
"ace-builds": "1.43.4",
|
||||
"@tanem/react-nprogress": "6.0.3",
|
||||
"ace-builds": "1.43.6",
|
||||
"axios": "1.15.0",
|
||||
"axios-rate-limit": "1.9.0",
|
||||
"bcrypt": "6.0.0",
|
||||
"bowser": "2.13.1",
|
||||
"connect-typeorm": "1.1.4",
|
||||
"bowser": "2.14.1",
|
||||
"connect-typeorm": "2.0.0",
|
||||
"cookie-parser": "1.4.7",
|
||||
"copy-to-clipboard": "3.3.3",
|
||||
"country-flag-icons": "1.6.4",
|
||||
"cronstrue": "2.23.0",
|
||||
"date-fns": "2.29.3",
|
||||
"dns-caching": "^0.2.7",
|
||||
"email-templates": "12.0.3",
|
||||
"country-flag-icons": "1.6.16",
|
||||
"cronstrue": "3.14.0",
|
||||
"date-fns": "4.1.0",
|
||||
"dns-caching": "^0.2.9",
|
||||
"email-templates": "13.0.1",
|
||||
"express": "4.21.2",
|
||||
"express-openapi-validator": "4.13.8",
|
||||
"express-rate-limit": "6.7.0",
|
||||
"express-session": "1.18.2",
|
||||
"express-openapi-validator": "5.6.2",
|
||||
"express-rate-limit": "8.3.2",
|
||||
"express-session": "1.19.0",
|
||||
"formik": "^2.4.9",
|
||||
"gravatar-url": "3.1.0",
|
||||
"gravatar-url": "4.0.1",
|
||||
"http-proxy-agent": "^7.0.2",
|
||||
"https-proxy-agent": "^7.0.6",
|
||||
"lodash": "4.17.23",
|
||||
"mime": "3",
|
||||
"js-yaml": "^4.1.1",
|
||||
"lodash": "4.18.1",
|
||||
"mime": "^4.1.0",
|
||||
"nanoid": "^5.1.7",
|
||||
"next": "^14.2.35",
|
||||
"node-cache": "5.1.2",
|
||||
"node-gyp": "9.3.1",
|
||||
"node-gyp": "12.2.0",
|
||||
"node-schedule": "2.1.1",
|
||||
"nodemailer": "7.0.12",
|
||||
"nodemailer": "8.0.5",
|
||||
"openpgp": "6.3.0",
|
||||
"pg": "8.17.2",
|
||||
"pug": "3.0.3",
|
||||
"pg": "8.20.0",
|
||||
"pug": "3.0.4",
|
||||
"react": "^18.3.1",
|
||||
"react-ace": "10.1.0",
|
||||
"react-animate-height": "2.1.2",
|
||||
"react-aria": "3.44.0",
|
||||
"react-ace": "14.0.1",
|
||||
"react-animate-height": "3.2.3",
|
||||
"react-aria": "3.47.0",
|
||||
"react-dom": "^18.3.1",
|
||||
"react-intersection-observer": "9.4.3",
|
||||
"react-intl": "^6.6.8",
|
||||
"react-markdown": "8.0.5",
|
||||
"react-intersection-observer": "10.0.3",
|
||||
"react-intl": "^7.1.14",
|
||||
"react-markdown": "10.1.0",
|
||||
"react-popper-tooltip": "4.4.2",
|
||||
"react-select": "5.10.2",
|
||||
"react-spring": "9.7.1",
|
||||
"react-spring": "10.0.3",
|
||||
"react-toast-notifications": "2.5.1",
|
||||
"react-transition-group": "^4.4.5",
|
||||
"react-truncate-markup": "5.1.2",
|
||||
"react-use-clipboard": "1.0.9",
|
||||
"reflect-metadata": "0.1.13",
|
||||
"secure-random-password": "0.2.3",
|
||||
"semver": "7.7.3",
|
||||
"sharp": "^0.33.4",
|
||||
"sqlite3": "5.1.7",
|
||||
"swagger-ui-express": "4.6.2",
|
||||
"swr": "2.3.8",
|
||||
"tailwind-merge": "^2.6.0",
|
||||
"semver": "7.7.4",
|
||||
"sharp": "^0.34.5",
|
||||
"sqlite3": "^6.0.1",
|
||||
"swagger-ui-express": "5.0.1",
|
||||
"swr": "2.4.1",
|
||||
"tailwind-merge": "^2.6.1",
|
||||
"typeorm": "0.3.28",
|
||||
"ua-parser-js": "^1.0.35",
|
||||
"undici": "^7.18.2",
|
||||
"validator": "^13.15.23",
|
||||
"ua-parser-js": "^2.0.9",
|
||||
"undici": "^8.1.0",
|
||||
"validator": "^13.15.35",
|
||||
"web-push": "3.6.7",
|
||||
"wink-jaro-distance": "^2.0.0",
|
||||
"winston": "3.19.0",
|
||||
"winston-daily-rotate-file": "4.7.1",
|
||||
"xml2js": "0.5.0",
|
||||
"yamljs": "0.3.0",
|
||||
"yup": "0.32.11",
|
||||
"winston-daily-rotate-file": "5.0.0",
|
||||
"xml2js": "0.6.2",
|
||||
"yup": "1.7.1",
|
||||
"zod": "4.3.6"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@commitlint/cli": "17.4.4",
|
||||
"@commitlint/config-conventional": "17.4.4",
|
||||
"@commitlint/cli": "20.5.0",
|
||||
"@commitlint/config-conventional": "20.5.0",
|
||||
"@eslint/js": "9.39.3",
|
||||
"@next/eslint-plugin-next": "^16.1.6",
|
||||
"@next/eslint-plugin-next": "^16.2.3",
|
||||
"@tailwindcss/aspect-ratio": "^0.4.2",
|
||||
"@tailwindcss/forms": "^0.5.10",
|
||||
"@tailwindcss/typography": "^0.5.16",
|
||||
"@tailwindcss/forms": "^0.5.11",
|
||||
"@tailwindcss/typography": "^0.5.19",
|
||||
"@types/bcrypt": "6.0.0",
|
||||
"@types/cookie-parser": "1.4.10",
|
||||
"@types/country-flag-icons": "1.2.2",
|
||||
@@ -132,55 +128,55 @@
|
||||
"@types/eslint-plugin-jsx-a11y": "^6.10.1",
|
||||
"@types/express": "4.17.17",
|
||||
"@types/express-session": "1.18.2",
|
||||
"@types/lodash": "4.17.21",
|
||||
"@types/mime": "3",
|
||||
"@types/js-yaml": "^4.0.9",
|
||||
"@types/lodash": "4.17.24",
|
||||
"@types/mime": "^3.0.4",
|
||||
"@types/node": "22.10.5",
|
||||
"@types/node-schedule": "2.1.8",
|
||||
"@types/nodemailer": "7",
|
||||
"@types/react": "^18.3.3",
|
||||
"@types/react-dom": "^18.3.0",
|
||||
"@types/nodemailer": "^8.0.0",
|
||||
"@types/react": "^18.3.28",
|
||||
"@types/react-dom": "^18.3.7",
|
||||
"@types/react-transition-group": "4.4.12",
|
||||
"@types/secure-random-password": "0.2.1",
|
||||
"@types/semver": "7.7.1",
|
||||
"@types/supertest": "^6.0.3",
|
||||
"@types/supertest": "^7.2.0",
|
||||
"@types/swagger-ui-express": "4.1.8",
|
||||
"@types/ua-parser-js": "^0.7.36",
|
||||
"@types/validator": "^13.15.10",
|
||||
"@types/web-push": "3.6.4",
|
||||
"@types/wink-jaro-distance": "^2.0.2",
|
||||
"@types/xml2js": "0.4.14",
|
||||
"@types/yamljs": "0.2.31",
|
||||
"@types/yup": "0.29.14",
|
||||
"autoprefixer": "^10.4.23",
|
||||
"baseline-browser-mapping": "^2.8.32",
|
||||
"autoprefixer": "^10.5.0",
|
||||
"baseline-browser-mapping": "^2.10.18",
|
||||
"commander": "^14.0.3",
|
||||
"commitizen": "4.3.1",
|
||||
"copyfiles": "2.4.1",
|
||||
"cy-mobile-commands": "0.3.0",
|
||||
"cypress": "14.5.4",
|
||||
"cypress": "15.13.1",
|
||||
"cz-conventional-changelog": "3.3.0",
|
||||
"eslint": "9.39.3",
|
||||
"eslint-config-prettier": "10.1.8",
|
||||
"eslint-plugin-formatjs": "6.2.0",
|
||||
"eslint-plugin-formatjs": "6.4.5",
|
||||
"eslint-plugin-jsx-a11y": "6.10.2",
|
||||
"eslint-plugin-no-relative-import-paths": "1.6.1",
|
||||
"eslint-plugin-prettier": "4.2.1",
|
||||
"eslint-plugin-react": "7.37.5",
|
||||
"eslint-plugin-react-hooks": "7.0.1",
|
||||
"globals": "^17.3.0",
|
||||
"globals": "^17.5.0",
|
||||
"husky": "8.0.3",
|
||||
"jiti": "^2.6.1",
|
||||
"lint-staged": "13.1.2",
|
||||
"nodemon": "3.1.11",
|
||||
"postcss": "^8.5.6",
|
||||
"prettier": "3.8.1",
|
||||
"lint-staged": "16.4.0",
|
||||
"nodemon": "3.1.14",
|
||||
"postcss": "^8.5.9",
|
||||
"prettier": "3.8.2",
|
||||
"prettier-plugin-organize-imports": "4.3.0",
|
||||
"prettier-plugin-tailwindcss": "0.6.14",
|
||||
"prettier-plugin-tailwindcss": "0.7.2",
|
||||
"supertest": "^7.2.2",
|
||||
"tailwindcss": "3.4.19",
|
||||
"ts-node": "10.9.2",
|
||||
"tsc-alias": "1.8.16",
|
||||
"tsconfig-paths": "4.2.0",
|
||||
"typescript": "5.4.5",
|
||||
"typescript-eslint": "^8.56.1"
|
||||
"typescript-eslint": "^8.58.2"
|
||||
},
|
||||
"engines": {
|
||||
"node": "^22.19.0",
|
||||
@@ -217,5 +213,8 @@
|
||||
"sqlite3>node-gyp": "8.4.1",
|
||||
"@types/express-session": "1.18.2"
|
||||
}
|
||||
},
|
||||
"scarfSettings": {
|
||||
"enabled": false
|
||||
}
|
||||
}
|
||||
}
|
||||
6999
pnpm-lock.yaml
generated
6999
pnpm-lock.yaml
generated
File diff suppressed because it is too large
Load Diff
@@ -12,8 +12,8 @@ import { DbAwareColumn, resolveDbType } from '@server/utils/DbColumnHelper';
|
||||
import { AfterDate } from '@server/utils/dateHelpers';
|
||||
import bcrypt from 'bcrypt';
|
||||
import { randomUUID } from 'crypto';
|
||||
import { nanoid } from 'nanoid';
|
||||
import path from 'path';
|
||||
import { default as generatePassword } from 'secure-random-password';
|
||||
import {
|
||||
AfterLoad,
|
||||
Column,
|
||||
@@ -193,7 +193,7 @@ export class User {
|
||||
}
|
||||
|
||||
public async generatePassword(): Promise<void> {
|
||||
const password = generatePassword.randomPassword({ length: 16 });
|
||||
const password = nanoid(16);
|
||||
await this.setPassword(password);
|
||||
|
||||
const { applicationTitle, applicationUrl } = getSettings().main;
|
||||
|
||||
@@ -38,12 +38,13 @@ import express from 'express';
|
||||
import * as OpenApiValidator from 'express-openapi-validator';
|
||||
import type { Store } from 'express-session';
|
||||
import session from 'express-session';
|
||||
import fs from 'fs/promises';
|
||||
import http from 'http';
|
||||
import https from 'https';
|
||||
import yaml from 'js-yaml';
|
||||
import next from 'next';
|
||||
import path from 'path';
|
||||
import swaggerUi from 'swagger-ui-express';
|
||||
import YAML from 'yamljs';
|
||||
|
||||
const API_SPEC_PATH = path.join(__dirname, '../seerr-api.yml');
|
||||
|
||||
@@ -221,7 +222,8 @@ app
|
||||
}).connect(sessionRespository) as Store,
|
||||
})
|
||||
);
|
||||
const apiDocs = YAML.load(API_SPEC_PATH);
|
||||
const apiSpecContent = await fs.readFile(API_SPEC_PATH, 'utf-8');
|
||||
const apiDocs = yaml.load(apiSpecContent) as Record<string, unknown>;
|
||||
server.use('/api-docs', swaggerUi.serve, swaggerUi.setup(apiDocs));
|
||||
server.use(
|
||||
OpenApiValidator.middleware({
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
/* eslint-disable no-console */
|
||||
import path from 'path';
|
||||
import * as winston from 'winston';
|
||||
import 'winston-daily-rotate-file';
|
||||
@@ -14,6 +15,42 @@ const hformat = winston.format.printf(
|
||||
}
|
||||
);
|
||||
|
||||
const seerrFileTransport = new winston.transports.DailyRotateFile({
|
||||
filename: process.env.CONFIG_DIRECTORY
|
||||
? `${process.env.CONFIG_DIRECTORY}/logs/seerr-%DATE%.log`
|
||||
: path.join(__dirname, '../config/logs/seerr-%DATE%.log'),
|
||||
datePattern: 'YYYY-MM-DD',
|
||||
zippedArchive: true,
|
||||
maxSize: '20m',
|
||||
maxFiles: '7d',
|
||||
createSymlink: true,
|
||||
symlinkName: 'seerr.log',
|
||||
});
|
||||
const machineLogFileTransport = new winston.transports.DailyRotateFile({
|
||||
filename: process.env.CONFIG_DIRECTORY
|
||||
? `${process.env.CONFIG_DIRECTORY}/logs/.machinelogs-%DATE%.json`
|
||||
: path.join(__dirname, '../config/logs/.machinelogs-%DATE%.json'),
|
||||
datePattern: 'YYYY-MM-DD',
|
||||
zippedArchive: true,
|
||||
maxSize: '20m',
|
||||
maxFiles: '1d',
|
||||
createSymlink: true,
|
||||
symlinkName: '.machinelogs.json',
|
||||
format: winston.format.combine(
|
||||
winston.format.splat(),
|
||||
winston.format.timestamp(),
|
||||
winston.format.json()
|
||||
),
|
||||
});
|
||||
|
||||
seerrFileTransport.on('error', (err) => {
|
||||
console.error('Error in seerr file transport:', err);
|
||||
});
|
||||
|
||||
machineLogFileTransport.on('error', (err) => {
|
||||
console.error('Error in machine log file transport:', err);
|
||||
});
|
||||
|
||||
const logger = winston.createLogger({
|
||||
level: process.env.LOG_LEVEL?.toLowerCase() || 'debug',
|
||||
format: winston.format.combine(
|
||||
@@ -30,33 +67,8 @@ const logger = winston.createLogger({
|
||||
hformat
|
||||
),
|
||||
}),
|
||||
new winston.transports.DailyRotateFile({
|
||||
filename: process.env.CONFIG_DIRECTORY
|
||||
? `${process.env.CONFIG_DIRECTORY}/logs/seerr-%DATE%.log`
|
||||
: path.join(__dirname, '../config/logs/seerr-%DATE%.log'),
|
||||
datePattern: 'YYYY-MM-DD',
|
||||
zippedArchive: true,
|
||||
maxSize: '20m',
|
||||
maxFiles: '7d',
|
||||
createSymlink: true,
|
||||
symlinkName: 'seerr.log',
|
||||
}),
|
||||
new winston.transports.DailyRotateFile({
|
||||
filename: process.env.CONFIG_DIRECTORY
|
||||
? `${process.env.CONFIG_DIRECTORY}/logs/.machinelogs-%DATE%.json`
|
||||
: path.join(__dirname, '../config/logs/.machinelogs-%DATE%.json'),
|
||||
datePattern: 'YYYY-MM-DD',
|
||||
zippedArchive: true,
|
||||
maxSize: '20m',
|
||||
maxFiles: '1d',
|
||||
createSymlink: true,
|
||||
symlinkName: '.machinelogs.json',
|
||||
format: winston.format.combine(
|
||||
winston.format.splat(),
|
||||
winston.format.timestamp(),
|
||||
winston.format.json()
|
||||
),
|
||||
}),
|
||||
seerrFileTransport,
|
||||
machineLogFileTransport,
|
||||
],
|
||||
});
|
||||
|
||||
|
||||
@@ -55,10 +55,11 @@ const NotificationsDiscord = () => {
|
||||
webhookUrl: Yup.string()
|
||||
.when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationUrl)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationUrl)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.url(intl.formatMessage(messages.validationUrl)),
|
||||
webhookRoleId: Yup.string()
|
||||
|
||||
@@ -73,10 +73,11 @@ const NotificationsEmail = () => {
|
||||
emailFrom: Yup.string()
|
||||
.when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationEmail)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationEmail)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.test(
|
||||
'email',
|
||||
@@ -85,25 +86,28 @@ const NotificationsEmail = () => {
|
||||
),
|
||||
smtpHost: Yup.string().when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationSmtpHostRequired)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationSmtpHostRequired)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
smtpPort: Yup.number().when('enabled', {
|
||||
is: true,
|
||||
then: Yup.number()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationSmtpPortRequired)),
|
||||
otherwise: Yup.number().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationSmtpPortRequired)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
pgpPrivateKey: Yup.string()
|
||||
.when('pgpPassword', {
|
||||
is: (value: unknown) => !!value,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationPgpPrivateKey)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationPgpPrivateKey)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.matches(
|
||||
/-----BEGIN PGP PRIVATE KEY BLOCK-----.+-----END PGP PRIVATE KEY BLOCK-----/s,
|
||||
@@ -111,10 +115,11 @@ const NotificationsEmail = () => {
|
||||
),
|
||||
pgpPassword: Yup.string().when('pgpPrivateKey', {
|
||||
is: (value: unknown) => !!value,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationPgpPassword)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationPgpPassword)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
},
|
||||
[['pgpPrivateKey', 'pgpPassword']]
|
||||
|
||||
@@ -48,10 +48,11 @@ const NotificationsGotify = () => {
|
||||
url: Yup.string()
|
||||
.when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationUrlRequired)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationUrlRequired)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.test(
|
||||
'valid-url',
|
||||
@@ -65,19 +66,21 @@ const NotificationsGotify = () => {
|
||||
),
|
||||
token: Yup.string().when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationTokenRequired)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationTokenRequired)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
priority: Yup.string().when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.min(0)
|
||||
.max(9)
|
||||
.required(intl.formatMessage(messages.validationPriorityRequired)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.min(0)
|
||||
.max(9)
|
||||
.required(intl.formatMessage(messages.validationPriorityRequired)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
});
|
||||
|
||||
|
||||
@@ -55,10 +55,11 @@ const NotificationsNtfy = () => {
|
||||
url: Yup.string()
|
||||
.when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationNtfyUrl)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationNtfyUrl)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.test(
|
||||
'valid-url',
|
||||
@@ -68,19 +69,22 @@ const NotificationsNtfy = () => {
|
||||
topic: Yup.string()
|
||||
.when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationNtfyUrl)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationNtfyTopic)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.defined(intl.formatMessage(messages.validationNtfyTopic)),
|
||||
priority: Yup.number().when('enabled', {
|
||||
is: true,
|
||||
then: Yup.number()
|
||||
.min(1)
|
||||
.max(5)
|
||||
.required(intl.formatMessage(messages.validationPriorityRequired)),
|
||||
otherwise: Yup.number().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.min(1)
|
||||
.max(5)
|
||||
.required(intl.formatMessage(messages.validationPriorityRequired)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
});
|
||||
|
||||
|
||||
@@ -46,10 +46,11 @@ const NotificationsPushbullet = () => {
|
||||
const NotificationsPushbulletSchema = Yup.object().shape({
|
||||
accessToken: Yup.string().when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationAccessTokenRequired)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationAccessTokenRequired)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
});
|
||||
|
||||
|
||||
@@ -61,10 +61,13 @@ const NotificationsPushover = () => {
|
||||
accessToken: Yup.string()
|
||||
.when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationAccessTokenRequired)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(
|
||||
intl.formatMessage(messages.validationAccessTokenRequired)
|
||||
),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.matches(
|
||||
/^[a-z\d]{30}$/i,
|
||||
@@ -73,10 +76,11 @@ const NotificationsPushover = () => {
|
||||
userToken: Yup.string()
|
||||
.when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationUserTokenRequired)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationUserTokenRequired)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.matches(
|
||||
/^[a-z\d]{30}$/i,
|
||||
|
||||
@@ -45,10 +45,11 @@ const NotificationsSlack = () => {
|
||||
webhookUrl: Yup.string()
|
||||
.when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationWebhookUrl)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationWebhookUrl)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.url(intl.formatMessage(messages.validationWebhookUrl)),
|
||||
});
|
||||
|
||||
@@ -53,31 +53,28 @@ const NotificationsTelegram = () => {
|
||||
const NotificationsTelegramSchema = Yup.object().shape({
|
||||
botAPI: Yup.string().when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationBotAPIRequired)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationBotAPIRequired)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
chatId: Yup.string()
|
||||
.when(['enabled', 'types'], {
|
||||
is: (enabled: boolean, types: number) => enabled && !!types,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationChatIdRequired)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationChatIdRequired)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.matches(
|
||||
/^-?\d+$/,
|
||||
intl.formatMessage(messages.validationChatIdRequired)
|
||||
),
|
||||
messageThreadId: Yup.string()
|
||||
.when(['types'], {
|
||||
is: (enabled: boolean, types: number) => enabled && !!types,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationMessageThreadId)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
})
|
||||
.transform((v) => v || null)
|
||||
.nullable()
|
||||
.matches(/^\d+$/, intl.formatMessage(messages.validationMessageThreadId)),
|
||||
});
|
||||
|
||||
|
||||
@@ -127,10 +127,11 @@ const NotificationsWebhook = () => {
|
||||
webhookUrl: Yup.string()
|
||||
.when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationWebhookUrl)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationWebhookUrl)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.test(
|
||||
'valid-url',
|
||||
@@ -183,10 +184,13 @@ const NotificationsWebhook = () => {
|
||||
jsonPayload: Yup.string()
|
||||
.when('enabled', {
|
||||
is: true,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationJsonPayloadRequired)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(
|
||||
intl.formatMessage(messages.validationJsonPayloadRequired)
|
||||
),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.test(
|
||||
'validate-json',
|
||||
|
||||
@@ -116,13 +116,15 @@ const SettingsJellyfin: React.FC<SettingsJellyfinProps> = ({
|
||||
.required(intl.formatMessage(messages.validationHostnameRequired)),
|
||||
port: Yup.number().when(['hostname'], {
|
||||
is: (value: unknown) => !!value,
|
||||
then: Yup.number()
|
||||
.typeError(intl.formatMessage(messages.validationPortRequired))
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationPortRequired)),
|
||||
otherwise: Yup.number()
|
||||
.typeError(intl.formatMessage(messages.validationPortRequired))
|
||||
.nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.typeError(intl.formatMessage(messages.validationPortRequired))
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationPortRequired)),
|
||||
otherwise: (schema) =>
|
||||
schema
|
||||
.typeError(intl.formatMessage(messages.validationPortRequired))
|
||||
.nullable(),
|
||||
}),
|
||||
urlBase: Yup.string()
|
||||
.test(
|
||||
|
||||
@@ -74,26 +74,32 @@ const SettingsNetwork = () => {
|
||||
const NetworkSettingsSchema = Yup.object().shape({
|
||||
dnsCacheForceMinTtl: Yup.number().when('dnsCacheEnabled', {
|
||||
is: true,
|
||||
then: Yup.number()
|
||||
.typeError(intl.formatMessage(messages.validationDnsCacheMinTtl))
|
||||
.required(intl.formatMessage(messages.validationDnsCacheMinTtl))
|
||||
.min(0),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.typeError(intl.formatMessage(messages.validationDnsCacheMinTtl))
|
||||
.required(intl.formatMessage(messages.validationDnsCacheMinTtl))
|
||||
.min(0),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
dnsCacheForceMaxTtl: Yup.number().when('dnsCacheEnabled', {
|
||||
is: true,
|
||||
then: Yup.number()
|
||||
.typeError(intl.formatMessage(messages.validationDnsCacheMaxTtl))
|
||||
.required(intl.formatMessage(messages.validationDnsCacheMaxTtl))
|
||||
.min(-1),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.typeError(intl.formatMessage(messages.validationDnsCacheMaxTtl))
|
||||
.required(intl.formatMessage(messages.validationDnsCacheMaxTtl))
|
||||
.min(-1),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
proxyPort: Yup.number().when('proxyEnabled', {
|
||||
is: (proxyEnabled: boolean) => proxyEnabled,
|
||||
then: Yup.number()
|
||||
.typeError(intl.formatMessage(messages.validationProxyPort))
|
||||
.integer(intl.formatMessage(messages.validationProxyPort))
|
||||
.min(1, intl.formatMessage(messages.validationProxyPort))
|
||||
.max(65535, intl.formatMessage(messages.validationProxyPort))
|
||||
.required(intl.formatMessage(messages.validationProxyPort)),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.typeError(intl.formatMessage(messages.validationProxyPort))
|
||||
.integer(intl.formatMessage(messages.validationProxyPort))
|
||||
.min(1, intl.formatMessage(messages.validationProxyPort))
|
||||
.max(65535, intl.formatMessage(messages.validationProxyPort))
|
||||
.required(intl.formatMessage(messages.validationProxyPort)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
apiRequestTimeout: Yup.number()
|
||||
.typeError(intl.formatMessage(messages.validationApiRequestTimeout))
|
||||
|
||||
@@ -150,10 +150,13 @@ const SettingsPlex = ({ onComplete }: SettingsPlexProps) => {
|
||||
tautulliHostname: Yup.string()
|
||||
.when(['tautulliPort', 'tautulliApiKey'], {
|
||||
is: (value: unknown) => !!value,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationHostnameRequired)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(
|
||||
intl.formatMessage(messages.validationHostnameRequired)
|
||||
),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.matches(
|
||||
/^(([a-z]|\d|_|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*)?([a-z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])$/i,
|
||||
@@ -161,13 +164,15 @@ const SettingsPlex = ({ onComplete }: SettingsPlexProps) => {
|
||||
),
|
||||
tautulliPort: Yup.number().when(['tautulliHostname', 'tautulliApiKey'], {
|
||||
is: (value: unknown) => !!value,
|
||||
then: Yup.number()
|
||||
.typeError(intl.formatMessage(messages.validationPortRequired))
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationPortRequired)),
|
||||
otherwise: Yup.number()
|
||||
.typeError(intl.formatMessage(messages.validationPortRequired))
|
||||
.nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.typeError(intl.formatMessage(messages.validationPortRequired))
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationPortRequired)),
|
||||
otherwise: (schema) =>
|
||||
schema
|
||||
.typeError(intl.formatMessage(messages.validationPortRequired))
|
||||
.nullable(),
|
||||
}),
|
||||
tautulliUrlBase: Yup.string()
|
||||
.test(
|
||||
@@ -182,10 +187,11 @@ const SettingsPlex = ({ onComplete }: SettingsPlexProps) => {
|
||||
),
|
||||
tautulliApiKey: Yup.string().when(['tautulliHostname', 'tautulliPort'], {
|
||||
is: (value: unknown) => !!value,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationApiKey)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationApiKey)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
tautulliExternalUrl: Yup.string()
|
||||
.test(
|
||||
|
||||
@@ -63,9 +63,9 @@ const SettingsUsers = () => {
|
||||
.test({
|
||||
name: 'atLeastOneAuth',
|
||||
test: function (values) {
|
||||
const isValid = ['localLogin', 'mediaServerLogin'].some(
|
||||
(field) => !!values[field]
|
||||
);
|
||||
const isValid = (
|
||||
['localLogin', 'mediaServerLogin'] as (keyof typeof values)[]
|
||||
).some((field) => !!values[field]);
|
||||
|
||||
if (isValid) return true;
|
||||
return this.createError({
|
||||
|
||||
@@ -44,10 +44,11 @@ const UserNotificationsDiscord = () => {
|
||||
discordId: Yup.string()
|
||||
.when('types', {
|
||||
is: (types: number) => !!types,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationDiscordId)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationDiscordId)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.matches(/^\d{17,19}$/, intl.formatMessage(messages.validationDiscordId)),
|
||||
});
|
||||
|
||||
@@ -44,10 +44,13 @@ const UserPushbulletSettings = () => {
|
||||
const UserNotificationsPushbulletSchema = Yup.object().shape({
|
||||
pushbulletAccessToken: Yup.string().when('types', {
|
||||
is: (types: number) => !!types,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationPushbulletAccessToken)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(
|
||||
intl.formatMessage(messages.validationPushbulletAccessToken)
|
||||
),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
}),
|
||||
});
|
||||
|
||||
|
||||
@@ -57,12 +57,13 @@ const UserPushoverSettings = () => {
|
||||
pushoverApplicationToken: Yup.string()
|
||||
.when('types', {
|
||||
is: (types: number) => !!types,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(
|
||||
intl.formatMessage(messages.validationPushoverApplicationToken)
|
||||
),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(
|
||||
intl.formatMessage(messages.validationPushoverApplicationToken)
|
||||
),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.matches(
|
||||
/^[a-z\d]{30}$/i,
|
||||
@@ -71,10 +72,11 @@ const UserPushoverSettings = () => {
|
||||
pushoverUserKey: Yup.string()
|
||||
.when('types', {
|
||||
is: (types: number) => !!types,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationPushoverUserKey)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationPushoverUserKey)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.matches(
|
||||
/^[a-z\d]{30}$/i,
|
||||
|
||||
@@ -50,25 +50,19 @@ const UserTelegramSettings = () => {
|
||||
telegramChatId: Yup.string()
|
||||
.when('types', {
|
||||
is: (types: number) => !!types,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationTelegramChatId)),
|
||||
otherwise: Yup.string().nullable(),
|
||||
then: (schema) =>
|
||||
schema
|
||||
.nullable()
|
||||
.required(intl.formatMessage(messages.validationTelegramChatId)),
|
||||
otherwise: (schema) => schema.nullable(),
|
||||
})
|
||||
.matches(
|
||||
/^-?\d+$/,
|
||||
intl.formatMessage(messages.validationTelegramChatId)
|
||||
),
|
||||
telegramMessageThreadId: Yup.string()
|
||||
.when(['types'], {
|
||||
is: (enabled: boolean, types: number) => enabled && !!types,
|
||||
then: Yup.string()
|
||||
.nullable()
|
||||
.required(
|
||||
intl.formatMessage(messages.validationTelegramMessageThreadId)
|
||||
),
|
||||
otherwise: Yup.string().nullable(),
|
||||
})
|
||||
.transform((v) => v || null)
|
||||
.nullable()
|
||||
.matches(
|
||||
/^\d+$/,
|
||||
intl.formatMessage(messages.validationTelegramMessageThreadId)
|
||||
|
||||
@@ -74,7 +74,7 @@ const UserPasswordChange = () => {
|
||||
confirmPassword: Yup.string()
|
||||
.required(intl.formatMessage(messages.validationConfirmPassword))
|
||||
.oneOf(
|
||||
[Yup.ref('newPassword'), null],
|
||||
[Yup.ref('newPassword'), ''],
|
||||
intl.formatMessage(messages.validationConfirmPasswordSame)
|
||||
),
|
||||
});
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
import { shouldPolyfill as shouldPolyfillDisplayNames } from '@formatjs/intl-displaynames/should-polyfill';
|
||||
import { shouldPolyfill as shouldPolyfillLocale } from '@formatjs/intl-locale/should-polyfill';
|
||||
import { shouldPolyfill as shouldPolyfillPluralrules } from '@formatjs/intl-pluralrules/should-polyfill';
|
||||
import { shouldPolyfill as shouldPolyfillDisplayNames } from '@formatjs/intl-displaynames/should-polyfill.js';
|
||||
import { shouldPolyfill as shouldPolyfillLocale } from '@formatjs/intl-locale/should-polyfill.js';
|
||||
import { shouldPolyfill as shouldPolyfillPluralrules } from '@formatjs/intl-pluralrules/should-polyfill.js';
|
||||
|
||||
const polyfillLocale = async () => {
|
||||
if (shouldPolyfillLocale()) {
|
||||
await import('@formatjs/intl-locale/polyfill');
|
||||
await import('@formatjs/intl-locale/polyfill.js');
|
||||
}
|
||||
};
|
||||
|
||||
@@ -15,8 +15,10 @@ const polyfillPluralRules = async (locale: string) => {
|
||||
return;
|
||||
}
|
||||
// Load the polyfill 1st BEFORE loading data
|
||||
await import('@formatjs/intl-pluralrules/polyfill-force');
|
||||
await import(`@formatjs/intl-pluralrules/locale-data/${unsupportedLocale}`);
|
||||
await import('@formatjs/intl-pluralrules/polyfill-force.js');
|
||||
await import(
|
||||
`@formatjs/intl-pluralrules/locale-data/${unsupportedLocale}.js`
|
||||
);
|
||||
};
|
||||
|
||||
const polyfillDisplayNames = async (locale: string) => {
|
||||
@@ -26,8 +28,10 @@ const polyfillDisplayNames = async (locale: string) => {
|
||||
return;
|
||||
}
|
||||
// Load the polyfill 1st BEFORE loading data
|
||||
await import('@formatjs/intl-displaynames/polyfill-force');
|
||||
await import(`@formatjs/intl-displaynames/locale-data/${unsupportedLocale}`);
|
||||
await import('@formatjs/intl-displaynames/polyfill-force.js');
|
||||
await import(
|
||||
`@formatjs/intl-displaynames/locale-data/${unsupportedLocale}.js`
|
||||
);
|
||||
};
|
||||
|
||||
export const polyfillIntl = async (locale: string) => {
|
||||
|
||||
Reference in New Issue
Block a user