Compare commits

..

1 Commits

Author SHA1 Message Date
fallenbagel
b30794dd20 fix(base-scanner): derive media availability from actual season state instead of scanner input
The media-level status was incorrectly set to AVAILABLE when only some seasons were available. The
issue was isAllStandardSeasons/isAll4kSeasons checked the scanner's input array which only contains
seasons found by current scanner (e.g. 1 seaason in jellyfin). If that single season was fully
available, the check passes and the media gets marked AVAILABLE regardless of how many total seasons
existed. And the shouldStayAvailable (and its 4k check) locked the AVAILABLE status once set, as
long as no new seasons were added with a status which prevented the incorrect status from correcting
itself.
2026-02-14 00:46:25 +08:00
153 changed files with 1619 additions and 1742 deletions

View File

@@ -1,7 +1,6 @@
name: 🐛 Bug Report
description: Report a problem
labels: ['awaiting triage']
type: bug
labels: ['bug', 'awaiting triage']
body:
- type: markdown
attributes:

View File

@@ -1,63 +0,0 @@
name: 📚 Documentation
description: Report a docs problem or suggest a docs improvement
title: "[Docs]: "
labels: ["documentation", "awaiting triage"]
type: task
body:
- type: markdown
attributes:
value: |
Thanks for helping improve the docs!
Use this template for documentation issues (typos, unclear steps, missing info, outdated screenshots).
For app bugs or feature ideas, please use the other templates.
- type: input
id: doc-location
attributes:
label: Page / Location
description: Link to the docs page or the file/path (e.g. https://docs.seerr.dev/... or README.md)
placeholder: "https://docs.seerr.dev/..."
validations:
required: true
- type: dropdown
id: doc-area
attributes:
label: Docs Area
options:
- docs site
- migration guide
- README / repo docs
- API / integrations
- other
validations:
required: true
- type: textarea
id: problem
attributes:
label: Whats wrong / missing?
description: Describe the issue in the docs.
validations:
required: true
- type: textarea
id: suggested-fix
attributes:
label: Suggested change
description: If you know what should be changed, describe it (or paste proposed wording).
validations:
required: false
- type: checkboxes
id: search-existing
attributes:
label: Search Existing Issues
description: Have you searched existing issues to see if this has already been reported?
options:
- label: Yes, I have searched existing issues.
required: true
- type: checkboxes
id: terms
attributes:
label: Code of Conduct
description: By submitting this issue, you agree to follow our Code of Conduct.
options:
- label: I agree to follow Seerr's [Code of Conduct](https://github.com/seerr-team/seerr/blob/develop/CODE_OF_CONDUCT.md).
required: true

View File

@@ -1,7 +1,6 @@
name: ✨ Feature Request
description: Suggest an idea
labels: ['awaiting triage']
type: feature
labels: ['enhancement', 'awaiting triage']
body:
- type: markdown
attributes:

View File

@@ -1,65 +0,0 @@
name: 🧰 Maintenance / Chore
description: CI, GitHub Actions, build, dependencies, refactors (non-feature work)
title: "[Chore]: "
labels: ["maintenance", "awaiting triage"]
type: task
body:
- type: markdown
attributes:
value: |
Maintainers / contributors: use this for internal tasks (CI, workflows, tooling, refactors).
If you're reporting a user-facing bug or requesting a feature, use the other templates.
- type: dropdown
id: area
attributes:
label: Area
options:
- CI / GitHub Actions
- build / packaging
- dependencies
- release process
- refactor / tech debt
- tooling / scripts
- other
validations:
required: true
- type: textarea
id: summary
attributes:
label: Summary
description: What needs doing and why?
validations:
required: true
- type: textarea
id: acceptance
attributes:
label: Acceptance criteria
description: What does "done" look like?
placeholder: |
- [ ] ...
- [ ] ...
validations:
required: false
- type: input
id: related
attributes:
label: Related links
description: PRs, failing workflow runs, logs, or relevant issues.
validations:
required: false
- type: checkboxes
id: search-existing
attributes:
label: Search Existing Issues
description: Have you searched existing issues to see if this has already been reported?
options:
- label: Yes, I have searched existing issues.
required: true
- type: checkboxes
id: terms
attributes:
label: Code of Conduct
description: By submitting this issue, you agree to follow our Code of Conduct.
options:
- label: I agree to follow Seerr's [Code of Conduct](https://github.com/seerr-team/seerr/blob/develop/CODE_OF_CONDUCT.md).
required: true

4
.github/cliff.toml vendored
View File

@@ -33,9 +33,9 @@ body = """
{{ self::print_commit(commit=commit) }}
{%- endfor %}
{%- for commit in commits %}
{%- if not commit.scope %}
{%- if not commit.scope -%}
{{ self::print_commit(commit=commit) }}
{%- endif %}
{%- endif -%}
{%- endfor -%}
{%- endfor -%}

View File

@@ -16,7 +16,7 @@
description: 'Update appVersion in Chart.yaml to match Docker image',
fileMatch: ['(^|/)Chart\\.yaml$'],
matchStrings: [
"#\\s+renovate:\\s+image=(?<depName>\\S*)\nappVersion:\\s+'(?<currentValue>\\S*)'",
'#\\s+renovate:\\s+image=(?<depName>\\S*)\nappVersion:\\s+"(?<currentValue>\\S*)"',
],
datasourceTemplate: 'docker',
},

View File

@@ -18,7 +18,7 @@ env:
DOCKER_HUB: seerr/seerr
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
group: ci-${{ github.ref }}
cancel-in-progress: true
jobs:

View File

@@ -20,7 +20,7 @@ permissions:
contents: read
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
group: codeql-${{ github.ref }}
cancel-in-progress: true
jobs:

View File

@@ -14,7 +14,7 @@ permissions:
contents: read
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
group: merge-conflict-${{ github.ref }}
cancel-in-progress: true
jobs:

View File

@@ -28,7 +28,7 @@ permissions:
contents: read
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
group: cypress-${{ github.ref }}
cancel-in-progress: true
jobs:

View File

@@ -6,7 +6,7 @@ on:
workflow_dispatch:
push:
branches:
- develop
- legacy-jellyseerr
paths:
- 'docs/**'
- 'gen-docs/**'
@@ -15,7 +15,7 @@ permissions:
contents: read
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
group: pages
cancel-in-progress: true
jobs:

View File

@@ -25,7 +25,7 @@ permissions:
contents: read
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
group: docs-link-check-${{ github.ref }}
cancel-in-progress: true
jobs:

View File

@@ -14,7 +14,7 @@ permissions:
contents: read
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
group: helm-charts
cancel-in-progress: true
jobs:

View File

@@ -18,7 +18,7 @@ permissions:
contents: read
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
group: charts-lint-${{ github.ref }}
cancel-in-progress: true
jobs:

View File

@@ -15,7 +15,7 @@ env:
DOCKER_HUB: seerr/seerr
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
group: preview-${{ github.ref }}
cancel-in-progress: true
jobs:

View File

@@ -11,7 +11,7 @@ permissions:
contents: read
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
group: release-${{ github.ref }}
cancel-in-progress: true
env:
@@ -279,17 +279,17 @@ jobs:
--certificate-identity "https://github.com/${{ github.workflow_ref }}" \
--certificate-oidc-issuer "https://token.actions.githubusercontent.com"
# - name: Verify attestations
# run: |
# cosign verify-attestation "ghcr.io/${{ github.repository }}@${{ needs.publish.outputs.image_digest }}" \
# --type cyclonedx \
# --certificate-identity "https://github.com/${{ github.workflow_ref }}" \
# --certificate-oidc-issuer "https://token.actions.githubusercontent.com" > /dev/null
- name: Verify attestations
run: |
cosign verify-attestation "ghcr.io/${{ github.repository }}@${{ needs.publish.outputs.image_digest }}" \
--type cyclonedx \
--certificate-identity "https://github.com/${{ github.workflow_ref }}" \
--certificate-oidc-issuer "https://token.actions.githubusercontent.com" > /dev/null
# cosign verify-attestation "${{ env.DOCKER_HUB }}@${{ needs.publish.outputs.image_digest }}" \
# --type cyclonedx \
# --certificate-identity "https://github.com/${{ github.workflow_ref }}" \
# --certificate-oidc-issuer "https://token.actions.githubusercontent.com" > /dev/null
cosign verify-attestation "${{ env.DOCKER_HUB }}@${{ needs.publish.outputs.image_digest }}" \
--type cyclonedx \
--certificate-identity "https://github.com/${{ github.workflow_ref }}" \
--certificate-oidc-issuer "https://token.actions.githubusercontent.com" > /dev/null
publish-release:
name: Publish release

View File

@@ -12,7 +12,7 @@ on:
permissions: {}
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
group: renovate-helm-hooks-${{ github.ref }}
cancel-in-progress: true
jobs:

View File

@@ -1,28 +0,0 @@
name: "Semantic PR"
on:
pull_request_target:
types:
- opened
- reopened
- edited
- synchronize
permissions: {}
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
cancel-in-progress: true
jobs:
main:
name: Validate PR Title
runs-on: ubuntu-slim
permissions:
contents: read
pull-requests: read
checks: write
steps:
- uses: amannn/action-semantic-pull-request@48f256284bd46cdaab1048c3721360e808335d50 # v6.1.1
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}

View File

@@ -9,7 +9,7 @@ on:
permissions: {}
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
group: close-stale-${{ github.ref }}
cancel-in-progress: true
jobs:

View File

@@ -14,7 +14,7 @@ permissions:
contents: read
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
group: docs-pr-${{ github.ref }}
cancel-in-progress: true
jobs:

View File

@@ -16,7 +16,7 @@ permissions:
contents: read
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
group: trivy-scan-${{ github.ref }}
cancel-in-progress: true
jobs:

View File

@@ -122,7 +122,7 @@ Steps:
- If you are taking on an existing bug or feature ticket, please comment on the [issue](/../../issues) to avoid multiple people working on the same thing.
- All commits **must** follow [Conventional Commits](https://www.conventionalcommits.org/en/v1.0.0/)
- Pull requests with titles or commits not following this standard will **not** be merged. PR titles are automatically checked for compliance.
- Pull requests with commits not following this standard will **not** be merged.
- Please make meaningful commits, or squash them prior to opening a pull request.
- Do not squash commits once people have begun reviewing your changes.
- Always rebase your commit to the latest `develop` branch. Do **not** merge `develop` into your branch.

View File

@@ -1,6 +1,6 @@
<p align="center">
<img src="./public/logo_full.svg" alt="Seerr" style="margin: 20px 0;">
</p>
<div align="center">⚠️ <strong>NOTE:</strong> We are currently in the process of merging Overseerr and Jellyseerr into this unified repository.</div>
<h1 align="center" style="font-size: 4em;">🚧 Seerr</h1>
<p align="center">
<img src="https://github.com/seerr-team/seerr/actions/workflows/release.yml/badge.svg" alt="Seerr Release" />
<img src="https://github.com/seerr-team/seerr/actions/workflows/ci.yml/badge.svg" alt="Seerr CI">
@@ -26,25 +26,37 @@
- Granular permission system.
- Support for various notification agents.
- Mobile-friendly design, for when you need to approve requests on the go!
- Support for watchlisting & blocklisting media.
- Support for watchlisting & blacklisting media.
With more features on the way! Check out our [issue tracker](/../../issues) to see the features which have already been requested.
## Getting Started
Check out our documentation for instructions on how to install and run Seerr:
For instructions on how to install and run **Jellyseerr**, please refer to the official documentation:
https://docs.seerr.dev/getting-started/
> [!IMPORTANT]
> **Seerr is not officially released yet.**
> The project is currently available **only on the `develop` branch** and is intended for **beta testing only**.
The documentation linked above is for running the **latest Jellyseerr** release.
> [!WARNING]
> If you are migrating from **Overseerr** to **Seerr** for beta testing, **do not follow the Jellyseerr latest setup guide**.
Instead, follow the dedicated migration guide (with `:develop` tag):
https://github.com/seerr-team/seerr/blob/develop/docs/migration-guide.mdx
> [!CAUTION]
> **DO NOT run Jellyseerr (latest) using an existing Overseerr database. This includes third-party images with `seerr:latest` (as it points to jellyseerr 2.7.3 and not seerr.**
> Doing so **may cause database corruption and/or irreversible data loss and/or weird unintended behaviour**.
For migration assistance, beta testing questions, or troubleshooting, please join our **Discord** and ask for support there.
## Preview
<img src="./public/preview.jpg" alt="Seerr application preview" />
## Migrating from Overseerr/Jellyseerr to Seerr
Read our [release announcement](https://docs.seerr.dev/blog/seerr-release) to learn what Seerr means for Jellyseerr and Overseerr users.
Please follow our [migration guide](https://docs.seerr.dev/migration-guide) for detailed instructions on migrating from Overseerr or Jellyseerr.
<img src="./public/preview.jpg">
## Support

View File

@@ -3,9 +3,9 @@ kubeVersion: '>=1.23.0-0'
name: seerr-chart
description: Seerr helm chart for Kubernetes
type: application
version: 3.1.0
version: 3.0.0
# renovate: image=ghcr.io/seerr-team/seerr
appVersion: 'v3.0.1'
appVersion: '3.0.0'
maintainers:
- name: Seerr Team
url: https://github.com/orgs/seerr-team/people

View File

@@ -1,6 +1,6 @@
# seerr-chart
![Version: 3.1.0](https://img.shields.io/badge/Version-3.1.0-informational?style=flat-square) ![Type: application](https://img.shields.io/badge/Type-application-informational?style=flat-square) ![AppVersion: v3.0.1](https://img.shields.io/badge/AppVersion-v3.0.1-informational?style=flat-square)
![Version: 3.0.0](https://img.shields.io/badge/Version-3.0.0-informational?style=flat-square) ![Type: application](https://img.shields.io/badge/Type-application-informational?style=flat-square) ![AppVersion: 3.0.0](https://img.shields.io/badge/AppVersion-3.0.0-informational?style=flat-square)
Seerr helm chart for Kubernetes
@@ -44,10 +44,9 @@ If `replicaCount` value was used - remove it. Helm update should work fine after
| Key | Type | Default | Description |
|-----|------|---------|-------------|
| affinity | object | `{}` | |
| config | object | `{"persistence":{"accessModes":["ReadWriteOnce"],"annotations":{},"existingClaim":"","name":"","size":"5Gi","volumeName":""}}` | Creating PVC to store configuration |
| config | object | `{"persistence":{"accessModes":["ReadWriteOnce"],"annotations":{},"name":"","size":"5Gi","volumeName":""}}` | Creating PVC to store configuration |
| config.persistence.accessModes | list | `["ReadWriteOnce"]` | Access modes of persistent disk |
| config.persistence.annotations | object | `{}` | Annotations for PVCs |
| config.persistence.existingClaim | string | `""` | Specify an existing `PersistentVolumeClaim` to use. If this value is provided, the default PVC will not be created |
| config.persistence.name | string | `""` | Config name |
| config.persistence.size | string | `"5Gi"` | Size of persistent disk |
| config.persistence.volumeName | string | `""` | Name of the permanent volume to reference in the claim. Can be used to bind to existing volumes. |

View File

@@ -1,4 +1,3 @@
{{- if not .Values.config.persistence.existingClaim -}}
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
@@ -23,4 +22,3 @@ spec:
resources:
requests:
storage: "{{ .Values.config.persistence.size }}"
{{- end -}}

View File

@@ -103,7 +103,7 @@ spec:
volumes:
- name: config
persistentVolumeClaim:
claimName: {{ if .Values.config.persistence.existingClaim }}{{ .Values.config.persistence.existingClaim }}{{- else }}{{ include "seerr.configPersistenceName" . }}{{- end }}
claimName: {{ include "seerr.configPersistenceName" . }}
{{- with .Values.volumes }}
{{- toYaml . | nindent 8 }}
{{- end }}

View File

@@ -86,8 +86,6 @@ config:
# -- Name of the permanent volume to reference in the claim.
# Can be used to bind to existing volumes.
volumeName: ''
# -- Specify an existing `PersistentVolumeClaim` to use. If this value is provided, the default PVC will not be created
existingClaim: ''
ingress:
enabled: false

View File

@@ -18,8 +18,8 @@
"discoverRegion": "",
"streamingRegion": "",
"originalLanguage": "",
"blocklistedTags": "",
"blocklistedTagsLimit": 50,
"blacklistedTags": "",
"blacklistedTagsLimit": 50,
"trustProxy": false,
"mediaServerType": 1,
"partialRequestsEnabled": true,

View File

@@ -23,7 +23,7 @@ Welcome to the Seerr Documentation.
- Localization into other languages.
- Support for **PostgreSQL** and **SQLite** databases.
- Support for various notification agents.
- Easily **Watchlist** or **Blocklist** media.
- Easily **Watchlist** or **Blacklist** media.
- More features to come!
## We need your help!

View File

@@ -5,7 +5,12 @@ sidebar_position: 3
---
# Unraid
:::danger
This method has not yet been updated for Seerr and is awaiting a community contribution.
Feel free to open a pull request on GitHub to update this installation method.
:::
<!--
:::warning
Third-party installation methods are maintained by the community. The Seerr team is not responsible for these packages.
:::
@@ -14,76 +19,9 @@ Third-party installation methods are maintained by the community. The Seerr team
This method is not recommended for most users. It is intended for advanced users who are using Unraid.
:::
If an official Unraid Community Applications template for Seerr isn't available in your catalog, you can install Seerr manually using Unraid's Docker UI.
## Fresh Installation
### 1. Create the config directory
:::note
Seerr is now rootless. Unraid typically runs Docker containers as `nobody:users` (UID 99, GID 100), but Seerr now runs internally as UID 1000, GID 1000. This creates a permission mismatch.
:::
:::info
**If migrating**: Copy your existing Jellyseerr/Overseerr config files (e.g., from `/mnt/user/appdata/overseerr/` or `/mnt/user/appdata/jellyseerr`) to `/mnt/user/appdata/seerr`, then apply the permissions below
:::
Open the Unraid terminal and run:
```bash
mkdir -p /mnt/user/appdata/seerr
chown -R 1000:1000 /mnt/user/appdata/seerr
```
### 2. Add the Docker container
Navigate to the **Docker** tab in Unraid and click **Add Container**. Fill in the following:
| Field | Value |
|---|---|
| **Name** | `seerr` |
| **Repository** | `ghcr.io/seerr-team/seerr:latest` |
| **Registry URL** (optional) | `https://ghcr.io` |
| **Icon URL** | `https://raw.githubusercontent.com/seerr-team/seerr/develop/public/android-chrome-512x512.png` |
| **WebUI** | `http://[IP]:[PORT:5055]` |
| **Extra Parameters** | `--init` |
| **Network Type** | `bridge` |
| **Privileged** | `Off` |
Then click **Add another Path, Port, Variable** to add:
**Port:**
| Field | Value |
|---|---|
| Container Port | `5055` |
| Host Port | `5055` |
| Connection Type | `TCP` |
**Path:**
| Field | Value |
|---|---|
| Container Path | `/app/config` |
| Host Path | `/mnt/user/appdata/seerr` |
**Variable:**
| Field | Value |
|---|---|
| Key | `TZ` |
| Value | Your [TZ database name](https://en.wikipedia.org/wiki/List_of_tz_database_time_zones) (e.g., `America/New_York`) |
**Variable (optional):**
| Field | Value |
|---|---|
| Key | `LOG_LEVEL` |
| Value | `info` |
Click **Apply** to create and start the container.
### 3. Access Seerr
Open the WebUI at `http://<your-unraid-ip>:5055` and follow the setup wizard.
:::info
The `--init` flag in **Extra Parameters** is required. Seerr does not include its own init process, so `--init` ensures proper signal handling and clean container shutdowns.
:::
1. Ensure you have the **Community Applications** plugin installed.
2. Inside the **Community Applications** app store, search for **Seerr**.
3. Click the **Install Button**.
4. On the following **Add Container** screen, make changes to the **Host Port** and **Host Path 1** \(Appdata\) as needed.
5. Click apply and access "Seerr" at your `<ServerIP:HostPort>` in a web browser.
-->

View File

@@ -23,6 +23,7 @@ Installation methods are now divided into two categories: official and third-par
The Seerr team is only responsible for official installation methods, while third-party methods are maintained by the community.
Some methods are currently not maintained, but this does not mean they are permanently discontinued. The community may restore and support them if they choose to do so.
- **Unraid app:** Not maintained
- **Snap package:** Not maintained
:::
@@ -199,82 +200,14 @@ Summary of changes :
</TabItem>
</Tabs>
## Third-party installation methods
### Nix
### Nix (Third-party installation methods)
Waiting for https://github.com/NixOS/nixpkgs/pull/450096 and https://github.com/NixOS/nixpkgs/pull/450093
### AUR
### AUR (Third-party installation methods)
See https://aur.archlinux.org/packages/seerr
### TrueNAS
### TrueNAS (Third-party installation methods)
Waiting for https://github.com/truenas/apps/issues/3374
### Unraid
Refer to [Seerr Unraid Documentation](/getting-started/third-parties/unraid), all of our examples have been updated to reflect the below change.
Seerr will automatically migrate your existing Overseerr or Jellyseerr data on first startup. No manual database migration is needed.
1. Stop and remove the old Overseerr (or Jellyseerr) container from the Unraid **Docker** tab. Click the container icon, then **Stop**, then **Remove**. **⚠️ Do not delete the appdata folder ⚠️**
2. Back up your existing appdata folder:
```bash
cp -a /mnt/user/appdata/overseerr /mnt/user/appdata/overseerr-backup
```
3. Fix config folder permissions — Seerr runs as the `node` user (UID 1000) instead of root:
```bash
chown -R 1000:1000 /mnt/user/appdata/overseerr
```
For Jellyseerr users, replace `overseerr` with `jellyseerr` in the path above.
4. Add a new container in the Unraid **Docker** tab. Click **Add Container** and fill in the following:
| Field | Value |
|---|---|
| **Name** | `seerr` |
| **Repository** | `ghcr.io/seerr-team/seerr:latest` |
| **Registry URL** (optional) | `https://ghcr.io` |
| **Icon URL** | `https://raw.githubusercontent.com/seerr-team/seerr/develop/public/android-chrome-512x512.png` |
| **WebUI** | `http://[IP]:[PORT:5055]` |
| **Extra Parameters** | `--init` |
| **Network Type** | `bridge` |
| **Privileged** | `Off` |
Then click **Add another Path, Port, Variable** to add:
**Port:**
| Field | Value |
|---|---|
| Container Port | `5055` |
| Host Port | `5055` |
| Connection Type | `TCP` |
**Path** — point this to your existing config folder:
| Field | Value |
|---|---|
| Container Path | `/app/config` |
| Host Path | `/mnt/user/appdata/overseerr` |
For Jellyseerr users, use `/mnt/user/appdata/jellyseerr`.
**Variable:**
| Field | Value |
|---|---|
| Key | `TZ` |
| Value | Your [TZ database name](https://en.wikipedia.org/wiki/List_of_tz_database_time_zones) (e.g., `America/New_York`) |
**Variable (optional):**
| Field | Value |
|---|---|
| Key | `LOG_LEVEL` |
| Value | `info` |
5. Click **Apply** to start the container. Check the container logs to confirm the automatic migration completed successfully.
:::tip
If you are using a reverse proxy (such as SWAG or Nginx Proxy Manager), update your proxy configuration to point to the new container name `seerr`. The default port remains `5055`.
:::

View File

@@ -13,7 +13,7 @@ These settings are stored in the `settings.json` file located in the Seerr data
## User Data
Apart from the settings, all other data—including user accounts, media requests, blocklist etc. are stored in the database (either SQLite or PostgreSQL).
Apart from the settings, all other data—including user accounts, media requests, blacklist etc. are stored in the database (either SQLite or PostgreSQL).
# Backup

View File

@@ -6,22 +6,18 @@ sidebar_position: 2
# Web Push
The web push notification agent enables you and your users to receive Seerr notifications in a supported browser.
This notification agent does not require any configuration, but is not enabled in Seerr
:::warning
Web push notifications require a secure connection to your Seerr instance. Refer to the [Reverse Proxy](/extending-seerr/reverse-proxy) documentation for more information.
:::
The web push notification agent enables you and your users to receive Seerr notifications in a supported browser. This offers a native notification experience without the need to install an app.
To set up web push notifications, simply enable the agent in **Settings → Notifications → Web Push**. You and your users will then be prompted to allow notifications in your web browser.
This notification agent does not require any configuration, but is not enabled by default in Seerr.
Users can opt out of these notifications, or customize the notification types they would like to subscribe to, in their user settings.
To set up web push notifications, simply enable the agent in **Settings → Notifications → Web Push**.
You and your users have the option to enable web push notifications by going to your **User Profile → Edit Settings → Notifications → Web Push → Enable web push**. Here you can also customize the notifications you'd like to receive.
:::info[Mobile Users]
For Web Push notifications to work on mobile you need to add Seerr to your home screen as progressive web app (PWA).
:::
:::info[iOS Users]
On iOS you may need to enable the Safari notifications feature flag by going to **Settings → Safari → Advanced → Feature Flags** and enabling "Notifications".
:::info
Web push notifications offer a native notification experience without the need to install an app.
:::

View File

@@ -62,13 +62,13 @@ Set the default display language for Seerr. Users can override this setting in t
These settings filter content shown on the "Discover" home page based on regional availability and original language, respectively. The Streaming Region filters the available streaming providers on the media page. Users can override these global settings by configuring these same options in their user settings.
## Blocklist Content with Tags and Limit Content Blocklisted per Tag
## Blacklist Content with Tags and Limit Content Blacklisted per Tag
These settings blocklist any TV shows or movies that have one of the entered tags. The "Process Blocklisted Tags" job adds entries to the blocklist based on the configured blocklisted tags. If a blocklisted tag is removed, any media blocklisted under that tag will be removed from the blocklist when the "Process Blocklisted Tags" job runs.
These settings blacklist any TV shows or movies that have one of the entered tags. The "Process Blacklisted Tags" job adds entries to the blacklist based on the configured blacklisted tags. If a blacklisted tag is removed, any media blacklisted under that tag will be removed from the blacklist when the "Process Blacklisted Tags" job runs.
The limit setting determines how many pages per tag the job will process, with each page containing 20 entries. The job cycles through all 16 available discovery sort options, querying the defined number of pages to blocklist media that is most likely to appear at the top of each sort. Higher limits will create a more accurate blocklist, but will require more storage.
The limit setting determines how many pages per tag the job will process, with each page containing 20 entries. The job cycles through all 16 available discovery sort options, querying the defined number of pages to blacklist media that is most likely to appear at the top of each sort. Higher limits will create a more accurate blacklist, but will require more storage.
Blocklisted tags are disabled until at least one tag is entered. These settings cannot be overridden in user settings.
Blacklisted tags are disabled until at least one tag is entered. These settings cannot be overridden in user settings.
## Hide Available Media
@@ -78,9 +78,9 @@ Available media will still appear in search results, however, so it is possible
This setting is **disabled** by default.
## Hide Blocklisted Items
## Hide Blacklisted Items
When enabled, media that has been blocklisted will not appear on the "Discover" home page, for all administrators. This can be useful to hide content that you don't want to see, such as content with specific tags or content that has been manually blocklisted when you have the "Manage Blocklist" permission.
When enabled, media that has been blacklisted will not appear on the "Discover" home page, for all administrators. This can be useful to hide content that you don't want to see, such as content with specific tags or content that has been manually blacklisted when you have the "Manage Blacklist" permission.
This setting is **disabled** by default.

View File

@@ -21,7 +21,7 @@ Seerr brings several features that were previously available in Jellyseerr but m
* **Alternative media solution:** Added support for Jellyfin and Emby in addition to the existing Plex integration.
* **PostgreSQL support**: In addition to SQLite, you can now opt in to using a PostgreSQL database.
* **Blocklist for movies, series, and tags**: Allows permitted users to hide movies, series, or tags from regular users.
* **Blacklist for movies, series, and tags**: Allows permitted users to hide movies, series, or tags from regular users.
* **Override rules**: Adjust default request settings based on conditions such as user, tag, or other criteria.
* **TVDB metadata**: Option to use TheTVDB metadata for series (as in Sonarr) instead of TMDB.
* **DNS caching**: Reduces lookup times and external requests, especially useful when using systems like Pi-Hole/Adguard Home.

Binary file not shown.

Before

Width:  |  Height:  |  Size: 15 KiB

After

Width:  |  Height:  |  Size: 15 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 6.0 KiB

After

Width:  |  Height:  |  Size: 25 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 1.6 KiB

After

Width:  |  Height:  |  Size: 22 KiB

View File

@@ -122,7 +122,7 @@
"@types/cookie-parser": "1.4.10",
"@types/country-flag-icons": "1.2.2",
"@types/csurf": "1.11.5",
"@types/email-templates": "10.0.4",
"@types/email-templates": "8.0.4",
"@types/express": "4.17.17",
"@types/express-session": "1.18.2",
"@types/lodash": "4.17.21",

327
pnpm-lock.yaml generated
View File

@@ -278,8 +278,8 @@ importers:
specifier: 1.11.5
version: 1.11.5
'@types/email-templates':
specifier: 10.0.4
version: 10.0.4(encoding@0.1.13)
specifier: 8.0.4
version: 8.0.4(encoding@0.1.13)
'@types/express':
specifier: 4.17.17
version: 4.17.17
@@ -2941,8 +2941,8 @@ packages:
'@types/debug@4.1.12':
resolution: {integrity: sha512-vIChWdVG3LG1SMxEvI/AK+FWJthlrqlTu7fbrlywTkkaONwk/UAGaULXRlf8vkzFBLVm0zkMdCquhL5aOjhXPQ==}
'@types/email-templates@10.0.4':
resolution: {integrity: sha512-8O2bdGPO6RYgH2DrnFAcuV++s+8KNA5e2Erjl6UxgKRVsBH9zXu2YLrLyOBRMn2VyEYmzgF+6QQUslpVhj0y/g==}
'@types/email-templates@8.0.4':
resolution: {integrity: sha512-HYvVoyG8qS6PrimZZOS4wMrtQ9MelKEl0sOpi4zVpz2Ds74v+UvWckIFz3NyGyTwAR1okMbwJkApgR2GL/ALjg==}
'@types/eslint@8.56.10':
resolution: {integrity: sha512-Shavhk87gCtY2fhXDctcfS3e6FdxWkCx1iUZ9eEUbh7rTqlZT0/IzOkCOVt0fCjcFuZ9FPYfuezTBImfHCDBGQ==}
@@ -3148,6 +3148,14 @@ packages:
typescript:
optional: true
'@typescript-eslint/eslint-plugin@8.54.0':
resolution: {integrity: sha512-hAAP5io/7csFStuOmR782YmTthKBJ9ND3WVL60hcOjvtGFb+HJxH4O5huAcmcZ9v9G8P+JETiZ/G1B8MALnWZQ==}
engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0}
peerDependencies:
'@typescript-eslint/parser': ^8.54.0
eslint: ^8.57.0 || ^9.0.0
typescript: '>=4.8.4 <6.0.0'
'@typescript-eslint/parser@7.18.0':
resolution: {integrity: sha512-4Z+L8I2OqhZV8qA132M4wNL30ypZGYOQVBfMgxDH/K5UX0PNqTu1c6za9ST5r9+tavvHiTWmBnKzpCJ/GlVFtg==}
engines: {node: ^18.18.0 || >=20.0.0}
@@ -3158,10 +3166,33 @@ packages:
typescript:
optional: true
'@typescript-eslint/parser@8.54.0':
resolution: {integrity: sha512-BtE0k6cjwjLZoZixN0t5AKP0kSzlGu7FctRXYuPAm//aaiZhmfq1JwdYpYr1brzEspYyFeF+8XF5j2VK6oalrA==}
engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0}
peerDependencies:
eslint: ^8.57.0 || ^9.0.0
typescript: '>=4.8.4 <6.0.0'
'@typescript-eslint/project-service@8.54.0':
resolution: {integrity: sha512-YPf+rvJ1s7MyiWM4uTRhE4DvBXrEV+d8oC3P9Y2eT7S+HBS0clybdMIPnhiATi9vZOYDc7OQ1L/i6ga6NFYK/g==}
engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0}
peerDependencies:
typescript: '>=4.8.4 <6.0.0'
'@typescript-eslint/scope-manager@7.18.0':
resolution: {integrity: sha512-jjhdIE/FPF2B7Z1uzc6i3oWKbGcHb87Qw7AWj6jmEqNOfDFbJWtjt/XfwCpvNkpGWlcJaog5vTR+VV8+w9JflA==}
engines: {node: ^18.18.0 || >=20.0.0}
'@typescript-eslint/scope-manager@8.54.0':
resolution: {integrity: sha512-27rYVQku26j/PbHYcVfRPonmOlVI6gihHtXFbTdB5sb6qA0wdAQAbyXFVarQ5t4HRojIz64IV90YtsjQSSGlQg==}
engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0}
'@typescript-eslint/tsconfig-utils@8.54.0':
resolution: {integrity: sha512-dRgOyT2hPk/JwxNMZDsIXDgyl9axdJI3ogZ2XWhBPsnZUv+hPesa5iuhdYt2gzwA9t8RE5ytOJ6xB0moV0Ujvw==}
engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0}
peerDependencies:
typescript: '>=4.8.4 <6.0.0'
'@typescript-eslint/type-utils@7.18.0':
resolution: {integrity: sha512-XL0FJXuCLaDuX2sYqZUUSOJ2sG5/i1AAze+axqmLnSkNEVMVYLF+cbwlB2w8D1tinFuSikHmFta+P+HOofrLeA==}
engines: {node: ^18.18.0 || >=20.0.0}
@@ -3172,6 +3203,13 @@ packages:
typescript:
optional: true
'@typescript-eslint/type-utils@8.54.0':
resolution: {integrity: sha512-hiLguxJWHjjwL6xMBwD903ciAwd7DmK30Y9Axs/etOkftC3ZNN9K44IuRD/EB08amu+Zw6W37x9RecLkOo3pMA==}
engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0}
peerDependencies:
eslint: ^8.57.0 || ^9.0.0
typescript: '>=4.8.4 <6.0.0'
'@typescript-eslint/types@5.45.0':
resolution: {integrity: sha512-QQij+u/vgskA66azc9dCmx+rev79PzX8uDHpsqSjEFtfF2gBUTRCpvYMh2gw2ghkJabNkPlSUCimsyBEQZd1DA==}
engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
@@ -3180,6 +3218,10 @@ packages:
resolution: {integrity: sha512-iZqi+Ds1y4EDYUtlOOC+aUmxnE9xS/yCigkjA7XpTKV6nCBd3Hp/PRGGmdwnfkV2ThMyYldP1wRpm/id99spTQ==}
engines: {node: ^18.18.0 || >=20.0.0}
'@typescript-eslint/types@8.54.0':
resolution: {integrity: sha512-PDUI9R1BVjqu7AUDsRBbKMtwmjWcn4J3le+5LpcFgWULN3LvHC5rkc9gCVxbrsrGmO1jfPybN5s6h4Jy+OnkAA==}
engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0}
'@typescript-eslint/typescript-estree@5.45.0':
resolution: {integrity: sha512-maRhLGSzqUpFcZgXxg1qc/+H0bT36lHK4APhp0AEUVrpSwXiRAomm/JGjSG+kNUio5kAa3uekCYu/47cnGn5EQ==}
engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
@@ -3198,12 +3240,25 @@ packages:
typescript:
optional: true
'@typescript-eslint/typescript-estree@8.54.0':
resolution: {integrity: sha512-BUwcskRaPvTk6fzVWgDPdUndLjB87KYDrN5EYGetnktoeAvPtO4ONHlAZDnj5VFnUANg0Sjm7j4usBlnoVMHwA==}
engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0}
peerDependencies:
typescript: '>=4.8.4 <6.0.0'
'@typescript-eslint/utils@7.18.0':
resolution: {integrity: sha512-kK0/rNa2j74XuHVcoCZxdFBMF+aq/vH83CXAOHieC+2Gis4mF8jJXT5eAfyD3K0sAxtPuwxaIOIOvhwzVDt/kw==}
engines: {node: ^18.18.0 || >=20.0.0}
peerDependencies:
eslint: ^8.56.0
'@typescript-eslint/utils@8.54.0':
resolution: {integrity: sha512-9Cnda8GS57AQakvRyG0PTejJNlA2xhvyNtEVIMlDWOOeEyBkYWhGPnfrIAnqxLMTSTo6q8g12XVjjev5l1NvMA==}
engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0}
peerDependencies:
eslint: ^8.57.0 || ^9.0.0
typescript: '>=4.8.4 <6.0.0'
'@typescript-eslint/visitor-keys@5.45.0':
resolution: {integrity: sha512-jc6Eccbn2RtQPr1s7th6jJWQHBHI6GBVQkCHoJFQ5UreaKm59Vxw+ynQUPPY2u2Amquc+7tmEoC2G52ApsGNNg==}
engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
@@ -3212,6 +3267,10 @@ packages:
resolution: {integrity: sha512-cDF0/Gf81QpY3xYyJKDV14Zwdmid5+uuENhjH2EqFaF0ni+yAyq/LzMaIJdhNJXZI7uLzwIlA+V7oWoyn6Curg==}
engines: {node: ^18.18.0 || >=20.0.0}
'@typescript-eslint/visitor-keys@8.54.0':
resolution: {integrity: sha512-VFlhGSl4opC0bprJiItPQ1RfUhGDIBokcPwaFH4yiBCaNPeld/9VeXbiPO1cLyorQi1G1vL+ecBk1x8o1axORA==}
engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0}
'@ungap/structured-clone@1.3.0':
resolution: {integrity: sha512-WmoN8qaIAo7WTYWbAZuG8PYEhn5fkz7dZrqTBZ7dtt//lL2Gwms1IcnQ5yHqjDfX8Ft5j4YzDM23f87zBfDe9g==}
@@ -3739,16 +3798,9 @@ packages:
resolution: {integrity: sha512-Pj779qHxV2tuapviy1bSZNEL1maXr13bPYpsvSDB68HlYcYuhlDrmGd63i0JHMCLKzc7rUSNIrpdJlhVlNwrxA==}
engines: {node: '>= 0.8.0'}
cheerio-select@1.6.0:
resolution: {integrity: sha512-eq0GdBvxVFbqWgmCm7M3XGs1I8oLy/nExUnh6oLqmBditPO9AqQJrkslDpMun/hZ0yyTs8L0m85OHp4ho6Qm9g==}
cheerio-select@2.1.0:
resolution: {integrity: sha512-9v9kG0LvzrlcungtnJtpGNxY+fzECQKhK4EGJX2vByejiMX84MFNQw4UxPJl3bFbTMw+Dfs37XaIkCwTZfLh4g==}
cheerio@1.0.0-rc.10:
resolution: {integrity: sha512-g0J0q/O6mW8z5zxQ3A8E8J1hUgp4SMOvEoW/x84OwyHKe/Zccz83PVT4y5Crcr530FV6NgmKI1qvGTKVl9XXVw==}
engines: {node: '>= 6'}
cheerio@1.0.0-rc.12:
resolution: {integrity: sha512-VqR8m68vM46BNnuZ5NtnGBKIE/DfN0cRIzg9n40EIq9NOv90ayxLBXA8fXC5gquFRGJSTRqBq25Jt2ECLR431Q==}
engines: {node: '>= 6'}
@@ -3907,6 +3959,10 @@ packages:
resolution: {integrity: sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA==}
engines: {node: '>= 6'}
commander@5.1.0:
resolution: {integrity: sha512-P0CysNDQ7rtVw4QIQtm+MRxV66vKFSvlsQvGYXZWR3qFU0jlMKHZZZgw8e+8DSah4UDKMqnknRDQz+xuQXQ/Zg==}
engines: {node: '>= 6'}
commander@6.2.1:
resolution: {integrity: sha512-U7VdrJFnJgo4xjrHpTzu0yrHPGImdsmD95ZlgYSEajAn2JKzDhDTPG9kBTefmObL2w/ngeZnilk+OV9CG3d7UA==}
engines: {node: '>= 6'}
@@ -4627,6 +4683,10 @@ packages:
resolution: {integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==}
engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
eslint-visitor-keys@4.2.1:
resolution: {integrity: sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==}
engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0}
eslint@8.57.1:
resolution: {integrity: sha512-ypowyDxpVSYpkXr9WPv2PAZCtNip1Mv5KTW0SCurXv/9iOpcrH9PaqUElksqEB6pChqHGDRCFTyrZlGhnLNGiA==}
engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
@@ -5017,22 +5077,20 @@ packages:
glob@10.3.10:
resolution: {integrity: sha512-fa46+tv1Ak0UPK1TOy/pZrIybNNt4HCv7SDzwyfiOZkvZLEbjsZkJBPtDHVshZjbecAoAGSC20MjLDG/qr679g==}
engines: {node: '>=16 || 14 >=14.17'}
deprecated: Old versions of glob are not supported, and contain widely publicized security vulnerabilities, which have been fixed in the current version. Please update. Support for old versions may be purchased (at exorbitant rates) by contacting i@izs.me
hasBin: true
glob@10.5.0:
resolution: {integrity: sha512-DfXN8DfhJ7NH3Oe7cFmu3NCu1wKbkReJ8TorzSAFbSKrlNaQSKfIzqYqVY8zlbs2NLBbWpRiU52GX2PbaBVNkg==}
deprecated: Old versions of glob are not supported, and contain widely publicized security vulnerabilities, which have been fixed in the current version. Please update. Support for old versions may be purchased (at exorbitant rates) by contacting i@izs.me
hasBin: true
glob@7.2.3:
resolution: {integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==}
deprecated: Old versions of glob are not supported, and contain widely publicized security vulnerabilities, which have been fixed in the current version. Please update. Support for old versions may be purchased (at exorbitant rates) by contacting i@izs.me
deprecated: Glob versions prior to v9 are no longer supported
glob@8.1.0:
resolution: {integrity: sha512-r8hpEjiQEYlF2QU0df3dS+nxxSIreXQS1qRhMJM0Q5NDdR386C7jb7Hwwod8Fgiuex+k0GFjgft18yvxm5XoCQ==}
engines: {node: '>=12'}
deprecated: Old versions of glob are not supported, and contain widely publicized security vulnerabilities, which have been fixed in the current version. Please update. Support for old versions may be purchased (at exorbitant rates) by contacting i@izs.me
deprecated: Glob versions prior to v9 are no longer supported
global-directory@4.0.1:
resolution: {integrity: sha512-wHTUcDUoZ1H5/0iVqEudYW4/kAlN5cZ3j/bXn0Dpbizl9iaUVeWSHqiOjsgk6OW2bkLclbBjzewBz6weQ1zA2Q==}
@@ -5167,12 +5225,12 @@ packages:
resolution: {integrity: sha512-qY60FjREgVZL03vJU6IfMV4GDjGBIoOyvuFdpBDIX9yTlDw0TjxVBQp+P8NvpdIXNJvfWBTNul7fsAQJq2FNpg==}
engines: {node: '>=14'}
htmlparser2@4.1.0:
resolution: {integrity: sha512-4zDq1a1zhE4gQso/c5LP1OtrhYTncXNSpvJYtWJBtXAETPlMfi3IFNjGuQbYLuVY4ZR0QMqRVvo4Pdy9KLyP8Q==}
htmlparser2@5.0.1:
resolution: {integrity: sha512-vKZZra6CSe9qsJzh0BjBGXo8dvzNsq/oGvsjfRdOrrryfeD9UOBEEQdeoqCRmKZchF5h2zOBMQ6YuQ0uRUmdbQ==}
htmlparser2@6.1.0:
resolution: {integrity: sha512-gyyPk6rgonLFEDGoeRgQNaEUvdJ4ktTmmUh/h2t7s+M8oPpIPxgNACWa+6ESR57kXstwqPiCut0V8NRpcwgU7A==}
htmlparser2@8.0.2:
resolution: {integrity: sha512-GYdjWKDkbRLkZ5geuHs5NY1puJ+PXwP7+fHPRz06Eirsb9ugf6d8kkXav6ADhcODhFFPMIXyxkxSuMf3D6NCFA==}
@@ -5260,6 +5318,10 @@ packages:
resolution: {integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==}
engines: {node: '>= 4'}
ignore@7.0.5:
resolution: {integrity: sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==}
engines: {node: '>= 4'}
image-size@1.2.1:
resolution: {integrity: sha512-rH+46sQJ2dlwfjfhCyNx5thzrv+dtmBIhPHk0zgRUukHzZ/kRueTJXoYYsclBaKcSMBWuGbOFXtioLpzTb5euw==}
engines: {node: '>=16.x'}
@@ -5603,6 +5665,10 @@ packages:
resolution: {integrity: sha512-eIz2msL/EzL9UFTFFx7jBTkeZfku0yUAyZZZmJ93H2TYEiroIx2PQjEXcwYtYl8zXCxb+PAmA2hLIt/6ZEkPHw==}
engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
jiti@1.21.6:
resolution: {integrity: sha512-2yTgeWTWzMWkHu6Jp9NKgePDaYHbntiwvYuuJLbbN9vl7DC9DvXKOB2BC3ZZ92D3cvV/aflH0osDfwpHepQ53w==}
hasBin: true
jiti@1.21.7:
resolution: {integrity: sha512-/imKNG4EbWNrVjoNC/1H5/9GFy+tqjGBHCaSsN+P2RnPqjsLmv6UD3Ej+Kj8nBWaRAwyk7kK5ZUc+OEatnTR3A==}
hasBin: true
@@ -5718,8 +5784,8 @@ packages:
engines: {node: '>=10.0.0'}
hasBin: true
juice@8.1.0:
resolution: {integrity: sha512-FLzurJrx5Iv1e7CfBSZH68dC04EEvXvvVvPYB7Vx1WAuhCp1ZPIMtqxc+WTWxVkpTIC2Ach/GAv0rQbtGf6YMA==}
juice@7.0.0:
resolution: {integrity: sha512-AjKQX31KKN+uJs+zaf+GW8mBO/f/0NqSh2moTMyvwBY+4/lXIYTU8D8I2h6BAV3Xnz6GGsbalUyFqbYMe+Vh+Q==}
engines: {node: '>=10.0.0'}
hasBin: true
@@ -6244,6 +6310,10 @@ packages:
resolution: {integrity: sha512-lKwV/1brpG6mBUFHtb7NUmtABCb2WZZmm2wNiOA5hAb8VdCS4B3dtMWyvcoViccwAW/COERjXLt0zP1zXUN26g==}
engines: {node: '>=10'}
minimatch@9.0.4:
resolution: {integrity: sha512-KqWh+VchfxcMNRAJjj2tnsSJdNbHsVgnkBhTNrW7AjVo6OvLtxw8zfT9oLw1JSohlFzJ8jCoTgaoXvJ+kHt6fw==}
engines: {node: '>=16 || 14 >=14.17'}
minimatch@9.0.5:
resolution: {integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==}
engines: {node: '>=16 || 14 >=14.17'}
@@ -6693,15 +6763,9 @@ packages:
resolution: {integrity: sha512-1Y1A//QUXEZK7YKz+rD9WydcE1+EuPr6ZBgKecAB8tmoW6UFv0NREVJe1p+jRxtThkcbbKkfwIbWJe/IeE6m2Q==}
engines: {node: '>=0.10.0'}
parse5-htmlparser2-tree-adapter@6.0.1:
resolution: {integrity: sha512-qPuWvbLgvDGilKc5BoicRovlT4MtYT6JfJyBOMDsKoiT+GiuP5qyrPCnR9HcPECIJJmZh5jRndyNThnhhb/vlA==}
parse5-htmlparser2-tree-adapter@7.0.0:
resolution: {integrity: sha512-B77tOZrqqfUfnVcOrUvfdLbz4pu4RopLD/4vmu3HUPswwTA8OH0EMW9BlWR2B0RCoiZRAHEUu7IxeP1Pd1UU+g==}
parse5@6.0.1:
resolution: {integrity: sha512-Ofn/CTFzRGTTxwpNEs9PP93gXShHcTq255nzRYSKe8AkVpZY7e1fpmTfOyoIvjP5HG7Z2ZM7VS9PPhQGW2pOpw==}
parse5@7.1.2:
resolution: {integrity: sha512-Czj1WaSVpaoj0wbhMzLmWD69anp2WH7FXMB9n1Sy8/ZFF9jolSQVMu1Ij5WIyGmcBmhk7EOndpO4mIpihVqAXw==}
@@ -8013,7 +8077,7 @@ packages:
tar@6.2.1:
resolution: {integrity: sha512-DZ4yORTwrbTj/7MZYq2w+/ZFdI6OZ/f9SFHR+71gIVUZhOQPHzVCLpvRnPgyaMpfWxxk/4ONva3GQSyNIKRv6A==}
engines: {node: '>=10'}
deprecated: Old versions of tar are not supported, and contain widely publicized security vulnerabilities, which have been fixed in the current version. Please update. Support for old versions may be purchased (at exorbitant rates) by contacting i@izs.me
deprecated: Old versions of tar are not supported, and contain widely publicized security vulnerabilities, which have been fixed in the current version. Please update. Support for old versions may be purchased (at exhorbitant rates) by contacting i@izs.me
temp-dir@2.0.0:
resolution: {integrity: sha512-aoBAniQmmwtcKp/7BzsH8Cxzv8OL736p7v1ihGb5e9DJ9kTwGWHrQrVB5+lfVDzfGrdRzXch+ig7LHaY1JTOrg==}
@@ -8152,6 +8216,12 @@ packages:
peerDependencies:
typescript: '>=4.2.0'
ts-api-utils@2.4.0:
resolution: {integrity: sha512-3TaVTaAv2gTiMB35i3FiGJaRfwb3Pyn/j3m/bfAvGe8FB7CF6u+LMYqYlDh7reQf7UNvoTvdfAqHGmPGOSsPmA==}
engines: {node: '>=18.12'}
peerDependencies:
typescript: '>=4.8.4'
ts-interface-checker@0.1.13:
resolution: {integrity: sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA==}
@@ -8534,6 +8604,10 @@ packages:
engines: {node: '>= 16'}
hasBin: true
web-resource-inliner@5.0.0:
resolution: {integrity: sha512-AIihwH+ZmdHfkJm7BjSXiEClVt4zUFqX4YlFAzjL13wLtDuUneSaFvDBTbdYRecs35SiU7iNKbMnN+++wVfb6A==}
engines: {node: '>=10.0.0'}
web-resource-inliner@6.0.1:
resolution: {integrity: sha512-kfqDxt5dTB1JhqsCUQVFDj0rmY+4HLwGQIsLPbyrsN9y9WV/1oFDSx3BQ4GfCv9X+jVeQ7rouTqwK53rA/7t8A==}
engines: {node: '>=10.0.0'}
@@ -12118,11 +12192,11 @@ snapshots:
dependencies:
'@types/ms': 0.7.34
'@types/email-templates@10.0.4(encoding@0.1.13)':
'@types/email-templates@8.0.4(encoding@0.1.13)':
dependencies:
'@types/html-to-text': 9.0.4
'@types/nodemailer': 7.0.9
juice: 8.1.0(encoding@0.1.13)
juice: 7.0.0(encoding@0.1.13)
transitivePeerDependencies:
- encoding
@@ -12340,6 +12414,22 @@ snapshots:
transitivePeerDependencies:
- supports-color
'@typescript-eslint/eslint-plugin@8.54.0(@typescript-eslint/parser@8.54.0(eslint@8.57.1)(typescript@5.4.5))(eslint@8.57.1)(typescript@5.4.5)':
dependencies:
'@eslint-community/regexpp': 4.12.2
'@typescript-eslint/parser': 8.54.0(eslint@8.57.1)(typescript@5.4.5)
'@typescript-eslint/scope-manager': 8.54.0
'@typescript-eslint/type-utils': 8.54.0(eslint@8.57.1)(typescript@5.4.5)
'@typescript-eslint/utils': 8.54.0(eslint@8.57.1)(typescript@5.4.5)
'@typescript-eslint/visitor-keys': 8.54.0
eslint: 8.57.1
ignore: 7.0.5
natural-compare: 1.4.0
ts-api-utils: 2.4.0(typescript@5.4.5)
typescript: 5.4.5
transitivePeerDependencies:
- supports-color
'@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5)':
dependencies:
'@typescript-eslint/scope-manager': 7.18.0
@@ -12353,11 +12443,41 @@ snapshots:
transitivePeerDependencies:
- supports-color
'@typescript-eslint/parser@8.54.0(eslint@8.57.1)(typescript@5.4.5)':
dependencies:
'@typescript-eslint/scope-manager': 8.54.0
'@typescript-eslint/types': 8.54.0
'@typescript-eslint/typescript-estree': 8.54.0(typescript@5.4.5)
'@typescript-eslint/visitor-keys': 8.54.0
debug: 4.4.3(supports-color@5.5.0)
eslint: 8.57.1
typescript: 5.4.5
transitivePeerDependencies:
- supports-color
'@typescript-eslint/project-service@8.54.0(typescript@5.4.5)':
dependencies:
'@typescript-eslint/tsconfig-utils': 8.54.0(typescript@5.4.5)
'@typescript-eslint/types': 8.54.0
debug: 4.4.3(supports-color@5.5.0)
typescript: 5.4.5
transitivePeerDependencies:
- supports-color
'@typescript-eslint/scope-manager@7.18.0':
dependencies:
'@typescript-eslint/types': 7.18.0
'@typescript-eslint/visitor-keys': 7.18.0
'@typescript-eslint/scope-manager@8.54.0':
dependencies:
'@typescript-eslint/types': 8.54.0
'@typescript-eslint/visitor-keys': 8.54.0
'@typescript-eslint/tsconfig-utils@8.54.0(typescript@5.4.5)':
dependencies:
typescript: 5.4.5
'@typescript-eslint/type-utils@7.18.0(eslint@8.57.1)(typescript@5.4.5)':
dependencies:
'@typescript-eslint/typescript-estree': 7.18.0(typescript@5.4.5)
@@ -12370,10 +12490,24 @@ snapshots:
transitivePeerDependencies:
- supports-color
'@typescript-eslint/type-utils@8.54.0(eslint@8.57.1)(typescript@5.4.5)':
dependencies:
'@typescript-eslint/types': 8.54.0
'@typescript-eslint/typescript-estree': 8.54.0(typescript@5.4.5)
'@typescript-eslint/utils': 8.54.0(eslint@8.57.1)(typescript@5.4.5)
debug: 4.4.3(supports-color@5.5.0)
eslint: 8.57.1
ts-api-utils: 2.4.0(typescript@5.4.5)
typescript: 5.4.5
transitivePeerDependencies:
- supports-color
'@typescript-eslint/types@5.45.0': {}
'@typescript-eslint/types@7.18.0': {}
'@typescript-eslint/types@8.54.0': {}
'@typescript-eslint/typescript-estree@5.45.0(typescript@4.9.5)':
dependencies:
'@typescript-eslint/types': 5.45.0
@@ -12403,6 +12537,21 @@ snapshots:
transitivePeerDependencies:
- supports-color
'@typescript-eslint/typescript-estree@8.54.0(typescript@5.4.5)':
dependencies:
'@typescript-eslint/project-service': 8.54.0(typescript@5.4.5)
'@typescript-eslint/tsconfig-utils': 8.54.0(typescript@5.4.5)
'@typescript-eslint/types': 8.54.0
'@typescript-eslint/visitor-keys': 8.54.0
debug: 4.4.3(supports-color@5.5.0)
minimatch: 9.0.5
semver: 7.7.3
tinyglobby: 0.2.15
ts-api-utils: 2.4.0(typescript@5.4.5)
typescript: 5.4.5
transitivePeerDependencies:
- supports-color
'@typescript-eslint/utils@7.18.0(eslint@8.57.1)(typescript@5.4.5)':
dependencies:
'@eslint-community/eslint-utils': 4.9.1(eslint@8.57.1)
@@ -12414,6 +12563,17 @@ snapshots:
- supports-color
- typescript
'@typescript-eslint/utils@8.54.0(eslint@8.57.1)(typescript@5.4.5)':
dependencies:
'@eslint-community/eslint-utils': 4.9.1(eslint@8.57.1)
'@typescript-eslint/scope-manager': 8.54.0
'@typescript-eslint/types': 8.54.0
'@typescript-eslint/typescript-estree': 8.54.0(typescript@5.4.5)
eslint: 8.57.1
typescript: 5.4.5
transitivePeerDependencies:
- supports-color
'@typescript-eslint/visitor-keys@5.45.0':
dependencies:
'@typescript-eslint/types': 5.45.0
@@ -12424,6 +12584,11 @@ snapshots:
'@typescript-eslint/types': 7.18.0
eslint-visitor-keys: 3.4.3
'@typescript-eslint/visitor-keys@8.54.0':
dependencies:
'@typescript-eslint/types': 8.54.0
eslint-visitor-keys: 4.2.1
'@ungap/structured-clone@1.3.0': {}
JSONStream@1.3.5:
@@ -13015,14 +13180,6 @@ snapshots:
check-more-types@2.24.0: {}
cheerio-select@1.6.0:
dependencies:
css-select: 4.3.0
css-what: 6.1.0
domelementtype: 2.3.0
domhandler: 4.3.1
domutils: 2.8.0
cheerio-select@2.1.0:
dependencies:
boolbase: 1.0.0
@@ -13032,16 +13189,6 @@ snapshots:
domhandler: 5.0.3
domutils: 3.1.0
cheerio@1.0.0-rc.10:
dependencies:
cheerio-select: 1.6.0
dom-serializer: 1.4.1
domhandler: 4.3.1
htmlparser2: 6.1.0
parse5: 6.0.1
parse5-htmlparser2-tree-adapter: 6.0.1
tslib: 2.8.1
cheerio@1.0.0-rc.12:
dependencies:
cheerio-select: 2.1.0
@@ -13201,6 +13348,8 @@ snapshots:
commander@4.1.1: {}
commander@5.1.0: {}
commander@6.2.1: {}
commander@7.2.0: {}
@@ -13368,7 +13517,7 @@ snapshots:
dependencies:
'@types/node': 22.10.5
cosmiconfig: 9.0.0(typescript@5.4.5)
jiti: 1.21.7
jiti: 1.21.6
typescript: 5.4.5
optional: true
@@ -14000,12 +14149,12 @@ snapshots:
dependencies:
'@next/eslint-plugin-next': 14.2.35
'@rushstack/eslint-patch': 1.10.3
'@typescript-eslint/eslint-plugin': 7.18.0(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint@8.57.1)(typescript@5.4.5)
'@typescript-eslint/parser': 7.18.0(eslint@8.57.1)(typescript@5.4.5)
'@typescript-eslint/eslint-plugin': 8.54.0(@typescript-eslint/parser@8.54.0(eslint@8.57.1)(typescript@5.4.5))(eslint@8.57.1)(typescript@5.4.5)
'@typescript-eslint/parser': 8.54.0(eslint@8.57.1)(typescript@5.4.5)
eslint: 8.57.1
eslint-import-resolver-node: 0.3.9
eslint-import-resolver-typescript: 3.6.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint-plugin-import@2.29.1)(eslint@8.57.1)
eslint-plugin-import: 2.29.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.1)
eslint-import-resolver-typescript: 3.6.1(@typescript-eslint/parser@8.54.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint-plugin-import@2.29.1)(eslint@8.57.1)
eslint-plugin-import: 2.29.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint@8.57.1)
eslint-plugin-jsx-a11y: 6.10.2(eslint@8.57.1)
eslint-plugin-react: 7.37.5(eslint@8.57.1)
eslint-plugin-react-hooks: 4.6.0(eslint@8.57.1)
@@ -14027,13 +14176,13 @@ snapshots:
transitivePeerDependencies:
- supports-color
eslint-import-resolver-typescript@3.6.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint-plugin-import@2.29.1)(eslint@8.57.1):
eslint-import-resolver-typescript@3.6.1(@typescript-eslint/parser@8.54.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint-plugin-import@2.29.1)(eslint@8.57.1):
dependencies:
debug: 4.4.3(supports-color@5.5.0)
enhanced-resolve: 5.17.0
eslint: 8.57.1
eslint-module-utils: 2.8.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.1)
eslint-plugin-import: 2.29.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.1)
eslint-module-utils: 2.8.1(@typescript-eslint/parser@8.54.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.1)
eslint-plugin-import: 2.29.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint@8.57.1)
fast-glob: 3.3.3
get-tsconfig: 4.13.0
is-core-module: 2.16.1
@@ -14044,14 +14193,24 @@ snapshots:
- eslint-import-resolver-webpack
- supports-color
eslint-module-utils@2.8.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.1):
eslint-module-utils@2.8.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint@8.57.1):
dependencies:
debug: 3.2.7(supports-color@8.1.1)
optionalDependencies:
'@typescript-eslint/parser': 7.18.0(eslint@8.57.1)(typescript@5.4.5)
eslint: 8.57.1
eslint-import-resolver-node: 0.3.9
eslint-import-resolver-typescript: 3.6.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint-plugin-import@2.29.1)(eslint@8.57.1)
transitivePeerDependencies:
- supports-color
eslint-module-utils@2.8.1(@typescript-eslint/parser@8.54.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.1):
dependencies:
debug: 3.2.7(supports-color@8.1.1)
optionalDependencies:
'@typescript-eslint/parser': 8.54.0(eslint@8.57.1)(typescript@5.4.5)
eslint: 8.57.1
eslint-import-resolver-node: 0.3.9
eslint-import-resolver-typescript: 3.6.1(@typescript-eslint/parser@8.54.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint-plugin-import@2.29.1)(eslint@8.57.1)
transitivePeerDependencies:
- supports-color
@@ -14073,7 +14232,7 @@ snapshots:
- supports-color
- ts-jest
eslint-plugin-import@2.29.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.1):
eslint-plugin-import@2.29.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint@8.57.1):
dependencies:
array-includes: 3.1.8
array.prototype.findlastindex: 1.2.5
@@ -14083,7 +14242,7 @@ snapshots:
doctrine: 2.1.0
eslint: 8.57.1
eslint-import-resolver-node: 0.3.9
eslint-module-utils: 2.8.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.1)
eslint-module-utils: 2.8.1(@typescript-eslint/parser@7.18.0(eslint@8.57.1)(typescript@5.4.5))(eslint-import-resolver-node@0.3.9)(eslint@8.57.1)
hasown: 2.0.2
is-core-module: 2.16.1
is-glob: 4.0.3
@@ -14162,6 +14321,8 @@ snapshots:
eslint-visitor-keys@3.4.3: {}
eslint-visitor-keys@4.2.1: {}
eslint@8.57.1:
dependencies:
'@eslint-community/eslint-utils': 4.9.1(eslint@8.57.1)
@@ -14700,7 +14861,7 @@ snapshots:
dependencies:
foreground-child: 3.2.1
jackspeak: 2.3.6
minimatch: 9.0.5
minimatch: 9.0.4
minipass: 7.1.2
path-scurry: 1.11.1
@@ -14708,7 +14869,7 @@ snapshots:
dependencies:
foreground-child: 3.2.1
jackspeak: 3.4.3
minimatch: 9.0.5
minimatch: 9.0.4
minipass: 7.1.2
package-json-from-dist: 1.0.1
path-scurry: 1.11.1
@@ -14872,17 +15033,17 @@ snapshots:
htmlparser2: 8.0.2
selderee: 0.11.0
htmlparser2@5.0.1:
htmlparser2@4.1.0:
dependencies:
domelementtype: 2.3.0
domhandler: 3.3.0
domutils: 2.8.0
entities: 2.2.0
htmlparser2@6.1.0:
htmlparser2@5.0.1:
dependencies:
domelementtype: 2.3.0
domhandler: 4.3.1
domhandler: 3.3.0
domutils: 2.8.0
entities: 2.2.0
@@ -14999,6 +15160,8 @@ snapshots:
ignore@5.3.2: {}
ignore@7.0.5: {}
image-size@1.2.1:
dependencies:
queue: 6.0.2
@@ -15347,6 +15510,9 @@ snapshots:
merge-stream: 2.0.0
supports-color: 8.1.1
jiti@1.21.6:
optional: true
jiti@1.21.7: {}
joi@17.13.3:
@@ -15481,13 +15647,13 @@ snapshots:
transitivePeerDependencies:
- encoding
juice@8.1.0(encoding@0.1.13):
juice@7.0.0(encoding@0.1.13):
dependencies:
cheerio: 1.0.0-rc.10
commander: 6.2.1
cheerio: 1.0.0-rc.12
commander: 5.1.0
mensch: 0.3.4
slick: 1.12.2
web-resource-inliner: 6.0.1(encoding@0.1.13)
web-resource-inliner: 5.0.0(encoding@0.1.13)
transitivePeerDependencies:
- encoding
@@ -16243,6 +16409,10 @@ snapshots:
dependencies:
brace-expansion: 2.0.2
minimatch@9.0.4:
dependencies:
brace-expansion: 2.0.2
minimatch@9.0.5:
dependencies:
brace-expansion: 2.0.2
@@ -16730,17 +16900,11 @@ snapshots:
parse-passwd@1.0.0: {}
parse5-htmlparser2-tree-adapter@6.0.1:
dependencies:
parse5: 6.0.1
parse5-htmlparser2-tree-adapter@7.0.0:
dependencies:
domhandler: 5.0.3
parse5: 7.1.2
parse5@6.0.1: {}
parse5@7.1.2:
dependencies:
entities: 4.5.0
@@ -18392,6 +18556,10 @@ snapshots:
dependencies:
typescript: 5.4.5
ts-api-utils@2.4.0(typescript@5.4.5):
dependencies:
typescript: 5.4.5
ts-interface-checker@0.1.13: {}
ts-node@10.9.2(@swc/core@1.6.5(@swc/helpers@0.5.11))(@types/node@20.5.1)(typescript@5.4.5):
@@ -18767,6 +18935,17 @@ snapshots:
transitivePeerDependencies:
- supports-color
web-resource-inliner@5.0.0(encoding@0.1.13):
dependencies:
ansi-colors: 4.1.3
escape-goat: 3.0.0
htmlparser2: 4.1.0
mime: 2.6.0
node-fetch: 2.7.0(encoding@0.1.13)
valid-data-url: 3.0.1
transitivePeerDependencies:
- encoding
web-resource-inliner@6.0.1(encoding@0.1.13):
dependencies:
ansi-colors: 4.1.3

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.9 KiB

After

Width:  |  Height:  |  Size: 17 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 8.0 KiB

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 24 KiB

After

Width:  |  Height:  |  Size: 60 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 21 KiB

After

Width:  |  Height:  |  Size: 50 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 25 KiB

After

Width:  |  Height:  |  Size: 36 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 14 KiB

After

Width:  |  Height:  |  Size: 13 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 27 KiB

After

Width:  |  Height:  |  Size: 38 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 38 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 27 KiB

After

Width:  |  Height:  |  Size: 37 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 30 KiB

After

Width:  |  Height:  |  Size: 41 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 32 KiB

After

Width:  |  Height:  |  Size: 43 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 43 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 17 KiB

After

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 44 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 31 KiB

After

Width:  |  Height:  |  Size: 44 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 34 KiB

After

Width:  |  Height:  |  Size: 47 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 50 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 36 KiB

After

Width:  |  Height:  |  Size: 49 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 37 KiB

After

Width:  |  Height:  |  Size: 51 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 24 KiB

After

Width:  |  Height:  |  Size: 19 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 35 KiB

After

Width:  |  Height:  |  Size: 42 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 49 KiB

After

Width:  |  Height:  |  Size: 65 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 38 KiB

After

Width:  |  Height:  |  Size: 45 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 34 KiB

After

Width:  |  Height:  |  Size: 34 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 40 KiB

After

Width:  |  Height:  |  Size: 47 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 42 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 47 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 43 KiB

After

Width:  |  Height:  |  Size: 48 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 35 KiB

After

Width:  |  Height:  |  Size: 31 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 38 KiB

After

Width:  |  Height:  |  Size: 33 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 33 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 42 KiB

After

Width:  |  Height:  |  Size: 35 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 55 KiB

After

Width:  |  Height:  |  Size: 62 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 44 KiB

After

Width:  |  Height:  |  Size: 37 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 37 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 10 KiB

After

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 12 KiB

After

Width:  |  Height:  |  Size: 20 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 16 KiB

After

Width:  |  Height:  |  Size: 24 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.0 KiB

After

Width:  |  Height:  |  Size: 12 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.0 KiB

After

Width:  |  Height:  |  Size: 8.5 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 774 B

After

Width:  |  Height:  |  Size: 821 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.9 KiB

After

Width:  |  Height:  |  Size: 2.1 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 15 KiB

After

Width:  |  Height:  |  Size: 15 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 9.3 KiB

After

Width:  |  Height:  |  Size: 61 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.1 KiB

After

Width:  |  Height:  |  Size: 53 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.0 KiB

After

Width:  |  Height:  |  Size: 53 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

After

Width:  |  Height:  |  Size: 13 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 6.0 KiB

After

Width:  |  Height:  |  Size: 25 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 5.9 KiB

After

Width:  |  Height:  |  Size: 25 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 1.6 KiB

After

Width:  |  Height:  |  Size: 22 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.7 KiB

After

Width:  |  Height:  |  Size: 7.2 KiB

BIN
public/os_logo_square.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 193 KiB

After

Width:  |  Height:  |  Size: 137 KiB

View File

@@ -3,7 +3,7 @@
// previously cached resources to be updated from the network.
// This variable is intentionally declared and unused.
// eslint-disable-next-line @typescript-eslint/no-unused-vars
const OFFLINE_VERSION = 5;
const OFFLINE_VERSION = 4;
const CACHE_NAME = 'offline';
// Customize this with a different URL if needed.
const OFFLINE_URL = '/offline.html';

View File

@@ -38,8 +38,8 @@ tags:
description: Endpoints related to getting service (Radarr/Sonarr) details.
- name: watchlist
description: Collection of media to watch later
- name: blocklist
description: Blocklisted media from discovery page.
- name: blacklist
description: Blacklisted media from discovery page.
servers:
- url: '{server}/api/v1'
variables:
@@ -48,7 +48,7 @@ servers:
components:
schemas:
Blocklist:
Blacklist:
type: object
properties:
tmdbId:
@@ -4529,123 +4529,12 @@ paths:
restricted:
type: boolean
example: false
/blocklist:
get:
summary: Returns blocklisted items
description: Returns list of all blocklisted media
tags:
- blocklist
parameters:
- in: query
name: take
schema:
type: number
nullable: true
example: 25
- in: query
name: skip
schema:
type: number
nullable: true
example: 0
- in: query
name: search
schema:
type: string
nullable: true
example: dune
- in: query
name: filter
schema:
type: string
enum: [all, manual, blocklistedTags]
default: manual
responses:
'200':
description: Blocklisted items returned
content:
application/json:
schema:
type: object
properties:
pageInfo:
$ref: '#/components/schemas/PageInfo'
results:
type: array
items:
type: object
properties:
user:
$ref: '#/components/schemas/User'
createdAt:
type: string
example: 2024-04-21T01:55:44.000Z
id:
type: number
example: 1
mediaType:
type: string
example: movie
title:
type: string
example: Dune
tmdbId:
type: number
example: 438631
post:
summary: Add media to blocklist
tags:
- blocklist
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/Blocklist'
responses:
'201':
description: Item succesfully blocklisted
'412':
description: Item has already been blocklisted
/blocklist/{tmdbId}:
get:
summary: Get media from blocklist
tags:
- blocklist
parameters:
- in: path
name: tmdbId
description: tmdbId ID
required: true
example: '1'
schema:
type: string
responses:
'200':
description: Blocklist details in JSON
delete:
summary: Remove media from blocklist
tags:
- blocklist
parameters:
- in: path
name: tmdbId
description: tmdbId ID
required: true
example: '1'
schema:
type: string
responses:
'204':
description: Succesfully removed media item
/blacklist:
get:
summary: Returns blocklisted items
description: |
**DEPRECATED**: Use `/blocklist` instead. This endpoint will be deprecated soon.
deprecated: true
summary: Returns blacklisted items
description: Returns list of all blacklisted media
tags:
- blocklist
- settings
parameters:
- in: query
name: take
@@ -4669,11 +4558,11 @@ paths:
name: filter
schema:
type: string
enum: [all, manual, blocklistedTags]
enum: [all, manual, blacklistedTags]
default: manual
responses:
'200':
description: Blocklisted items returned
description: Blacklisted items returned
content:
application/json:
schema:
@@ -4704,31 +4593,25 @@ paths:
type: number
example: 438631
post:
summary: Add media to blocklist
description: |
**DEPRECATED**: Use `/blocklist` instead. This endpoint will be deprecated soon.
deprecated: true
summary: Add media to blacklist
tags:
- blocklist
- blacklist
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/Blocklist'
$ref: '#/components/schemas/Blacklist'
responses:
'201':
description: Item succesfully blocklisted
description: Item succesfully blacklisted
'412':
description: Item has already been blocklisted
description: Item has already been blacklisted
/blacklist/{tmdbId}:
get:
summary: Get media from blocklist
description: |
**DEPRECATED**: Use `/blocklist/{tmdbId}` instead. This endpoint will be deprecated soon.
deprecated: true
summary: Get media from blacklist
tags:
- blocklist
- blacklist
parameters:
- in: path
name: tmdbId
@@ -4739,14 +4622,11 @@ paths:
type: string
responses:
'200':
description: Blocklist details in JSON
description: Blacklist details in JSON
delete:
summary: Remove media from blocklist
description: |
**DEPRECATED**: Use `/blocklist/{tmdbId}` instead. This endpoint will be deprecated soon.
deprecated: true
summary: Remove media from blacklist
tags:
- blocklist
- blacklist
parameters:
- in: path
name: tmdbId

View File

@@ -92,7 +92,7 @@ class ServarrBase<QueueItemAppendT> extends ExternalAPI {
apiKey,
cacheName,
apiName,
timeout = 10000,
timeout = 5000,
}: {
url: string;
apiKey: string;

View File

@@ -17,6 +17,6 @@ export enum MediaStatus {
PROCESSING,
PARTIALLY_AVAILABLE,
AVAILABLE,
BLOCKLISTED,
BLACKLISTED,
DELETED,
}

View File

@@ -2,7 +2,7 @@ import { MediaStatus, type MediaType } from '@server/constants/media';
import dataSource from '@server/datasource';
import Media from '@server/entity/Media';
import { User } from '@server/entity/User';
import type { BlocklistItem } from '@server/interfaces/api/blocklistInterfaces';
import type { BlacklistItem } from '@server/interfaces/api/blacklistInterfaces';
import { DbAwareColumn } from '@server/utils/DbColumnHelper';
import type { EntityManager } from 'typeorm';
import {
@@ -19,7 +19,7 @@ import type { ZodNumber, ZodOptional, ZodString } from 'zod';
@Entity()
@Unique(['tmdbId'])
export class Blocklist implements BlocklistItem {
export class Blacklist implements BlacklistItem {
@PrimaryGeneratedColumn()
public id: number;
@@ -36,68 +36,67 @@ export class Blocklist implements BlocklistItem {
@ManyToOne(() => User, (user) => user.id, {
eager: true,
})
@Index()
user?: User;
@OneToOne(() => Media, (media) => media.blocklist, {
@OneToOne(() => Media, (media) => media.blacklist, {
onDelete: 'CASCADE',
})
@JoinColumn()
public media: Media;
@Column({ nullable: true, type: 'varchar' })
public blocklistedTags?: string;
public blacklistedTags?: string;
@DbAwareColumn({ type: 'datetime', default: () => 'CURRENT_TIMESTAMP' })
public createdAt: Date;
constructor(init?: Partial<Blocklist>) {
constructor(init?: Partial<Blacklist>) {
Object.assign(this, init);
}
public static async addToBlocklist(
public static async addToBlacklist(
{
blocklistRequest,
blacklistRequest,
}: {
blocklistRequest: {
blacklistRequest: {
mediaType: MediaType;
title?: ZodOptional<ZodString>['_output'];
tmdbId: ZodNumber['_output'];
blocklistedTags?: string;
blacklistedTags?: string;
};
},
entityManager?: EntityManager
): Promise<void> {
const em = entityManager ?? dataSource;
const blocklist = new this({
...blocklistRequest,
const blacklist = new this({
...blacklistRequest,
});
const mediaRepository = em.getRepository(Media);
let media = await mediaRepository.findOne({
where: {
tmdbId: blocklistRequest.tmdbId,
tmdbId: blacklistRequest.tmdbId,
},
});
const blocklistRepository = em.getRepository(this);
const blacklistRepository = em.getRepository(this);
await blocklistRepository.save(blocklist);
await blacklistRepository.save(blacklist);
if (!media) {
media = new Media({
tmdbId: blocklistRequest.tmdbId,
status: MediaStatus.BLOCKLISTED,
status4k: MediaStatus.BLOCKLISTED,
mediaType: blocklistRequest.mediaType,
blocklist: Promise.resolve(blocklist),
tmdbId: blacklistRequest.tmdbId,
status: MediaStatus.BLACKLISTED,
status4k: MediaStatus.BLACKLISTED,
mediaType: blacklistRequest.mediaType,
blacklist: Promise.resolve(blacklist),
});
await mediaRepository.save(media);
} else {
media.blocklist = Promise.resolve(blocklist);
media.status = MediaStatus.BLOCKLISTED;
media.status4k = MediaStatus.BLOCKLISTED;
media.blacklist = Promise.resolve(blacklist);
media.status = MediaStatus.BLACKLISTED;
media.status4k = MediaStatus.BLACKLISTED;
await mediaRepository.save(media);
}

View File

@@ -5,7 +5,6 @@ import {
AfterLoad,
Column,
Entity,
Index,
ManyToOne,
OneToMany,
PrimaryGeneratedColumn,
@@ -20,7 +19,6 @@ class Issue {
public id: number;
@Column({ type: 'int' })
@Index()
public issueType: IssueType;
@Column({ type: 'int', default: IssueStatus.OPEN })
@@ -36,14 +34,12 @@ class Issue {
eager: true,
onDelete: 'CASCADE',
})
@Index()
public media: Media;
@ManyToOne(() => User, (user) => user.createdIssues, {
eager: true,
onDelete: 'CASCADE',
})
@Index()
public createdBy: User;
@ManyToOne(() => User, {
@@ -51,7 +47,6 @@ class Issue {
onDelete: 'CASCADE',
nullable: true,
})
@Index()
public modifiedBy?: User;
@OneToMany(() => IssueComment, (comment) => comment.issue, {

Some files were not shown because too many files have changed in this diff Show More