This commit is contained in:
Jesse Bannon 2023-02-28 16:58:53 -08:00
parent 328b4f8b8a
commit 169bcccfe2
10 changed files with 33 additions and 16 deletions

View file

@ -1,4 +1,3 @@
import tempfile
from typing import Any from typing import Any
from typing import Dict from typing import Dict
from typing import Optional from typing import Optional
@ -12,7 +11,7 @@ from ytdl_sub.validators.validators import LiteralDictValidator
from ytdl_sub.validators.validators import StringValidator from ytdl_sub.validators.validators import StringValidator
if IS_WINDOWS: if IS_WINDOWS:
_DEFAULT_LOCK_DIRECTORY = tempfile.TemporaryDirectory().name _DEFAULT_LOCK_DIRECTORY = "" # Not supported in Windows
_DEFAULT_FFMPEG_PATH = ".\\ffmpeg.exe" _DEFAULT_FFMPEG_PATH = ".\\ffmpeg.exe"
_DEFAULT_FFPROBE_PATH = ".\\ffprobe.exe" _DEFAULT_FFPROBE_PATH = ".\\ffprobe.exe"
else: else:

View file

@ -7,8 +7,10 @@ from typing import Optional
from yt_dlp.utils import sanitize_filename from yt_dlp.utils import sanitize_filename
from ytdl_sub.entries.entry import Entry from ytdl_sub.entries.entry import Entry
from ytdl_sub.validators.file_path_validators import OverridesStringFormatterValidatorFilePathValidator, \ from ytdl_sub.validators.file_path_validators import (
StringFormatterFilePathValidator OverridesStringFormatterValidatorFilePathValidator,
)
from ytdl_sub.validators.file_path_validators import StringFormatterFilePathValidator
from ytdl_sub.validators.strict_dict_validator import StrictDictValidator from ytdl_sub.validators.strict_dict_validator import StrictDictValidator
from ytdl_sub.validators.string_datetime import StringDatetimeValidator from ytdl_sub.validators.string_datetime import StringDatetimeValidator
from ytdl_sub.validators.string_formatter_validators import DictFormatterValidator from ytdl_sub.validators.string_formatter_validators import DictFormatterValidator

View file

@ -1,6 +1,4 @@
import os
import subprocess import subprocess
import sys
import tempfile import tempfile
from typing import Dict from typing import Dict
from typing import List from typing import List
@ -30,16 +28,19 @@ class FFMPEG:
@classmethod @classmethod
def set_paths(cls, ffmpeg_path: str, ffprobe_path: str) -> None: def set_paths(cls, ffmpeg_path: str, ffprobe_path: str) -> None:
"""Set ffmpeg paths for usage"""
cls._FFMPEG_PATH = ffmpeg_path cls._FFMPEG_PATH = ffmpeg_path
cls._FFPROBE_PATH = ffprobe_path cls._FFPROBE_PATH = ffprobe_path
@classmethod @classmethod
def ffmpeg_path(cls) -> str: def ffmpeg_path(cls) -> str:
"""Ensure the ffmpeg path has been set and return it"""
assert cls._FFMPEG_PATH, "ffmpeg has not been set" assert cls._FFMPEG_PATH, "ffmpeg has not been set"
return cls._FFMPEG_PATH return cls._FFMPEG_PATH
@classmethod @classmethod
def ffprobe_path(cls) -> str: def ffprobe_path(cls) -> str:
"""Ensure the ffprobe path has been set and return it"""
assert cls._FFPROBE_PATH, "ffprobe has not been set" assert cls._FFPROBE_PATH, "ffprobe has not been set"
return cls._FFPROBE_PATH return cls._FFPROBE_PATH
@ -150,7 +151,9 @@ def set_ffmpeg_metadata_chapters(
lines += _create_metadata_chapters(chapters=chapters, file_duration_sec=file_duration_sec) lines += _create_metadata_chapters(chapters=chapters, file_duration_sec=file_duration_sec)
tmp_file_path = FFMPEG.tmp_file_path(relative_file_path=file_path) tmp_file_path = FFMPEG.tmp_file_path(relative_file_path=file_path)
with tempfile.NamedTemporaryFile(mode="w", suffix=".txt", encoding="utf-8", delete=False) as metadata_file: with tempfile.NamedTemporaryFile(
mode="w", suffix=".txt", encoding="utf-8", delete=False
) as metadata_file:
metadata_file.write("\n".join(lines)) metadata_file.write("\n".join(lines))
metadata_file.flush() metadata_file.flush()

View file

@ -162,7 +162,7 @@ class FileHandlerTransactionLog:
------- -------
str formatted to always look like a unix string str formatted to always look like a unix string
""" """
return str(path_str).replace(os.sep, '/') return str(path_str).replace(os.sep, "/")
def __init__(self): def __init__(self):
self.files_created: Dict[str, FileMetadata] = {} self.files_created: Dict[str, FileMetadata] = {}
@ -320,7 +320,9 @@ class FileHandlerTransactionLog:
) )
if self.is_empty: if self.is_empty:
lines.append(f"No new, modified, or removed files in '{self.format_path_str(output_directory)}'") lines.append(
f"No new, modified, or removed files in '{self.format_path_str(output_directory)}'"
)
return "\n".join(lines) return "\n".join(lines)

View file

@ -11,14 +11,17 @@ from ytdl_sub.utils.system import IS_WINDOWS
logger = Logger.get() logger = Logger.get()
if IS_WINDOWS: if IS_WINDOWS:
@contextmanager @contextmanager
def working_directory_lock(config: ConfigFile): def working_directory_lock(config: ConfigFile):
"""Windows does not support working directory lock"""
logger.info( logger.info(
"Working directory lock not supported in Windows. " "Working directory lock not supported in Windows. "
"Ensure only one instance of ytdl-sub runs at once using working directory %s", "Ensure only one instance of ytdl-sub runs at once using working directory %s",
config.config_options.working_directory, config.config_options.working_directory,
) )
yield yield
else: else:
import fcntl import fcntl
@ -59,4 +62,3 @@ else:
finally: finally:
fcntl.flock(lock_file, fcntl.LOCK_UN) fcntl.flock(lock_file, fcntl.LOCK_UN)
lock_file.close() lock_file.close()

View file

@ -1,4 +1,3 @@
import sys import sys
IS_WINDOWS = sys.platform.startswith("win32") IS_WINDOWS = sys.platform.startswith("win32")

View file

@ -2,13 +2,15 @@ import os
from pathlib import Path from pathlib import Path
from typing import Dict from typing import Dict
from ytdl_sub.validators.string_formatter_validators import StringFormatterValidator, OverridesStringFormatterValidator from ytdl_sub.validators.string_formatter_validators import OverridesStringFormatterValidator
from ytdl_sub.validators.string_formatter_validators import StringFormatterValidator
class StringFormatterFilePathValidator(StringFormatterValidator): class StringFormatterFilePathValidator(StringFormatterValidator):
_expected_value_type_name = "filepath" _expected_value_type_name = "filepath"
def apply_formatter(self, variable_dict: Dict[str, str]) -> str: def apply_formatter(self, variable_dict: Dict[str, str]) -> str:
"""Turn into a Path, then a string, to get correct directory separators"""
return str(Path(super().apply_formatter(variable_dict))) return str(Path(super().apply_formatter(variable_dict)))
@ -16,4 +18,5 @@ class OverridesStringFormatterValidatorFilePathValidator(OverridesStringFormatte
_expected_value_type_name = "static filepath" _expected_value_type_name = "static filepath"
def apply_formatter(self, variable_dict: Dict[str, str]) -> str: def apply_formatter(self, variable_dict: Dict[str, str]) -> str:
"""Turn into a Path, then a string, to get correct directory separators"""
return os.path.realpath(super().apply_formatter(variable_dict)) return os.path.realpath(super().apply_formatter(variable_dict))

View file

@ -15,7 +15,8 @@ from ytdl_sub.cli.main import main
from ytdl_sub.config.config_file import ConfigFile from ytdl_sub.config.config_file import ConfigFile
from ytdl_sub.subscriptions.subscription import Subscription from ytdl_sub.subscriptions.subscription import Subscription
from ytdl_sub.subscriptions.subscription_download import SubscriptionDownload from ytdl_sub.subscriptions.subscription_download import SubscriptionDownload
from ytdl_sub.utils.file_handler import FileHandlerTransactionLog, FileHandler from ytdl_sub.utils.file_handler import FileHandler
from ytdl_sub.utils.file_handler import FileHandlerTransactionLog
from ytdl_sub.utils.logger import Logger from ytdl_sub.utils.logger import Logger
from ytdl_sub.utils.yaml import load_yaml from ytdl_sub.utils.yaml import load_yaml
@ -101,7 +102,9 @@ def timestamps_file_path():
"00:01:01 Part 5\n", "00:01:01 Part 5\n",
] ]
with tempfile.NamedTemporaryFile(mode="w", encoding="utf-8", suffix=".txt", delete=False) as tmp: with tempfile.NamedTemporaryFile(
mode="w", encoding="utf-8", suffix=".txt", delete=False
) as tmp:
tmp.writelines(timestamps) tmp.writelines(timestamps)
try: try:

View file

@ -43,7 +43,9 @@ def assert_transaction_log_matches(
# Read the expected summary file # Read the expected summary file
with open(transaction_log_path, "r", encoding="utf-8") as summary_file: with open(transaction_log_path, "r", encoding="utf-8") as summary_file:
expected_summary = summary_file.read().format(output_directory=FileHandlerTransactionLog.format_path_str(output_directory)) expected_summary = summary_file.read().format(
output_directory=FileHandlerTransactionLog.format_path_str(output_directory)
)
# Split, ensure there are the same number of new lines # Split, ensure there are the same number of new lines
summary_lines: List[str] = summary.split("\n") summary_lines: List[str] = summary.split("\n")

View file

@ -44,6 +44,8 @@ def test_load_yaml_file_not_found():
def test_load_yaml_invalid_syntax(bad_yaml_file_path): def test_load_yaml_invalid_syntax(bad_yaml_file_path):
with pytest.raises( with pytest.raises(
InvalidYamlException, InvalidYamlException,
match=re.escape(f"'{bad_yaml_file_path}' has invalid YAML, copy-paste it into a YAML checker to find the issue."), match=re.escape(
f"'{bad_yaml_file_path}' has invalid YAML, copy-paste it into a YAML checker to find the issue."
),
): ):
load_yaml(file_path=bad_yaml_file_path) load_yaml(file_path=bad_yaml_file_path)