mirror of
https://github.com/Sonarr/Sonarr.git
synced 2024-11-26 04:33:01 +01:00
Fixed: Improve quality and episode info output in parse result
This commit is contained in:
parent
bc374f07ce
commit
67234222e3
@ -11,6 +11,7 @@ import ModalHeader from 'Components/Modal/ModalHeader';
|
||||
import { icons } from 'Helpers/Props';
|
||||
import { clear, fetch } from 'Store/Actions/parseActions';
|
||||
import getErrorMessage from 'Utilities/Object/getErrorMessage';
|
||||
import translate from 'Utilities/String/translate';
|
||||
import ParseResult from './ParseResult';
|
||||
import parseStateSelector from './parseStateSelector';
|
||||
import styles from './ParseModalContent.css';
|
||||
@ -58,7 +59,7 @@ function ParseModalContent(props: ParseModalContentProps) {
|
||||
|
||||
return (
|
||||
<ModalContent onModalClose={onModalClose}>
|
||||
<ModalHeader>Test Parsing</ModalHeader>
|
||||
<ModalHeader>{translate('TestParsing')}</ModalHeader>
|
||||
|
||||
<ModalBody>
|
||||
<div className={styles.inputContainer}>
|
||||
@ -115,7 +116,7 @@ function ParseModalContent(props: ParseModalContentProps) {
|
||||
</ModalBody>
|
||||
|
||||
<ModalFooter>
|
||||
<Button onPress={onModalClose}>Close</Button>
|
||||
<Button onPress={onModalClose}>{translate('Close')}</Button>
|
||||
</ModalFooter>
|
||||
</ModalContent>
|
||||
);
|
||||
|
@ -1,20 +1,8 @@
|
||||
.item {
|
||||
.container {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
}
|
||||
|
||||
.title {
|
||||
margin-right: 20px;
|
||||
width: 250px;
|
||||
text-align: right;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.description {
|
||||
/* composes: description from '~Components/DescriptionList/DescriptionListItemTitle.css'; */
|
||||
}
|
||||
|
||||
@media (max-width: $breakpointSmall) {
|
||||
.item {
|
||||
display: block;
|
||||
}
|
||||
.column {
|
||||
flex: 0 0 50%;
|
||||
}
|
||||
|
5
frontend/src/Parse/ParseResult.css.d.ts
vendored
5
frontend/src/Parse/ParseResult.css.d.ts
vendored
@ -1,9 +1,8 @@
|
||||
// This file is automatically generated.
|
||||
// Please do not change this file!
|
||||
interface CssExports {
|
||||
'description': string;
|
||||
'item': string;
|
||||
'title': string;
|
||||
'column': string;
|
||||
'container': string;
|
||||
}
|
||||
export const cssExports: CssExports;
|
||||
export default cssExports;
|
||||
|
@ -5,6 +5,7 @@ import EpisodeFormats from 'Episode/EpisodeFormats';
|
||||
import SeriesTitleLink from 'Series/SeriesTitleLink';
|
||||
import translate from 'Utilities/String/translate';
|
||||
import ParseResultItem from './ParseResultItem';
|
||||
import styles from './ParseResult.css';
|
||||
|
||||
interface ParseResultProps {
|
||||
item: ParseModel;
|
||||
@ -45,11 +46,11 @@ function ParseResult(props: ParseResultProps) {
|
||||
<div>
|
||||
<FieldSet legend={translate('Release')}>
|
||||
<ParseResultItem
|
||||
title={translate('Release Title')}
|
||||
title={translate('ReleaseTitle')}
|
||||
data={releaseTitle}
|
||||
/>
|
||||
|
||||
<ParseResultItem title={translate('Series Title')} data={seriesTitle} />
|
||||
<ParseResultItem title={translate('SeriesTitle')} data={seriesTitle} />
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Year')}
|
||||
@ -57,7 +58,7 @@ function ParseResult(props: ParseResultProps) {
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('All Titles')}
|
||||
title={translate('AllTitles')}
|
||||
data={
|
||||
seriesTitleInfo.allTitles?.length > 0
|
||||
? seriesTitleInfo.allTitles.join(', ')
|
||||
@ -66,105 +67,113 @@ function ParseResult(props: ParseResultProps) {
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Release Group')}
|
||||
title={translate('ReleaseGroup')}
|
||||
data={releaseGroup ?? '-'}
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Release Hash')}
|
||||
title={translate('ReleaseHash')}
|
||||
data={releaseHash ? releaseHash : '-'}
|
||||
/>
|
||||
</FieldSet>
|
||||
|
||||
{/*
|
||||
|
||||
Year
|
||||
Secondary titles
|
||||
special episode
|
||||
|
||||
*/}
|
||||
<FieldSet legend={translate('EpisodeInfo')}>
|
||||
<div className={styles.container}>
|
||||
<div className={styles.column}>
|
||||
<ParseResultItem
|
||||
title={translate('SeasonNumber')}
|
||||
data={
|
||||
seasonNumber === 0 && absoluteEpisodeNumbers.length
|
||||
? '-'
|
||||
: seasonNumber
|
||||
}
|
||||
/>
|
||||
|
||||
<FieldSet legend={translate('Episode Info')}>
|
||||
<ParseResultItem
|
||||
title={translate('Season Number')}
|
||||
data={
|
||||
seasonNumber === 0 && absoluteEpisodeNumbers.length
|
||||
? '-'
|
||||
: seasonNumber
|
||||
}
|
||||
/>
|
||||
<ParseResultItem
|
||||
title={translate('EpisodeNumbers')}
|
||||
data={episodeNumbers.join(', ') || '-'}
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Episode Number(s)')}
|
||||
data={episodeNumbers.join(', ') || '-'}
|
||||
/>
|
||||
<ParseResultItem
|
||||
title={translate('AbsoluteEpisodeNumbers')}
|
||||
data={
|
||||
absoluteEpisodeNumbers.length
|
||||
? absoluteEpisodeNumbers.join(', ')
|
||||
: '-'
|
||||
}
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Absolute Episode Number(s)')}
|
||||
data={
|
||||
absoluteEpisodeNumbers.length
|
||||
? absoluteEpisodeNumbers.join(', ')
|
||||
: '-'
|
||||
}
|
||||
/>
|
||||
<ParseResultItem
|
||||
title={translate('Daily')}
|
||||
data={isDaily ? 'True' : 'False'}
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Special')}
|
||||
data={special ? 'True' : 'False'}
|
||||
/>
|
||||
<ParseResultItem
|
||||
title={translate('AirDate')}
|
||||
data={airDate ?? '-'}
|
||||
/>
|
||||
</div>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Full Season')}
|
||||
data={fullSeason ? 'True' : 'False'}
|
||||
/>
|
||||
<div className={styles.column}>
|
||||
<ParseResultItem
|
||||
title={translate('Special')}
|
||||
data={special ? 'True' : 'False'}
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Multi-Season')}
|
||||
data={isMultiSeason ? 'True' : 'False'}
|
||||
/>
|
||||
<ParseResultItem
|
||||
title={translate('FullSeason')}
|
||||
data={fullSeason ? 'True' : 'False'}
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Partial Season')}
|
||||
data={isPartialSeason ? 'True' : 'False'}
|
||||
/>
|
||||
<ParseResultItem
|
||||
title={translate('MultiSeason')}
|
||||
data={isMultiSeason ? 'True' : 'False'}
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Daily')}
|
||||
data={isDaily ? 'True' : 'False'}
|
||||
/>
|
||||
|
||||
<ParseResultItem title={translate('Air Date')} data={airDate ?? '-'} />
|
||||
<ParseResultItem
|
||||
title={translate('PartialSeason')}
|
||||
data={isPartialSeason ? 'True' : 'False'}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</FieldSet>
|
||||
|
||||
<FieldSet legend={translate('Quality')}>
|
||||
<ParseResultItem
|
||||
title={translate('Quality')}
|
||||
data={quality.quality.name}
|
||||
/>
|
||||
<div className={styles.container}>
|
||||
<div className={styles.column}>
|
||||
<ParseResultItem
|
||||
title={translate('Quality')}
|
||||
data={quality.quality.name}
|
||||
/>
|
||||
<ParseResultItem
|
||||
title={translate('Proper')}
|
||||
data={
|
||||
quality.revision.version > 1 && !quality.revision.isRepack
|
||||
? 'True'
|
||||
: '-'
|
||||
}
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Version')}
|
||||
data={quality.revision.version > 1 ? quality.revision.version : '-'}
|
||||
/>
|
||||
<ParseResultItem
|
||||
title={translate('Repack')}
|
||||
data={quality.revision.isRepack ? 'True' : '-'}
|
||||
/>
|
||||
</div>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Real')}
|
||||
data={quality.revision.real ? 'True' : '-'}
|
||||
/>
|
||||
<div className={styles.column}>
|
||||
<ParseResultItem
|
||||
title={translate('Version')}
|
||||
data={
|
||||
quality.revision.version > 1 ? quality.revision.version : '-'
|
||||
}
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Proper')}
|
||||
data={
|
||||
quality.revision.version > 1 && !quality.revision.isRepack
|
||||
? 'True'
|
||||
: '-'
|
||||
}
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Repack')}
|
||||
data={quality.revision.isRepack ? 'True' : '-'}
|
||||
/>
|
||||
<ParseResultItem
|
||||
title={translate('Real')}
|
||||
data={quality.revision.real ? 'True' : '-'}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</FieldSet>
|
||||
|
||||
<FieldSet legend={translate('Languages')}>
|
||||
@ -176,7 +185,7 @@ function ParseResult(props: ParseResultProps) {
|
||||
|
||||
<FieldSet legend={translate('Details')}>
|
||||
<ParseResultItem
|
||||
title={translate('Matched to Series')}
|
||||
title={translate('MatchedToSeries')}
|
||||
data={
|
||||
series ? (
|
||||
<SeriesTitleLink
|
||||
@ -190,12 +199,12 @@ function ParseResult(props: ParseResultProps) {
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Matched to Season')}
|
||||
title={translate('MatchedToSeason')}
|
||||
data={episodes.length ? episodes[0].seasonNumber : '-'}
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Matched to Episodes')}
|
||||
title={translate('MatchedToEpisodes')}
|
||||
data={
|
||||
episodes.length ? (
|
||||
<div>
|
||||
@ -218,12 +227,12 @@ function ParseResult(props: ParseResultProps) {
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Custom Formats')}
|
||||
title={translate('CustomFormats')}
|
||||
data={<EpisodeFormats formats={customFormats} />}
|
||||
/>
|
||||
|
||||
<ParseResultItem
|
||||
title={translate('Custom Format Score')}
|
||||
title={translate('CustomFormatScore')}
|
||||
data={customFormatScore}
|
||||
/>
|
||||
</FieldSet>
|
||||
|
@ -2,6 +2,7 @@ import React, { Fragment, useCallback, useState } from 'react';
|
||||
import PageToolbarButton from 'Components/Page/Toolbar/PageToolbarButton';
|
||||
import { icons } from 'Helpers/Props';
|
||||
import ParseModal from 'Parse/ParseModal';
|
||||
import translate from 'Utilities/String/translate';
|
||||
|
||||
function ParseToolbarButton() {
|
||||
const [isParseModalOpen, setIsParseModalOpen] = useState(false);
|
||||
@ -17,7 +18,7 @@ function ParseToolbarButton() {
|
||||
return (
|
||||
<Fragment>
|
||||
<PageToolbarButton
|
||||
label="Test Parsing"
|
||||
label={translate('TestParsing')}
|
||||
iconName={icons.PARSE}
|
||||
onPress={onOpenParseModalPress}
|
||||
/>
|
||||
|
@ -1,16 +1,19 @@
|
||||
{
|
||||
"AbsoluteEpisodeNumbers": "Absolute Episode Number(s)",
|
||||
"Activity": "Activity",
|
||||
"Add": "Add",
|
||||
"AddNew": "Add New",
|
||||
"Added": "Added",
|
||||
"AddingTag": "Adding tag",
|
||||
"AddNew": "Add New",
|
||||
"AirDate": "Air Date",
|
||||
"AllTitles": "All Titles",
|
||||
"ApiKeyValidationHealthCheckMessage": "Please update your API key to be at least {0} characters long. You can do this via settings or the config file",
|
||||
"AppDataLocationHealthCheckMessage": "Updating will not be possible to prevent deleting AppData on Update",
|
||||
"Apply": "Apply",
|
||||
"ApplyChanges": "Apply Changes",
|
||||
"ApplyTags": "Apply Tags",
|
||||
"ApplyTagsHelpTextHowToApply": "How to apply tags to the selected indexers",
|
||||
"ApplyTagsHelpTextAdd": "Add: Add the tags the existing list of tags",
|
||||
"ApplyTagsHelpTextHowToApply": "How to apply tags to the selected indexers",
|
||||
"ApplyTagsHelpTextRemove": "Remove: Remove the entered tags",
|
||||
"ApplyTagsHelpTextReplace": "Replace: Replace the tags with the entered tags (enter no tags to clear all tags)",
|
||||
"AutoAdd": "Auto Add",
|
||||
@ -34,6 +37,7 @@
|
||||
"CustomFormatScore": "Custom Format Score",
|
||||
"CustomFormats": "Custom Formats",
|
||||
"CutoffUnmet": "Cutoff Unmet",
|
||||
"Daily": "Daily",
|
||||
"Delete": "Delete",
|
||||
"DeleteCondition": "Delete Condition",
|
||||
"DeleteConditionMessageText": "Are you sure you want to delete the condition '{0}'?",
|
||||
@ -45,14 +49,15 @@
|
||||
"DeleteSelectedImportListsMessageText": "Are you sure you want to delete {count} selected import list(s)?",
|
||||
"DeleteSelectedIndexers": "Delete Indexer(s)",
|
||||
"DeleteSelectedIndexersMessageText": "Are you sure you want to delete {count} selected indexer(s)?",
|
||||
"Details": "Details",
|
||||
"Disabled": "Disabled",
|
||||
"DownloadClients": "Download Clients",
|
||||
"DownloadClientCheckNoneAvailableHealthCheckMessage": "No download client is available",
|
||||
"DownloadClientCheckUnableToCommunicateWithHealthCheckMessage": "Unable to communicate with {0}.",
|
||||
"DownloadClientRootFolderHealthCheckMessage": "Download client {0} places downloads in the root folder {1}. You should not download to a root folder.",
|
||||
"DownloadClientSortingHealthCheckMessage": "Download client {0} has {1} sorting enabled for Sonarr's category. You should disable sorting in your download client to avoid import issues.",
|
||||
"DownloadClientStatusAllClientHealthCheckMessage": "All download clients are unavailable due to failures",
|
||||
"DownloadClientStatusSingleClientHealthCheckMessage": "Download clients unavailable due to failures: {0}",
|
||||
"DownloadClients": "Download Clients",
|
||||
"Edit": "Edit",
|
||||
"EditSelectedDownloadClients": "Edit Selected Download Clients",
|
||||
"EditSelectedImportLists": "Edit Selected Import Lists",
|
||||
@ -63,23 +68,25 @@
|
||||
"EnableRSS": "Enable RSS",
|
||||
"Enabled": "Enabled",
|
||||
"Ended": "Ended",
|
||||
"EpisodeInfo": "Episode Info",
|
||||
"EpisodeNumbers": "Episode Number(s)",
|
||||
"Events": "Events",
|
||||
"ExistingTag": "Existing tag",
|
||||
"ExportCustomFormat": "Export Custom Format",
|
||||
"FullSeason": "Full Season",
|
||||
"General": "General",
|
||||
"HiddenClickToShow": "Hidden, click to show",
|
||||
"HideAdvanced": "Hide Advanced",
|
||||
"History": "History",
|
||||
"Implementation": "Implementation",
|
||||
"ImportLists": "Import Lists",
|
||||
"ImportListRootFolderMissingRootHealthCheckMessage": "Missing root folder for import list(s): {0}",
|
||||
"ImportListRootFolderMultipleMissingRootsHealthCheckMessage": "Multiple root folders are missing for import lists: {0}",
|
||||
"ImportListStatusAllUnavailableHealthCheckMessage": "All lists are unavailable due to failures",
|
||||
"ImportListStatusUnavailableHealthCheckMessage": "Lists unavailable due to failures: {0}",
|
||||
"ImportLists": "Import Lists",
|
||||
"ImportMechanismEnableCompletedDownloadHandlingIfPossibleHealthCheckMessage": "Enable Completed Download Handling if possible",
|
||||
"ImportMechanismEnableCompletedDownloadHandlingIfPossibleMultiComputerHealthCheckMessage": "Enable Completed Download Handling if possible (Multi-Computer unsupported)",
|
||||
"ImportMechanismHandlingDisabledHealthCheckMessage": "Enable Completed Download Handling",
|
||||
"Indexers": "Indexers",
|
||||
"IndexerJackettAllHealthCheckMessage": "Indexers using the unsupported Jackett 'all' endpoint: {0}",
|
||||
"IndexerLongTermStatusAllUnavailableHealthCheckMessage": "All indexers are unavailable due to failures for more than 6 hours",
|
||||
"IndexerLongTermStatusUnavailableHealthCheckMessage": "Indexers unavailable due to failures for more than 6 hours: {0}",
|
||||
@ -90,8 +97,10 @@
|
||||
"IndexerSearchNoInteractiveHealthCheckMessage": "No indexers available with Interactive Search enabled, Sonarr will not provide any interactive search results",
|
||||
"IndexerStatusAllUnavailableHealthCheckMessage": "All indexers are unavailable due to failures",
|
||||
"IndexerStatusUnavailableHealthCheckMessage": "Indexers unavailable due to failures: {0}",
|
||||
"Indexers": "Indexers",
|
||||
"Language": "Language",
|
||||
"Language that Sonarr will use for UI": "Language that Sonarr will use for UI",
|
||||
"Languages": "Languages",
|
||||
"LibraryImport": "Library Import",
|
||||
"LogFiles": "Log Files",
|
||||
"ManageClients": "Manage Clients",
|
||||
@ -99,12 +108,16 @@
|
||||
"ManageImportLists": "Manage Import Lists",
|
||||
"ManageIndexers": "Manage Indexers",
|
||||
"ManageLists": "Manage Lists",
|
||||
"MatchedToEpisodes": "Matched to Episodes",
|
||||
"MatchedToSeason": "Matched to Season",
|
||||
"MatchedToSeries": "Matched to Series",
|
||||
"MediaManagement": "Media Management",
|
||||
"Metadata": "Metadata",
|
||||
"MetadataSource": "Metadata Source",
|
||||
"Missing": "Missing",
|
||||
"Monitored": "Monitored",
|
||||
"MountHealthCheckMessage": "Mount containing a series path is mounted read-only: ",
|
||||
"MultiSeason": "Multi-Season",
|
||||
"Name": "Name",
|
||||
"Negated": "Negated",
|
||||
"Network": "Network",
|
||||
@ -117,18 +130,25 @@
|
||||
"NoSeasons": "No seasons",
|
||||
"OneSeason": "1 season",
|
||||
"OriginalLanguage": "Original Language",
|
||||
"PartialSeason": "Partial Season",
|
||||
"Path": "Path",
|
||||
"PreviousAiring": "Previous Airing",
|
||||
"Priority": "Priority",
|
||||
"Profiles": "Profiles",
|
||||
"Proper": "Proper",
|
||||
"ProxyBadRequestHealthCheckMessage": "Failed to test proxy. Status Code: {0}",
|
||||
"ProxyFailedToTestHealthCheckMessage": "Failed to test proxy: {0}",
|
||||
"ProxyResolveIpHealthCheckMessage": "Failed to resolve the IP Address for the Configured Proxy Host {0}",
|
||||
"Quality": "Quality",
|
||||
"QualityProfile": "Quality Profile",
|
||||
"Queue": "Queue",
|
||||
"Real": "Real",
|
||||
"RecycleBinUnableToWriteHealthCheckMessage": "Unable to write to configured recycling bin folder: {0}. Ensure this path exists and is writable by the user running Sonarr",
|
||||
"RefreshSeries": "Refresh Series",
|
||||
"Release": "Release",
|
||||
"ReleaseGroup": "Release Group",
|
||||
"ReleaseHash": "Release Hash",
|
||||
"ReleaseTitle": "Release Title",
|
||||
"RemotePathMappingBadDockerPathHealthCheckMessage": "You are using docker; download client {0} places downloads in {1} but this is not a valid {2} path. Review your remote path mappings and download client settings.",
|
||||
"RemotePathMappingDockerFolderMissingHealthCheckMessage": "You are using docker; download client {0} places downloads in {1} but this directory does not appear to exist inside the container. Review your remote path mappings and container volume settings.",
|
||||
"RemotePathMappingDownloadPermissionsHealthCheckMessage": "Sonarr can see but not access downloaded episode {0}. Likely permissions error.",
|
||||
@ -158,6 +178,7 @@
|
||||
"RemovedSeriesMultipleRemovedHealthCheckMessage": "Series {0} were removed from TheTVDB",
|
||||
"RemovedSeriesSingleRemovedHealthCheckMessage": "Series {0} was removed from TheTVDB",
|
||||
"RemovingTag": "Removing tag",
|
||||
"Repack": "Repack",
|
||||
"Replace": "Replace",
|
||||
"Required": "Required",
|
||||
"Result": "Result",
|
||||
@ -165,24 +186,29 @@
|
||||
"RootFolderMissingHealthCheckMessage": "Missing root folder: {0}",
|
||||
"RootFolderMultipleMissingHealthCheckMessage": "Multiple root folders are missing: {0}",
|
||||
"SearchForMonitoredEpisodes": "Search for monitored episodes",
|
||||
"SeasonNumber": "Season Number",
|
||||
"Series": "Series",
|
||||
"SeriesTitle": "Series Title",
|
||||
"SetTags": "Set Tags",
|
||||
"Settings": "Settings",
|
||||
"ShowAdvanced": "Show Advanced",
|
||||
"ShownClickToHide": "Shown, click to hide",
|
||||
"SizeOnDisk": "Size on disk",
|
||||
"Special": "Special",
|
||||
"System": "System",
|
||||
"SystemTimeHealthCheckMessage": "System time is off by more than 1 day. Scheduled tasks may not run correctly until the time is corrected",
|
||||
"Tags": "Tags",
|
||||
"Tasks": "Tasks",
|
||||
"TestParsing": "Test Parsing",
|
||||
"UI": "UI",
|
||||
"UI Language": "UI Language",
|
||||
"Unmonitored": "Unmonitored",
|
||||
"Updates": "Updates",
|
||||
"UpdateAvailableHealthCheckMessage": "New update is available",
|
||||
"UpdateStartupNotWritableHealthCheckMessage": "Cannot install update because startup folder '{0}' is not writable by the user '{1}'.",
|
||||
"UpdateStartupTranslocationHealthCheckMessage": "Cannot install update because startup folder '{0}' is in an App Translocation folder.",
|
||||
"UpdateUINotWritableHealthCheckMessage": "Cannot install update because UI folder '{0}' is not writable by the user '{1}'.",
|
||||
"Updates": "Updates",
|
||||
"Version": "Version",
|
||||
"Wanted": "Wanted",
|
||||
"Yes": "Yes"
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user