From be64e1159981a78e9ee43aa6d74b996fd334ec9a Mon Sep 17 00:00:00 2001 From: Sam Chau Date: Tue, 27 Jan 2026 22:33:36 +1030 Subject: [PATCH] docs: for add schema and sample data for testing --- docs/0.schema.sql | 482 + docs/1.initial.sql | 25029 +++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 25511 insertions(+) create mode 100644 docs/0.schema.sql create mode 100644 docs/1.initial.sql diff --git a/docs/0.schema.sql b/docs/0.schema.sql new file mode 100644 index 0000000..7f9f757 --- /dev/null +++ b/docs/0.schema.sql @@ -0,0 +1,482 @@ +-- ============================================================================ +-- PCD SCHEMA v1 +-- ============================================================================ + +-- ============================================================================ +-- CORE ENTITY TABLES (Independent - No Foreign Key Dependencies) +-- ============================================================================ +-- These tables form the foundation and can be populated in any order + +-- Tags are reusable labels that can be applied to multiple entity types +CREATE TABLE tags ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + name VARCHAR(50) UNIQUE NOT NULL, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP +); + +-- Languages used for profile configuration and custom format conditions +CREATE TABLE languages ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + name VARCHAR(30) UNIQUE NOT NULL, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP +); + +-- Regular expressions used in custom format pattern conditions +CREATE TABLE regular_expressions ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + name VARCHAR(100) UNIQUE NOT NULL, + pattern TEXT NOT NULL, + regex101_id VARCHAR(50), -- Optional link to regex101.com for testing + description TEXT, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP +); + +-- Individual quality definitions (e.g., "1080p Bluray", "2160p REMUX") +CREATE TABLE qualities ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + name VARCHAR(100) UNIQUE NOT NULL, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP +); + +-- Maps Profilarr canonical qualities to arr-specific API names +-- Absence of a row means the quality doesn't exist for that arr +-- Uses stable key: quality_name +CREATE TABLE quality_api_mappings ( + quality_name VARCHAR(100) NOT NULL, + arr_type VARCHAR(20) NOT NULL, -- 'radarr', 'sonarr' + api_name VARCHAR(100) NOT NULL, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + PRIMARY KEY (quality_name, arr_type), + FOREIGN KEY (quality_name) REFERENCES qualities(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Custom formats define patterns and conditions for media matching +CREATE TABLE custom_formats ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + name VARCHAR(100) UNIQUE NOT NULL, + description TEXT, + include_in_rename INTEGER NOT NULL DEFAULT 0, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP +); + +-- ============================================================================ +-- DEPENDENT ENTITY TABLES (Depend on Core Entities) +-- ============================================================================ + +-- Quality profiles define complete media acquisition strategies +CREATE TABLE quality_profiles ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + name VARCHAR(100) UNIQUE NOT NULL, + description TEXT, + upgrades_allowed INTEGER NOT NULL DEFAULT 1, + minimum_custom_format_score INTEGER NOT NULL DEFAULT 0, + upgrade_until_score INTEGER NOT NULL DEFAULT 0, + upgrade_score_increment INTEGER NOT NULL DEFAULT 1 CHECK (upgrade_score_increment > 0), + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP +); + +-- Quality groups combine multiple qualities treated as equivalent +-- Each group is specific to a quality profile (profiles do not share groups) +-- Uses stable key: quality_profile_name instead of quality_profile_id +CREATE TABLE quality_groups ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + quality_profile_name VARCHAR(100) NOT NULL, + name VARCHAR(100) NOT NULL, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + UNIQUE(quality_profile_name, name), + FOREIGN KEY (quality_profile_name) REFERENCES quality_profiles(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Conditions define the matching logic for custom formats +-- Each condition has a type and corresponding data in a type-specific table +-- Uses custom_format_name (stable) instead of custom_format_id (autoincrement) +CREATE TABLE custom_format_conditions ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + custom_format_name VARCHAR(100) NOT NULL, + name VARCHAR(100) NOT NULL, + type VARCHAR(50) NOT NULL, + arr_type VARCHAR(20) NOT NULL DEFAULT 'all', -- 'radarr', 'sonarr', 'all' + negate INTEGER NOT NULL DEFAULT 0, + required INTEGER NOT NULL DEFAULT 0, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + UNIQUE(custom_format_name, name), + FOREIGN KEY (custom_format_name) REFERENCES custom_formats(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- ============================================================================ +-- JUNCTION TABLES (Many-to-Many Relationships) +-- ============================================================================ + +-- Link regular expressions to tags +-- Uses stable keys: regular_expression_name and tag_name +CREATE TABLE regular_expression_tags ( + regular_expression_name VARCHAR(100) NOT NULL, + tag_name VARCHAR(50) NOT NULL, + PRIMARY KEY (regular_expression_name, tag_name), + FOREIGN KEY (regular_expression_name) REFERENCES regular_expressions(name) ON DELETE CASCADE ON UPDATE CASCADE, + FOREIGN KEY (tag_name) REFERENCES tags(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Link custom formats to tags +-- Uses stable keys: custom_format_name and tag_name +CREATE TABLE custom_format_tags ( + custom_format_name VARCHAR(100) NOT NULL, + tag_name VARCHAR(50) NOT NULL, + PRIMARY KEY (custom_format_name, tag_name), + FOREIGN KEY (custom_format_name) REFERENCES custom_formats(name) ON DELETE CASCADE ON UPDATE CASCADE, + FOREIGN KEY (tag_name) REFERENCES tags(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Link quality profiles to tags +-- Uses stable keys: quality_profile_name and tag_name +CREATE TABLE quality_profile_tags ( + quality_profile_name VARCHAR(100) NOT NULL, + tag_name VARCHAR(50) NOT NULL, + PRIMARY KEY (quality_profile_name, tag_name), + FOREIGN KEY (quality_profile_name) REFERENCES quality_profiles(name) ON DELETE CASCADE ON UPDATE CASCADE, + FOREIGN KEY (tag_name) REFERENCES tags(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Link quality profiles to languages with type modifiers +-- Type can be: 'must', 'only', 'not', or 'simple' (default language preference) +-- Uses stable keys: quality_profile_name and language_name +CREATE TABLE quality_profile_languages ( + quality_profile_name VARCHAR(100) NOT NULL, + language_name VARCHAR(30) NOT NULL, + type VARCHAR(20) NOT NULL DEFAULT 'simple', -- 'must', 'only', 'not', 'simple' + PRIMARY KEY (quality_profile_name, language_name), + FOREIGN KEY (quality_profile_name) REFERENCES quality_profiles(name) ON DELETE CASCADE ON UPDATE CASCADE, + FOREIGN KEY (language_name) REFERENCES languages(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Define which qualities belong to which quality groups +-- All qualities in a group are treated as equivalent +-- Uses stable keys: (quality_profile_name, quality_group_name) and quality_name +CREATE TABLE quality_group_members ( + quality_profile_name VARCHAR(100) NOT NULL, + quality_group_name VARCHAR(100) NOT NULL, + quality_name VARCHAR(100) NOT NULL, + PRIMARY KEY (quality_profile_name, quality_group_name, quality_name), + FOREIGN KEY (quality_profile_name, quality_group_name) REFERENCES quality_groups(quality_profile_name, name) ON DELETE CASCADE ON UPDATE CASCADE, + FOREIGN KEY (quality_name) REFERENCES qualities(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Define the quality list for a profile (ordered by position) +-- Each item references either a single quality OR a quality group (never both) +-- Every quality must be represented (either directly or in a group) +-- The enabled flag controls whether the quality/group is active +-- Uses stable keys: quality_profile_name, quality_name, quality_group_name +CREATE TABLE quality_profile_qualities ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + quality_profile_name VARCHAR(100) NOT NULL, + quality_name VARCHAR(100), -- References a single quality by name + quality_group_name VARCHAR(100), -- OR references a quality group by name (within this profile) + position INTEGER NOT NULL, -- Display order in the profile + enabled INTEGER NOT NULL DEFAULT 1, -- Whether this quality/group is enabled + upgrade_until INTEGER NOT NULL DEFAULT 0, -- Stop upgrading at this quality + CHECK ((quality_name IS NOT NULL AND quality_group_name IS NULL) OR (quality_name IS NULL AND quality_group_name IS NOT NULL)), + FOREIGN KEY (quality_profile_name) REFERENCES quality_profiles(name) ON DELETE CASCADE ON UPDATE CASCADE, + FOREIGN KEY (quality_name) REFERENCES qualities(name) ON DELETE CASCADE ON UPDATE CASCADE, + FOREIGN KEY (quality_profile_name, quality_group_name) REFERENCES quality_groups(quality_profile_name, name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Assign custom formats to quality profiles with scoring +-- Scores determine upgrade priority and filtering behavior +-- Uses stable keys: quality_profile_name and custom_format_name +CREATE TABLE quality_profile_custom_formats ( + quality_profile_name VARCHAR(100) NOT NULL, + custom_format_name VARCHAR(100) NOT NULL, + arr_type VARCHAR(20) NOT NULL, -- 'radarr', 'sonarr', 'all' + score INTEGER NOT NULL, + PRIMARY KEY (quality_profile_name, custom_format_name, arr_type), + FOREIGN KEY (quality_profile_name) REFERENCES quality_profiles(name) ON DELETE CASCADE ON UPDATE CASCADE, + FOREIGN KEY (custom_format_name) REFERENCES custom_formats(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- ============================================================================ +-- CUSTOM FORMAT CONDITION TYPE TABLES +-- ============================================================================ +-- Each condition type has a dedicated table storing type-specific data +-- A condition_id should only appear in ONE of these tables, matching its type + +-- Pattern-based conditions (release_title, release_group, edition) +-- Each pattern condition references exactly one regular expression +-- Uses stable keys: (custom_format_name, condition_name) and regular_expression_name +CREATE TABLE condition_patterns ( + custom_format_name VARCHAR(100) NOT NULL, + condition_name VARCHAR(100) NOT NULL, + regular_expression_name VARCHAR(100) NOT NULL, + PRIMARY KEY (custom_format_name, condition_name), + FOREIGN KEY (custom_format_name, condition_name) REFERENCES custom_format_conditions(custom_format_name, name) ON DELETE CASCADE ON UPDATE CASCADE, + FOREIGN KEY (regular_expression_name) REFERENCES regular_expressions(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Language-based conditions +-- Uses stable keys: (custom_format_name, condition_name) and language_name +CREATE TABLE condition_languages ( + custom_format_name VARCHAR(100) NOT NULL, + condition_name VARCHAR(100) NOT NULL, + language_name VARCHAR(30) NOT NULL, + except_language INTEGER NOT NULL DEFAULT 0, -- Match everything EXCEPT this language + PRIMARY KEY (custom_format_name, condition_name), + FOREIGN KEY (custom_format_name, condition_name) REFERENCES custom_format_conditions(custom_format_name, name) ON DELETE CASCADE ON UPDATE CASCADE, + FOREIGN KEY (language_name) REFERENCES languages(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Indexer flag conditions (e.g., "Scene", "Freeleech") +-- Uses stable key: (custom_format_name, condition_name) +CREATE TABLE condition_indexer_flags ( + custom_format_name VARCHAR(100) NOT NULL, + condition_name VARCHAR(100) NOT NULL, + flag VARCHAR(100) NOT NULL, + PRIMARY KEY (custom_format_name, condition_name), + FOREIGN KEY (custom_format_name, condition_name) REFERENCES custom_format_conditions(custom_format_name, name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Source conditions (e.g., "Bluray", "Web", "DVD") +-- Uses stable key: (custom_format_name, condition_name) +CREATE TABLE condition_sources ( + custom_format_name VARCHAR(100) NOT NULL, + condition_name VARCHAR(100) NOT NULL, + source VARCHAR(100) NOT NULL, + PRIMARY KEY (custom_format_name, condition_name), + FOREIGN KEY (custom_format_name, condition_name) REFERENCES custom_format_conditions(custom_format_name, name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Resolution conditions (e.g., "1080p", "2160p") +-- Uses stable key: (custom_format_name, condition_name) +CREATE TABLE condition_resolutions ( + custom_format_name VARCHAR(100) NOT NULL, + condition_name VARCHAR(100) NOT NULL, + resolution VARCHAR(100) NOT NULL, + PRIMARY KEY (custom_format_name, condition_name), + FOREIGN KEY (custom_format_name, condition_name) REFERENCES custom_format_conditions(custom_format_name, name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Quality modifier conditions (e.g., "REMUX", "WEBDL") +-- Uses stable key: (custom_format_name, condition_name) +CREATE TABLE condition_quality_modifiers ( + custom_format_name VARCHAR(100) NOT NULL, + condition_name VARCHAR(100) NOT NULL, + quality_modifier VARCHAR(100) NOT NULL, + PRIMARY KEY (custom_format_name, condition_name), + FOREIGN KEY (custom_format_name, condition_name) REFERENCES custom_format_conditions(custom_format_name, name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Size-based conditions with min/max bounds in bytes +-- Uses stable key: (custom_format_name, condition_name) +CREATE TABLE condition_sizes ( + custom_format_name VARCHAR(100) NOT NULL, + condition_name VARCHAR(100) NOT NULL, + min_bytes INTEGER, -- Null means no minimum + max_bytes INTEGER, -- Null means no maximum + PRIMARY KEY (custom_format_name, condition_name), + FOREIGN KEY (custom_format_name, condition_name) REFERENCES custom_format_conditions(custom_format_name, name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Release type conditions (e.g., "Movie", "Episode") +-- Uses stable key: (custom_format_name, condition_name) +CREATE TABLE condition_release_types ( + custom_format_name VARCHAR(100) NOT NULL, + condition_name VARCHAR(100) NOT NULL, + release_type VARCHAR(100) NOT NULL, + PRIMARY KEY (custom_format_name, condition_name), + FOREIGN KEY (custom_format_name, condition_name) REFERENCES custom_format_conditions(custom_format_name, name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Year-based conditions with min/max bounds +-- Uses stable key: (custom_format_name, condition_name) +CREATE TABLE condition_years ( + custom_format_name VARCHAR(100) NOT NULL, + condition_name VARCHAR(100) NOT NULL, + min_year INTEGER, -- Null means no minimum + max_year INTEGER, -- Null means no maximum + PRIMARY KEY (custom_format_name, condition_name), + FOREIGN KEY (custom_format_name, condition_name) REFERENCES custom_format_conditions(custom_format_name, name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- ============================================================================ +-- CUSTOM FORMAT TESTING +-- ============================================================================ + +-- Test cases for validating custom format matching logic +-- Each test belongs to a custom format and specifies whether a title should match +-- Uses stable key: custom_format_name +CREATE TABLE custom_format_tests ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + custom_format_name VARCHAR(100) NOT NULL, + title TEXT NOT NULL, -- Release title to test against + type VARCHAR(20) NOT NULL, -- 'movie' or 'series' + should_match INTEGER NOT NULL, -- 1 = should match, 0 = should not match + description TEXT, -- Why this test exists / edge case covered + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + UNIQUE(custom_format_name, title, type), + FOREIGN KEY (custom_format_name) REFERENCES custom_formats(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- ============================================================================ +-- MEDIA MANAGEMENT TABLES +-- ============================================================================ + +-- Radarr quality size definitions +-- Uses stable key: (name, quality_name) +CREATE TABLE radarr_quality_definitions ( + name VARCHAR(100) NOT NULL, + quality_name VARCHAR(100) NOT NULL, + min_size INTEGER NOT NULL DEFAULT 0, + max_size INTEGER NOT NULL, + preferred_size INTEGER NOT NULL, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + PRIMARY KEY (name, quality_name), + FOREIGN KEY (quality_name) REFERENCES qualities(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Sonarr quality size definitions +-- Uses stable key: (name, quality_name) +CREATE TABLE sonarr_quality_definitions ( + name VARCHAR(100) NOT NULL, + quality_name VARCHAR(100) NOT NULL, + min_size INTEGER NOT NULL DEFAULT 0, + max_size INTEGER NOT NULL, + preferred_size INTEGER NOT NULL, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + PRIMARY KEY (name, quality_name), + FOREIGN KEY (quality_name) REFERENCES qualities(name) ON DELETE CASCADE ON UPDATE CASCADE +); + +-- Radarr naming configuration +CREATE TABLE radarr_naming ( + name VARCHAR(100) PRIMARY KEY, + rename INTEGER NOT NULL DEFAULT 1, + movie_format TEXT NOT NULL, + movie_folder_format TEXT NOT NULL, + replace_illegal_characters INTEGER NOT NULL DEFAULT 0, + colon_replacement_format VARCHAR(20) NOT NULL DEFAULT 'smart', + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP +); + +-- Sonarr naming configuration +CREATE TABLE sonarr_naming ( + name VARCHAR(100) PRIMARY KEY, + rename INTEGER NOT NULL DEFAULT 1, + standard_episode_format TEXT NOT NULL, + daily_episode_format TEXT NOT NULL, + anime_episode_format TEXT NOT NULL, + series_folder_format TEXT NOT NULL, + season_folder_format TEXT NOT NULL, + replace_illegal_characters INTEGER NOT NULL DEFAULT 0, + colon_replacement_format INTEGER NOT NULL DEFAULT 4, + custom_colon_replacement_format TEXT, + multi_episode_style INTEGER NOT NULL DEFAULT 5, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP +); + +-- Radarr general media settings +CREATE TABLE radarr_media_settings ( + name VARCHAR(100) PRIMARY KEY, + propers_repacks VARCHAR(50) NOT NULL DEFAULT 'doNotPrefer', + enable_media_info INTEGER NOT NULL DEFAULT 1, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP +); + +-- Sonarr general media settings +CREATE TABLE sonarr_media_settings ( + name VARCHAR(100) PRIMARY KEY, + propers_repacks VARCHAR(50) NOT NULL DEFAULT 'doNotPrefer', + enable_media_info INTEGER NOT NULL DEFAULT 1, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP +); + +-- ============================================================================ +-- DELAY PROFILES +-- ============================================================================ + +-- Delay profiles control download timing preferences +-- Note: Tags removed - Radarr/Sonarr only allows updating the default profile (id=1) +-- which must have empty tags. Only one delay profile can be synced per arr instance. +CREATE TABLE delay_profiles ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + name VARCHAR(100) UNIQUE NOT NULL, + preferred_protocol VARCHAR(20) NOT NULL CHECK ( + preferred_protocol IN ('prefer_usenet', 'prefer_torrent', 'only_usenet', 'only_torrent') + ), + usenet_delay INTEGER, -- minutes, NULL if only_torrent + torrent_delay INTEGER, -- minutes, NULL if only_usenet + bypass_if_highest_quality INTEGER NOT NULL DEFAULT 0, + bypass_if_above_custom_format_score INTEGER NOT NULL DEFAULT 0, + minimum_custom_format_score INTEGER, -- Required when bypass_if_above_custom_format_score = 1 + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + -- Enforce usenet_delay is NULL only when only_torrent + CHECK ( + (preferred_protocol = 'only_torrent' AND usenet_delay IS NULL) OR + (preferred_protocol != 'only_torrent' AND usenet_delay IS NOT NULL) + ), + -- Enforce torrent_delay is NULL only when only_usenet + CHECK ( + (preferred_protocol = 'only_usenet' AND torrent_delay IS NULL) OR + (preferred_protocol != 'only_usenet' AND torrent_delay IS NOT NULL) + ), + -- Enforce minimum_custom_format_score required when bypass enabled + CHECK ( + (bypass_if_above_custom_format_score = 0 AND minimum_custom_format_score IS NULL) OR + (bypass_if_above_custom_format_score = 1 AND minimum_custom_format_score IS NOT NULL) + ) +); + +-- ============================================================================ +-- QUALITY PROFILE TESTING +-- ============================================================================ + +-- Test entities (movies/series for quality profile testing) +CREATE TABLE test_entities ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + type TEXT NOT NULL CHECK (type IN ('movie', 'series')), + tmdb_id INTEGER NOT NULL, + title TEXT NOT NULL, + year INTEGER, + poster_path TEXT, + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + UNIQUE(type, tmdb_id) +); + +-- Test releases attached to entities +-- Uses composite FK (entity_type, entity_tmdb_id) for stable references across recompiles +CREATE TABLE test_releases ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + entity_type TEXT NOT NULL CHECK (entity_type IN ('movie', 'series')), + entity_tmdb_id INTEGER NOT NULL, + title TEXT NOT NULL, + size_bytes INTEGER, + languages TEXT NOT NULL DEFAULT '[]', + indexers TEXT NOT NULL DEFAULT '[]', + flags TEXT NOT NULL DEFAULT '[]', + created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + updated_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP, + FOREIGN KEY (entity_type, entity_tmdb_id) REFERENCES test_entities(type, tmdb_id) ON DELETE CASCADE +); + +CREATE INDEX idx_test_releases_entity ON test_releases(entity_type, entity_tmdb_id); + +-- ============================================================================ +-- INDEXES AND CONSTRAINTS +-- ============================================================================ + +-- Ensure only one quality item per profile can be marked as upgrade_until +CREATE UNIQUE INDEX idx_one_upgrade_until_per_profile +ON quality_profile_qualities(quality_profile_name) +WHERE upgrade_until = 1; diff --git a/docs/1.initial.sql b/docs/1.initial.sql new file mode 100644 index 0000000..497fb44 --- /dev/null +++ b/docs/1.initial.sql @@ -0,0 +1,25029 @@ +-- ============================================================================ +-- PCD 2.0 Initial Import +-- Generated by YAML to SQL Converter +-- Generated at: 2026-01-26T13:53:37.969Z +-- ============================================================================ + +-- ============================================================================ +-- CORE ENTITIES +-- ============================================================================ + +-- Tags + +INSERT INTO tags (name) VALUES ('1080p'); +INSERT INTO tags (name) VALUES ('2160p'); +INSERT INTO tags (name) VALUES ('480p'); +INSERT INTO tags (name) VALUES ('576p'); +INSERT INTO tags (name) VALUES ('720p'); +INSERT INTO tags (name) VALUES ('Anime'); +INSERT INTO tags (name) VALUES ('Aspect Ratio'); +INSERT INTO tags (name) VALUES ('Audio'); +INSERT INTO tags (name) VALUES ('Balanced'); +INSERT INTO tags (name) VALUES ('Balanced Focused'); +INSERT INTO tags (name) VALUES ('Banned'); +INSERT INTO tags (name) VALUES ('Bleeding Edge'); +INSERT INTO tags (name) VALUES ('Bluray'); +INSERT INTO tags (name) VALUES ('Channel'); +INSERT INTO tags (name) VALUES ('Codec'); +INSERT INTO tags (name) VALUES ('Colour Grade'); +INSERT INTO tags (name) VALUES ('Compact'); +INSERT INTO tags (name) VALUES ('Compact Focused'); +INSERT INTO tags (name) VALUES ('Container'); +INSERT INTO tags (name) VALUES ('Dolby'); +INSERT INTO tags (name) VALUES ('DVD'); +INSERT INTO tags (name) VALUES ('Edition'); +INSERT INTO tags (name) VALUES ('Efficient'); +INSERT INTO tags (name) VALUES ('Efficient Focused'); +INSERT INTO tags (name) VALUES ('Encoder'); +INSERT INTO tags (name) VALUES ('Enhancement'); +INSERT INTO tags (name) VALUES ('Enhancements'); +INSERT INTO tags (name) VALUES ('Flag'); +INSERT INTO tags (name) VALUES ('Golden Popcorn'); +INSERT INTO tags (name) VALUES ('GPPi'); +INSERT INTO tags (name) VALUES ('h264'); +INSERT INTO tags (name) VALUES ('h265'); +INSERT INTO tags (name) VALUES ('HDR'); +INSERT INTO tags (name) VALUES ('HDTV'); +INSERT INTO tags (name) VALUES ('HEVC'); +INSERT INTO tags (name) VALUES ('Language'); +INSERT INTO tags (name) VALUES ('Lossless'); +INSERT INTO tags (name) VALUES ('Lossless Audio'); +INSERT INTO tags (name) VALUES ('Lossy Audio'); +INSERT INTO tags (name) VALUES ('Movie'); +INSERT INTO tags (name) VALUES ('Preview'); +INSERT INTO tags (name) VALUES ('Quality'); +INSERT INTO tags (name) VALUES ('Quality Focused'); +INSERT INTO tags (name) VALUES ('Release Group'); +INSERT INTO tags (name) VALUES ('Release Group Tier'); +INSERT INTO tags (name) VALUES ('Remux'); +INSERT INTO tags (name) VALUES ('Remux Focused'); +INSERT INTO tags (name) VALUES ('Repack'); +INSERT INTO tags (name) VALUES ('SD'); +INSERT INTO tags (name) VALUES ('Source'); +INSERT INTO tags (name) VALUES ('Storage'); +INSERT INTO tags (name) VALUES ('Streaming Service'); +INSERT INTO tags (name) VALUES ('TV'); +INSERT INTO tags (name) VALUES ('WEB-DL'); +INSERT INTO tags (name) VALUES ('x264'); +INSERT INTO tags (name) VALUES ('x265'); + +-- Languages +-- (Provided by 1.languages.sql - no inserts needed) + +-- Regular Expressions + +INSERT INTO regular_expressions (name, pattern, description) VALUES ('126811', '(?<=^|[\s.-])126811\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('3D', '(?<=\b[12]\d{3}\b).*\b((bluray|bd)?3d|sbs|half[ .-]ou|half[ .-]sbs)\b', 'Matches terms related to 3D video formats: +- `bluray3d` or `bd3d` (optional `bluray` or `bd` followed by `3d`). +- `sbs` (side-by-side). +- `half ou` or `half sbs` with space (` `), dot (`.`), or hyphen (`-`) as separators.'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('3L', '(?<=^|[\s.-])3L\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('4K4U', '(?<=^|[\s.-])4K4U\b', 'Matches the release group `4K4U` only if it is: + +- Preceded by the start of the string (`^`), a whitespace character (`\s`), a period (`.`), or a hyphen (`-`). +- Followed by a word boundary (`\b`), ensuring it ends cleanly without being part of a longer word. '); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('4KDVS', '(?<=^|[\s.-])4KDVS\b', 'Matches "4KDVS" when preceded by whitespace, a hyphen or dot'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('5.1 Surround', '\D5\.1\D', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('7.1 Surround', '\D7\.1\D', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('9volt', '(?<=^|[\s.-])9volt\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('AAC', '\bAAC(\b|\d)', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('ABM', '(?<=^|[\s.-])ABM\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('AC', '(?<=^|[\s.-])AC\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('ADE', '(?<=^|[\s.-])ADE\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('AI Movies', '(?<=\b[12]\d{3}\b).*(\b(AI)\b)', 'Matches AI Upscales'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('AI TV', '(?<=\bS\d+\b).*(\b(AI)\b)', 'Matches AI Upscales'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('AJP69', '(?<=^|[\s.-])AJP69\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Almighty', '(?<=^|[\s.-])Almighty\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Amazon Prime', '\b(?:AMZN|(?:AMAZON)(?=\s*.(?:WEB-?DL|WEBRIP)))\b', 'Amazon Prime Video, or simply Prime Video, is an American subscription video on-demand over-the-top streaming and rental service of Amazon offered both as a stand-alone service and as part of Amazon''s Prime subscription.'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('ANE', '(?<=^|[\s.-])ANE\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('AOC', '(?<=^|[\s.-])AOC\b', 'Banned for Excessive Audio Streams'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('AOmundson', '(?<=^|[\s.-])AOmundson\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('APEX', '(?<=^|[\s.-])APEX\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Apple TV+', '\b(ATVP|ATV|APTV|Apple TV\+)\s*\b', 'Apple TV+ is an American subscription OTT streaming service owned and operated by Apple Inc. Launched on November 1, 2019, it offers a selection of original production film and television series called Apple Originals.'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('ARCADE', '(?<=^|[\s.-])ARCADE\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Arid', '(?<=^|[\s.-])Arid\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('AROMA', '(?<=^|[\s.-])AROMA\b', 'Banned for Retagging'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Asakura', '(?<=^|[\s.-])Asakura\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('ATELiER', '(?<=^|[\s.-])ATELiER\b', 'Matches "ATELiER" when preceded by whitespace, a hyphen or dot'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Atmos', '\bATMOS|DDPA(\b|\d)', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Atmos (Missing)', '\bATMOS(\b|\d)', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('AV1', '\b(AV1)\b', 'AV1, or AOMedia Video 1, is a video coding format that compresses video files and streams while maintaining high quality.'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('AVC', '[xh][ ._-]?264|\bAVC(\b|\d)', 'An open source encoder that produces AVC videos. '); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('AViATOR', '(?<=^|[\s.-])AViATOR\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('B&W', '\d{4}.*?\bblack\b[\s.]*(?:and|\&|-|\/)?[\s.]*\bwhite\b|\bb\&?w\b', 'Black and White colour grading. This regex matches a 4-digit number (optionally surrounded by parentheses), followed by any amount of text, and then detects references to "black and white" in various formats. It supports `blackwhite` (no spaces), `black and white`, `black-white`, "`black & white`, `black/white`, as well as shorthand `BW` and `B&W`, while excluding invalid variations like `b w`, `b-w`, or `b/w`'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('b0mbardiers', '(?<=^|[\s.-])b0mbardiers\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Basic HDR Formats', '(?:(?<=^(?!.*\b(HLG|PQ|SDR)(\b|\d)).*?)HDR)|\b(dv(?![ .](HLG|SDR))|dovi|dolby[ .]?vision)\b', 'Matches Dolby Vision OR HDR10. Needed to better match UHD Blurays'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BBC iPlayer', '\b(iP)\b', 'BBC iPlayer is a video on demand service from the BBC. The service is available over-the-top on a wide range of devices, including mobile phones and tablets, personal computers and smart televisions. iPlayer services delivered to UK-based viewers are free from commercial advertising. '); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('beAst', '(?<=^|[\s.-])beAst\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BeiTai', '(?<=^|[\s.-])BeiTai\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BEN THE MEN', '\b(BEN[ ._-]THE[ ._-]MEN)\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Better Theatricals', '^\b(terminator.?2|alien[^s].*?1979|star.wars.*?(4k|19)(77)|.*?\bempire.strikes.back|.*?\breturn.of.the.jedi|apocalypse.now|the.exorcist.*?1973|donnie.darko|amadeus|payback.*?1999|payback.straight.up.*?2006|almost.famous)\b', 'Matches movies where the `Theatrical` cut is considered the better version. Subjectively chosen, based on Dictionarry''s personal preferences and major opinion. Needed to override the default special edition preference. Matches: +- Terminator 2: Judgement Day (1991) +- Alien (1979) +- Star Wars OT (1977-1983) +- Apocalypse Now (1979) +- The Exorcist (1973) +- Donnie Darko (2001) +- Amadeus (1984) +- Payback (1999) +- Almost Famous (2000)'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BeyondHD', '(?<=^|[\s.-])BeyondHD\b', 'Banned Due to only doing Full Discs'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BHDStudio', '(?<=^|[\s.-])BHDStudio\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BiTOR', '(?<=^|[\s.-])BiTOR\b', 'Banned for Fake DV/HDR Layer'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BiZKiT', '(?<=^|[\s.-])BiZKiT\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BLASPHEMY', '(?<=^|[\s.-])BLASPHEMY\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('bluegreeen', '(?<=^|[\s.-])bluegreeen\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('bluespots', '(?<=^|[\s.-])bluespots\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BLURANiUM', '(?<=^|[\s.-])BLURANiUM\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BlurayDesuYo', '(?<=^|[\s.-])BlurayDesuYo\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BLUTONiUM', '(?<=^|[\s.-])BLUTONiUM\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BlzT', '(?<=^|[\s.-])BlzT\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BMF', '(?<=^|[\s.-])BMF\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BOLS', '(?<=^|[\s.-])BOLS\b', 'Banned for Retagging'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Bracketed Year', '\[\d{4}\]', 'Match a year moniker inside square brackets'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Bravia Core', '\b(?:BCORE|(?:CORE)(?=\s*.(?:WEB-?DL|WEBRIP)))\b', 'Sony Pictures Core (formerly known as Bravia Core) is a video on demand service from Sony for its televisions and smartphones, launched in April 2021. The service offers the streaming of movies at up to 4K resolution provided by Sony Pictures Entertainment. CORE stands for Centre of Real Entertainment.'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BRUTE', '(?<=^|[\s.-])BRUTE\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BSTD', '(?<=^|[\s.-])BSTD\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BTM', '(?<=^|[\s.-])(BEN THE MEN|BEN|BTM)\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BTN', '(?<=^|[\s.-])BTN\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BTN Atmos', '\bTrue[ .-]?HDA[ .-]?[57]\.1', 'Matches BroadcastTheNet Atmos naming convention'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BTW', '(?<=^|[\s.-])BTW\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Bunny-Apocalypse', '(?<=^|[\s.-])Bunny-Apocalypse\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BV', '(?<=^|[\s.-])BV\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('BYNDR', '(?<=^|[\s.-])BYNDR\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('c0kE', '(?<=^|[\s.-])c0kE\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Cait-Sidhe', '(?<=^|[\s.-])Cait-Sidhe\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CasStudio', '(?<=^|[\s.-])CasStudio\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CBFM', '(?<=^|[\s.-])CBFM\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CBT', '(?<=^|[\s.-])CBT\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CHAOS', '(?<=^|[\s.-])CHAOS\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CHD', '(?<=^|[\s.-])CHD\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Chihiro', '(?<=^|[\s.-])Chihiro\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Chivaman', '(?<=^|[\s.-])Chivaman\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Chotab', '(?<=^|[\s.-])Chotab\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Cinefeel', '(?<=^|[\s.-])Cinefeel\b', 'Matches "Cinefeel" when preceded by whitespace, a hyphen or dot'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CiNEPHiLES', '(?<=^|[\s.-])CiNEPHiLES\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CJ', '(?<=^|[\s.-])CJ\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CLASSiCALHD', '(?<=^|[\s.-])CLASSiCALHD\b', 'Banned for LQ Non English / RaR'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CMCT', '(?<=^|[\s.-])CMCT\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CMRG', '(?<=^|[\s.-])CM(a)?R(io)?G\b', 'Prolific WEB-DL group. '); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CoalGirls', '(?<=^|[\s.-])CoalGirls\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('coffee', '(?<=^|[\s.-])coffee\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Colourisation', '\bcolou?r(i[sz]ed?|ed)?\b', 'Colourisation (or colorization in American English) is the process of adding colour to black-and-white, sepia, or other monochrome images. Matches variations of `color` in both American and British spellings, including: + +- **Base forms:** `color`, `colour` +- **Past tense/adjective forms:** `colored`, `coloured` +- **Verb forms:** `colorize`, `colourize`, `colorise`, `colourise` +- **Past participles:** `colorized`, `coloured`, `colourized`, `colourised`'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Commie', '(?<=^|[\s.-])Commie\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Crave', '\b(?:CRAV|(?:CRAVE)(?=\s*.(?:WEB-?DL|WEBRIP)))\b', 'Crave (originally CraveTV) is a Canadian subscription video on demand service. The service competes directly with other subscription-based over-the-top streaming services operating in Canada, primarily against American-based services. The service features Bell Media original programming, exclusive Canadian access to programming acquired from several U.S. television and streaming services, and various theatrically-released films. Crave''s major programming supplier is Warner Bros. Discovery (HBO / Max and Warner Bros. films). Starz, offered in partnership with Lionsgate.'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CREATiVE24', '(?<=^|[\s.-])CREATiVE24\b', 'Banned for Bloated Garbage'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CRFW', '(?<=^|[\s.-])CRFW\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CRiSC', '(?<=^|[\s.-])CRiSC\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Criterion Channel', '\b(CRiT)\b', 'The Criterion Channel is a subscription-based streaming service launched on April 8, 2019, by The Criterion Collection. Available in the United States and Canada, it features a rich library of films, including Criterion Collection releases with special features, curated playlists, temporarily licensed titles, and original content such as academic overviews and introductions. The Channel also showcases Janus-owned titles not yet available on physical media and maintains a collaborative relationship with Warner Bros. Discovery''s Max platform. Perfect for cinephiles, the service brings a curated cinematic experience to the digital space.'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CRUD', '(?<=^|[\s.-])CRUD\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Crunchyroll', '\b(C(runchy)?[ .-]?R(oll)?)\b', 'Crunchyroll is a popular streaming service focused on anime, manga, and Asian entertainment. It offers a large library of animated series and films, including both classic titles and new simulcasts straight from Japan, often with subtitles soon after they air. Users can watch on demand across devices, and there’s both a free, ad-supported tier and paid premium subscriptions with ad-free viewing and early access to episodes.'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CRX', '(?<=^|[\s.-])CRX\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CTR', '(?<=^|[\s.-])CTR\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('CtrlHD', '(?<=^|[\s.-])CtrlHD\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('cXcY', '(?<=^|[\s.-])cXcY\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('D-Z0N3', '(?<=^|[\s.-])D-Z0N3\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('d3g', '(?<=^|[\s.-])d3g\b', 'Banned for LQ and various Encode Issues.'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Dariush', '(?<=^|[\s.-])Dariush\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('DARKFLiX', '(?<=^|[\s.-])DARKFLiX\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('DarQ', '(?<=^|[\s.-])DarQ\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('dB', '(?<=^|[\s.-])dB\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('de[42]', '(?<=^|[\s.-])de[42]\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('deanzel', '(?<=^|[\s.-])deanzel\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('decibeL', '(?<=^|[\s.-])decibeL\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('DEFLATE', '(?<=^|[\s.-])DEFLATE\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Dekinai', '(?<=^|[\s.-])Dekinai\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('DepraveD', '(?<=^|[\s.-])DepraveD\b', 'Banned for Fake DV/HDR Layer'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('DEPTH', '(?<=^|[\s.-])DEPTH\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('DeViSiVE', '(?<=^|[\s.-])DeViSiVE\b', 'Ban for Mislabeled WEBRip'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Disney+', '\b(dsnp|dsny(p)?|disney\+)\s*\b', 'Disney+ is an American subscription video on-demand over-the-top streaming media service that primarily distributes films and television shows produced by Walt Disney Studios and Disney Television Studios, with dedicated content hubs for Disney''s flagship brands; Disney, Pixar, Marvel, Star Wars, National Geographic, ESPN, Hulu and Star.'); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('dkore', '(?<=^|[\s.-])dkore\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Doki', '(?<=^|[\s.-])Doki\b', ''); +INSERT INTO regular_expressions (name, pattern, description) VALUES ('Dolby Digital', '\bDD[^a-z+]|(?