Fold preset --format into the cli args
This commit is contained in:
parent
f7abca8d10
commit
5a76f1d68a
6 changed files with 87 additions and 116 deletions
|
|
@ -918,11 +918,6 @@ class HttpAPI(Common):
|
||||||
{"error": "name is required.", "data": item}, status=web.HTTPBadRequest.status_code
|
{"error": "name is required.", "data": item}, status=web.HTTPBadRequest.status_code
|
||||||
)
|
)
|
||||||
|
|
||||||
if not item.get("format"):
|
|
||||||
return web.json_response(
|
|
||||||
{"error": "format is required.", "data": item}, status=web.HTTPBadRequest.status_code
|
|
||||||
)
|
|
||||||
|
|
||||||
if not item.get("id", None) or not validate_uuid(item.get("id"), version=4):
|
if not item.get("id", None) or not validate_uuid(item.get("id"), version=4):
|
||||||
item["id"] = str(uuid.uuid4())
|
item["id"] = str(uuid.uuid4())
|
||||||
|
|
||||||
|
|
@ -936,7 +931,7 @@ class HttpAPI(Common):
|
||||||
|
|
||||||
presets.append(Preset(**item))
|
presets.append(Preset(**item))
|
||||||
try:
|
try:
|
||||||
presets = cls.save(presets=presets).load().get_all()
|
presets = cls.save(items=presets).load().get_all()
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
LOG.exception(e)
|
LOG.exception(e)
|
||||||
return web.json_response(
|
return web.json_response(
|
||||||
|
|
@ -1728,7 +1723,7 @@ class HttpAPI(Common):
|
||||||
LOG.error(str(e))
|
LOG.error(str(e))
|
||||||
return web.json_response(data={"message": str(e)}, status=web.HTTPInternalServerError.status_code)
|
return web.json_response(data={"message": str(e)}, status=web.HTTPInternalServerError.status_code)
|
||||||
|
|
||||||
url = "https://www.youtube.com/account"
|
url = "https://www.youtube.com/paid_memberships"
|
||||||
|
|
||||||
try:
|
try:
|
||||||
opts = {
|
opts = {
|
||||||
|
|
@ -1745,8 +1740,8 @@ class HttpAPI(Common):
|
||||||
LOG.debug(f"Checking '{url}' redirection.")
|
LOG.debug(f"Checking '{url}' redirection.")
|
||||||
response = await client.request(method="GET", url=url, follow_redirects=False)
|
response = await client.request(method="GET", url=url, follow_redirects=False)
|
||||||
return web.json_response(
|
return web.json_response(
|
||||||
data={"message": "Authenticated." if response.status_code == 200 else "Not authenticated."},
|
data={"message": "Authenticated." if 200 == response.status_code else "Not authenticated."},
|
||||||
status=200 if response.status_code == 200 else 401,
|
status=200 if 200 == response.status_code else 401,
|
||||||
)
|
)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
LOG.error(f"Failed to request '{url}'. '{e}'.")
|
LOG.error(f"Failed to request '{url}'. '{e}'.")
|
||||||
|
|
|
||||||
|
|
@ -24,9 +24,6 @@ class Preset:
|
||||||
name: str
|
name: str
|
||||||
"""The name of the preset."""
|
"""The name of the preset."""
|
||||||
|
|
||||||
format: str
|
|
||||||
"""The format of the preset."""
|
|
||||||
|
|
||||||
folder: str = ""
|
folder: str = ""
|
||||||
"""The default download folder to use if non is given."""
|
"""The default download folder to use if non is given."""
|
||||||
|
|
||||||
|
|
@ -56,13 +53,13 @@ class Presets(metaclass=Singleton):
|
||||||
This class is used to manage the presets.
|
This class is used to manage the presets.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
_presets: list[Preset] = []
|
_items: list[Preset] = []
|
||||||
"""The list of presets."""
|
"""The list of presets."""
|
||||||
|
|
||||||
_instance = None
|
_instance = None
|
||||||
"""The instance of the class."""
|
"""The instance of the class."""
|
||||||
|
|
||||||
_default_presets: list[Preset] = []
|
_default: list[Preset] = []
|
||||||
|
|
||||||
def __init__(self, file: str | None = None, config: Config | None = None):
|
def __init__(self, file: str | None = None, config: Config | None = None):
|
||||||
Presets._instance = self
|
Presets._instance = self
|
||||||
|
|
@ -77,13 +74,14 @@ class Presets(metaclass=Singleton):
|
||||||
except Exception:
|
except Exception:
|
||||||
pass
|
pass
|
||||||
|
|
||||||
with open(os.path.join(os.path.dirname(__file__), "presets.json")) as f:
|
default_file = os.path.join(os.path.dirname(__file__), "presets.json")
|
||||||
|
with open(default_file) as f:
|
||||||
for i, preset in enumerate(json.load(f)):
|
for i, preset in enumerate(json.load(f)):
|
||||||
try:
|
try:
|
||||||
self.validate(preset)
|
self.validate(preset)
|
||||||
self._default_presets.append(Preset(**preset))
|
self._default.append(Preset(**preset))
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
LOG.error(f"Failed to parse default preset '{i}'. '{e!s}'.")
|
LOG.error(f"Failed to parse '{default_file}:{i}'. '{e!s}'.")
|
||||||
continue
|
continue
|
||||||
|
|
||||||
def event_handler(_, __):
|
def event_handler(_, __):
|
||||||
|
|
@ -111,7 +109,7 @@ class Presets(metaclass=Singleton):
|
||||||
|
|
||||||
def attach(self, _: web.Application):
|
def attach(self, _: web.Application):
|
||||||
"""
|
"""
|
||||||
Attach the work to the aiohttp application.
|
Attach the class to the aiohttp application.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
_ (web.Application): The aiohttp application.
|
_ (web.Application): The aiohttp application.
|
||||||
|
|
@ -123,12 +121,12 @@ class Presets(metaclass=Singleton):
|
||||||
self.load()
|
self.load()
|
||||||
|
|
||||||
def get_all(self) -> list[Preset]:
|
def get_all(self) -> list[Preset]:
|
||||||
"""Return the presets."""
|
"""Return the items."""
|
||||||
return self._default_presets + self._presets
|
return self._default + self._items
|
||||||
|
|
||||||
def load(self) -> "Presets":
|
def load(self) -> "Presets":
|
||||||
"""
|
"""
|
||||||
Load the Presets.
|
Load the items.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
Presets: The current instance.
|
Presets: The current instance.
|
||||||
|
|
@ -139,16 +137,15 @@ class Presets(metaclass=Singleton):
|
||||||
if not os.path.exists(self._file) or os.path.getsize(self._file) < 10:
|
if not os.path.exists(self._file) or os.path.getsize(self._file) < 10:
|
||||||
return self
|
return self
|
||||||
|
|
||||||
LOG.info(f"Loading presets from '{self._file}'.")
|
LOG.info(f"Loading '{self._file}'.")
|
||||||
try:
|
try:
|
||||||
with open(self._file) as f:
|
with open(self._file) as f:
|
||||||
presets = json.load(f)
|
presets = json.load(f)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
LOG.error(f"Failed to parse presets from '{self._file}'. '{e}'.")
|
LOG.error(f"Failed to parse '{self._file}'. '{e}'.")
|
||||||
return self
|
return self
|
||||||
|
|
||||||
if not presets or len(presets) < 1:
|
if not presets or len(presets) < 1:
|
||||||
LOG.info(f"No presets were defined in '{self._file}'.")
|
|
||||||
return self
|
return self
|
||||||
|
|
||||||
need_save = False
|
need_save = False
|
||||||
|
|
@ -160,134 +157,144 @@ class Presets(metaclass=Singleton):
|
||||||
need_save = True
|
need_save = True
|
||||||
|
|
||||||
preset, preset_status = clean_item(preset, keys=("args", "postprocessors"))
|
preset, preset_status = clean_item(preset, keys=("args", "postprocessors"))
|
||||||
|
if preset.get("format"):
|
||||||
|
if not preset.get("cli"):
|
||||||
|
preset.update({"cli": f"--format {preset['format']}"})
|
||||||
|
else:
|
||||||
|
preset["cli"] = f"--format '{preset['format']}'\n" + preset["cli"]
|
||||||
|
|
||||||
|
preset["cli"] = str(preset["cli"]).strip()
|
||||||
|
|
||||||
|
preset.pop("format")
|
||||||
|
need_save = True
|
||||||
|
|
||||||
preset = Preset(**preset)
|
preset = Preset(**preset)
|
||||||
|
|
||||||
if preset_status:
|
if preset_status:
|
||||||
need_save = True
|
need_save = True
|
||||||
|
|
||||||
self._presets.append(preset)
|
self._items.append(preset)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
LOG.error(f"Failed to parse preset at list position '{i}'. '{e!s}'.")
|
LOG.error(f"Failed to parse '{self._file}:{i}'. '{e!s}'.")
|
||||||
continue
|
continue
|
||||||
|
|
||||||
if need_save:
|
if need_save:
|
||||||
LOG.info("Saving presets due to format, or id change.")
|
LOG.info(f"Saving '{self._file}' due to changes.")
|
||||||
self.save(self._presets)
|
self.save(self._items)
|
||||||
|
|
||||||
return self
|
return self
|
||||||
|
|
||||||
def clear(self) -> "Presets":
|
def clear(self) -> "Presets":
|
||||||
"""
|
"""
|
||||||
Clear all presets
|
Clear all items.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
Presets: The current instance.
|
Presets: The current instance.
|
||||||
|
|
||||||
"""
|
"""
|
||||||
if len(self._presets) < 1:
|
if len(self._items) < 1:
|
||||||
return self
|
return self
|
||||||
|
|
||||||
self._presets.clear()
|
self._items.clear()
|
||||||
|
|
||||||
return self
|
return self
|
||||||
|
|
||||||
def validate(self, preset: Preset | dict) -> bool:
|
def validate(self, item: Preset | dict) -> bool:
|
||||||
"""
|
"""
|
||||||
Validate the preset.
|
Validate the item.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
preset (Preset|dict): The preset to validate.
|
item (Preset|dict): The item to validate.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
bool: True if the preset is valid, False otherwise.
|
bool: True if valid
|
||||||
|
|
||||||
|
Raises:
|
||||||
|
ValueError: If the item is not valid.
|
||||||
|
|
||||||
"""
|
"""
|
||||||
if not isinstance(preset, dict):
|
if not isinstance(item, dict):
|
||||||
if not isinstance(preset, Preset):
|
if not isinstance(item, Preset):
|
||||||
msg = f"Invalid preset type. Was expecting a (Preset|dict), but got '{type(preset).__name__}'."
|
msg = f"Unexpected '{type(item).__name__}' type was given."
|
||||||
raise ValueError(msg) # noqa: TRY004
|
raise ValueError(msg) # noqa: TRY004
|
||||||
|
|
||||||
preset = preset.serialize()
|
item = item.serialize()
|
||||||
|
|
||||||
if not preset.get("id"):
|
if not item.get("id"):
|
||||||
msg = "No id found."
|
msg = "No id found."
|
||||||
raise ValueError(msg)
|
raise ValueError(msg)
|
||||||
|
|
||||||
if not preset.get("name"):
|
if not item.get("name"):
|
||||||
msg = "No name found."
|
msg = "No name found."
|
||||||
raise ValueError(msg)
|
raise ValueError(msg)
|
||||||
|
|
||||||
if not preset.get("format"):
|
if item.get("cli"):
|
||||||
msg = "No format found."
|
|
||||||
raise ValueError(msg)
|
|
||||||
|
|
||||||
if preset.get("cli"):
|
|
||||||
try:
|
try:
|
||||||
arg_converter(args=preset.get("cli"))
|
arg_converter(args=item.get("cli"))
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
msg = f"Invalid cli options. '{e!s}'."
|
msg = f"Invalid cli options. '{e!s}'."
|
||||||
raise ValueError(msg) from e
|
raise ValueError(msg) from e
|
||||||
|
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def save(self, presets: list[Preset | dict]) -> "Presets":
|
def save(self, items: list[Preset | dict]) -> "Presets":
|
||||||
"""
|
"""
|
||||||
Save the presets.
|
Save the items.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
presets (list[Preset]): The presets to save.
|
items (list[Preset]): The items to save.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
Presets: The current instance.
|
Presets: The current instance.
|
||||||
|
|
||||||
"""
|
"""
|
||||||
for i, preset in enumerate(presets):
|
for i, preset in enumerate(items):
|
||||||
try:
|
try:
|
||||||
if not isinstance(preset, Preset):
|
if not isinstance(preset, Preset):
|
||||||
preset = Preset(**preset)
|
preset = Preset(**preset)
|
||||||
presets[i] = preset
|
items[i] = preset
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
LOG.error(f"Failed to save preset '{i}' due to parsing error. '{e!s}'.")
|
LOG.error(f"Failed to save item '{i}' due to parsing error. '{e!s}'.")
|
||||||
continue
|
continue
|
||||||
|
|
||||||
try:
|
try:
|
||||||
self.validate(preset)
|
self.validate(preset)
|
||||||
except ValueError as e:
|
except ValueError as e:
|
||||||
LOG.error(f"Failed to validate preset '{i}: {preset.name}'. '{e}'.")
|
LOG.error(f"Failed to validate item '{i}: {preset.name}'. '{e}'.")
|
||||||
continue
|
continue
|
||||||
|
|
||||||
try:
|
try:
|
||||||
with open(self._file, "w") as f:
|
with open(self._file, "w") as f:
|
||||||
json.dump(obj=[preset.serialize() for preset in presets if preset.default is False], fp=f, indent=4)
|
json.dump(obj=[preset.serialize() for preset in items if preset.default is False], fp=f, indent=4)
|
||||||
|
|
||||||
LOG.info(f"Presets saved to '{self._file}'.")
|
LOG.info(f"Saved '{self._file}'.")
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
LOG.error(f"Failed to save presets to '{self._file}'. '{e!s}'.")
|
LOG.error(f"Failed to save '{self._file}'. '{e!s}'.")
|
||||||
|
|
||||||
return self
|
return self
|
||||||
|
|
||||||
def has(self, id_or_name: str) -> bool:
|
def has(self, id_or_name: str) -> bool:
|
||||||
"""
|
"""
|
||||||
Check if the preset exists by id or name.
|
Check if the item exists by id or name.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
id_or_name (str): The id or name of the preset.
|
id_or_name (str): The id or name of the item.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
bool: True if the preset exists, False otherwise.
|
bool: True if exists, False otherwise.
|
||||||
|
|
||||||
"""
|
"""
|
||||||
return self.get(id_or_name) is not None
|
return self.get(id_or_name) is not None
|
||||||
|
|
||||||
def get(self, id_or_name: str) -> Preset | None:
|
def get(self, id_or_name: str) -> Preset | None:
|
||||||
"""
|
"""
|
||||||
Get the preset by id or name.
|
Get the item by id or name.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
id_or_name (str): The id or name of the preset.
|
id_or_name (str): The id or name of the item.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
Preset|None: The preset if found, None otherwise.
|
Preset|None: The item if found, None otherwise.
|
||||||
|
|
||||||
"""
|
"""
|
||||||
if not id_or_name:
|
if not id_or_name:
|
||||||
|
|
|
||||||
|
|
@ -135,9 +135,6 @@ class YTDLPOpts(metaclass=Singleton):
|
||||||
|
|
||||||
self._preset_opts["cookiefile"] = str(file)
|
self._preset_opts["cookiefile"] = str(file)
|
||||||
|
|
||||||
if preset.format:
|
|
||||||
self._preset_opts["format"] = preset.format
|
|
||||||
|
|
||||||
if preset.template:
|
if preset.template:
|
||||||
self._preset_opts["outtmpl"] = {"default": preset.template, "chapter": self._config.output_template_chapter}
|
self._preset_opts["outtmpl"] = {"default": preset.template, "chapter": self._config.output_template_chapter}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -2,7 +2,6 @@
|
||||||
{
|
{
|
||||||
"id": "3e163c6c-64eb-4448-924f-814b629b3810",
|
"id": "3e163c6c-64eb-4448-924f-814b629b3810",
|
||||||
"name": "default",
|
"name": "default",
|
||||||
"format": "default",
|
|
||||||
"folder": "",
|
"folder": "",
|
||||||
"template": "",
|
"template": "",
|
||||||
"cookies": "",
|
"cookies": "",
|
||||||
|
|
@ -12,41 +11,37 @@
|
||||||
{
|
{
|
||||||
"id": "5bf9c42b-8852-468a-99f5-915622dfba25",
|
"id": "5bf9c42b-8852-468a-99f5-915622dfba25",
|
||||||
"name": "Best video and audio",
|
"name": "Best video and audio",
|
||||||
"format": "bv+ba/b",
|
|
||||||
"folder": "",
|
"folder": "",
|
||||||
"template": "",
|
"template": "",
|
||||||
"cookies": "",
|
"cookies": "",
|
||||||
"cli": "",
|
"cli": "--format 'bv+ba/b'",
|
||||||
"default": true
|
"default": true
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"id": "441675ed-b739-40f0-a0b0-1ecfcb9dc48b",
|
"id": "441675ed-b739-40f0-a0b0-1ecfcb9dc48b",
|
||||||
"name": "1080p H264/m4a or best available",
|
"name": "1080p H264/m4a or best available",
|
||||||
"format": "bv[height<=1080][ext=mp4]+ba[ext=m4a]/b[ext=mp4]/b[ext=webm]",
|
|
||||||
"folder": "",
|
"folder": "",
|
||||||
"template": "",
|
"template": "",
|
||||||
"cookies": "",
|
"cookies": "",
|
||||||
"cli": "-S vcodec:h264",
|
"cli": "-S vcodec:h264 --format 'bv[height<=1080][ext=mp4]+ba[ext=m4a]/b[ext=mp4]/b[ext=webm]'",
|
||||||
"default": true
|
"default": true
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"id": "9719fcc3-4cf2-4d88-b1e4-74dff3dba00e",
|
"id": "9719fcc3-4cf2-4d88-b1e4-74dff3dba00e",
|
||||||
"name": "720p h264/m4a or best available",
|
"name": "720p h264/m4a or best available",
|
||||||
"format": "bv[height<=720][ext=mp4]+ba[ext=m4a]/b[ext=mp4]/b[ext=webm]",
|
|
||||||
"folder": "",
|
"folder": "",
|
||||||
"template": "",
|
"template": "",
|
||||||
"cookies": "",
|
"cookies": "",
|
||||||
"cli": "-S vcodec:h264",
|
"cli": "-S vcodec:h264 --format 'bv[height<=720][ext=mp4]+ba[ext=m4a]/b[ext=mp4]/b[ext=webm]'",
|
||||||
"default": true
|
"default": true
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"id": "a6fd4b25-2b3e-458d-bb57-b75e41cc4330",
|
"id": "a6fd4b25-2b3e-458d-bb57-b75e41cc4330",
|
||||||
"name": "Audio only",
|
"name": "Audio only",
|
||||||
"format": "bestaudio/best",
|
|
||||||
"folder": "",
|
"folder": "",
|
||||||
"template": "",
|
"template": "",
|
||||||
"cookies": "",
|
"cookies": "",
|
||||||
"cli": "--extract-audio --add-chapters --embed-metadata --embed-thumbnail",
|
"cli": "--extract-audio --add-chapters --embed-metadata --embed-thumbnail --format 'bestaudio/best'",
|
||||||
"default": true
|
"default": true
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
|
|
|
||||||
|
|
@ -49,7 +49,7 @@
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="column is-6-tablet is-12-mobile">
|
<div class="column is-12">
|
||||||
<div class="field">
|
<div class="field">
|
||||||
<label class="label is-inline" for="name">
|
<label class="label is-inline" for="name">
|
||||||
<span class="icon"><i class="fa-solid fa-tag" /></span>
|
<span class="icon"><i class="fa-solid fa-tag" /></span>
|
||||||
|
|
@ -65,26 +65,7 @@
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="column is-6-tablet is-12-mobile">
|
<div class="column is-12">
|
||||||
<div class="field">
|
|
||||||
<label class="label is-inline" for="format">
|
|
||||||
<span class="icon"><i class="fa-solid fa-f" /></span>
|
|
||||||
Format
|
|
||||||
</label>
|
|
||||||
<div class="control">
|
|
||||||
<input type="text" class="input" id="format" v-model="form.format" :disabled="addInProgress">
|
|
||||||
</div>
|
|
||||||
<span class="help">
|
|
||||||
<span class="icon"><i class="fa-solid fa-info" /></span>
|
|
||||||
<span>The yt-dlp <code>[--format, -f]</code> video format code. see <NuxtLink
|
|
||||||
href="https://github.com/yt-dlp/yt-dlp?tab=readme-ov-file#format-selection" target="blank">this
|
|
||||||
page</NuxtLink> for more info. Note, as this key is required, you can set the value to
|
|
||||||
<code>default</code> to let <code>yt-dlp</code> choose the best format.</span>
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="column is-6-tablet is-12-mobile">
|
|
||||||
<div class="field">
|
<div class="field">
|
||||||
<label class="label is-inline" for="folder">
|
<label class="label is-inline" for="folder">
|
||||||
<span class="icon"><i class="fa-solid fa-folder" /></span>
|
<span class="icon"><i class="fa-solid fa-folder" /></span>
|
||||||
|
|
@ -102,7 +83,7 @@
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="column is-6-tablet is-12-mobile">
|
<div class="column is-12">
|
||||||
<div class="field">
|
<div class="field">
|
||||||
<label class="label is-inline" for="output_template">
|
<label class="label is-inline" for="output_template">
|
||||||
<span class="icon"><i class="fa-solid fa-file" /></span>
|
<span class="icon"><i class="fa-solid fa-file" /></span>
|
||||||
|
|
@ -127,7 +108,7 @@
|
||||||
<div class="field">
|
<div class="field">
|
||||||
<label class="label is-inline" for="cli_options">
|
<label class="label is-inline" for="cli_options">
|
||||||
<span class="icon"><i class="fa-solid fa-terminal" /></span>
|
<span class="icon"><i class="fa-solid fa-terminal" /></span>
|
||||||
Command arguments for yt-dlp
|
Command options for yt-dlp
|
||||||
</label>
|
</label>
|
||||||
<div class="control">
|
<div class="control">
|
||||||
<textarea class="textarea is-pre" v-model="form.cli" id="cli_options" :disabled="addInProgress"
|
<textarea class="textarea is-pre" v-model="form.cli" id="cli_options" :disabled="addInProgress"
|
||||||
|
|
@ -241,8 +222,7 @@ onMounted(() => {
|
||||||
})
|
})
|
||||||
|
|
||||||
const checkInfo = async () => {
|
const checkInfo = async () => {
|
||||||
const required = ['name', 'format'];
|
for (const key of ['name']) {
|
||||||
for (const key of required) {
|
|
||||||
if (!form[key]) {
|
if (!form[key]) {
|
||||||
toast.error(`The ${key} field is required.`);
|
toast.error(`The ${key} field is required.`);
|
||||||
return
|
return
|
||||||
|
|
@ -299,10 +279,6 @@ const convertOptions = async args => {
|
||||||
form.folder = response.download_path
|
form.folder = response.download_path
|
||||||
}
|
}
|
||||||
|
|
||||||
if (response.format) {
|
|
||||||
form.format = response.format
|
|
||||||
}
|
|
||||||
|
|
||||||
return response.opts
|
return response.opts
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
toast.error(e.message)
|
toast.error(e.message)
|
||||||
|
|
@ -336,7 +312,7 @@ const importItem = async () => {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((form.format || form.cli) && false === confirm('This will overwrite the current data. Are you sure?')) {
|
if (form.cli && false === confirm('This will overwrite the current data. Are you sure?')) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -344,14 +320,20 @@ const importItem = async () => {
|
||||||
form.name = item.name
|
form.name = item.name
|
||||||
}
|
}
|
||||||
|
|
||||||
if (item.format) {
|
|
||||||
form.format = item.format
|
|
||||||
}
|
|
||||||
|
|
||||||
if (item.cli) {
|
if (item.cli) {
|
||||||
form.cli = item.cli
|
form.cli = item.cli
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// -- backwards compatibility for old presets.
|
||||||
|
if (item.format) {
|
||||||
|
if (!item?.cli) {
|
||||||
|
form.cli = `--format '${item.format}'`
|
||||||
|
} else {
|
||||||
|
form.cli = `--format '${item.format}'\n${form.cli}`
|
||||||
|
}
|
||||||
|
form.cli = form.cli.trim()
|
||||||
|
}
|
||||||
|
|
||||||
if (item.template) {
|
if (item.template) {
|
||||||
form.template = item.template
|
form.template = item.template
|
||||||
}
|
}
|
||||||
|
|
@ -364,7 +346,7 @@ const importItem = async () => {
|
||||||
showImport.value = false
|
showImport.value = false
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
console.error(e)
|
console.error(e)
|
||||||
toast.error(`Failed to string. ${e.message}`)
|
toast.error(`Failed to parse string. ${e.message}`)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -71,11 +71,6 @@ div.is-centered {
|
||||||
</header>
|
</header>
|
||||||
<div class="card-content is-flex-grow-1">
|
<div class="card-content is-flex-grow-1">
|
||||||
<div class="content">
|
<div class="content">
|
||||||
<p class="is-text-overflow"
|
|
||||||
v-if="item?.format && false === ['default', 'not_set'].includes(item.format)">
|
|
||||||
<span class="icon"><i class="fa-solid fa-f" /></span>
|
|
||||||
<span v-text="item.format" />
|
|
||||||
</p>
|
|
||||||
<p class="is-text-overflow" v-if="item.folder">
|
<p class="is-text-overflow" v-if="item.folder">
|
||||||
<span class="icon"><i class="fa-solid fa-folder" /></span>
|
<span class="icon"><i class="fa-solid fa-folder" /></span>
|
||||||
<span>{{ calcPath(item.folder) }}</span>
|
<span>{{ calcPath(item.folder) }}</span>
|
||||||
|
|
@ -322,7 +317,7 @@ const exportItem = item => {
|
||||||
}
|
}
|
||||||
|
|
||||||
userData['_type'] = 'preset'
|
userData['_type'] = 'preset'
|
||||||
userData['_version'] = '2.0'
|
userData['_version'] = '2.5'
|
||||||
|
|
||||||
return copyText(base64UrlEncode(JSON.stringify(userData)))
|
return copyText(base64UrlEncode(JSON.stringify(userData)))
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue