fixes
This commit is contained in:
27
CLI.py
27
CLI.py
@@ -886,32 +886,9 @@ def _execute_pipeline(tokens: list):
|
|||||||
source_args = ctx.get_last_result_table_source_args()
|
source_args = ctx.get_last_result_table_source_args()
|
||||||
|
|
||||||
if source_cmd == 'search-file' and source_args and 'youtube' in source_args:
|
if source_cmd == 'search-file' and source_args and 'youtube' in source_args:
|
||||||
|
# Only auto-pipe if no other stages follow (stages is empty because we popped the selection)
|
||||||
|
if not stages:
|
||||||
print(f"Auto-piping YouTube selection to .pipe")
|
print(f"Auto-piping YouTube selection to .pipe")
|
||||||
# We can't modify stages here easily as we are outside the loop or before it?
|
|
||||||
# Actually, this block runs BEFORE the loop if stages[0] is a selection.
|
|
||||||
# But wait, the loop iterates over stages.
|
|
||||||
# If we are here, it means we handled the selection by filtering `piped_result`.
|
|
||||||
# The loop will then execute stages starting from 0?
|
|
||||||
# No, `_execute_pipeline` logic is complex.
|
|
||||||
|
|
||||||
# Let's look at where this block is.
|
|
||||||
# It is inside `_execute_pipeline`.
|
|
||||||
# It runs if `first_stage_selection_indices` is set (meaning stages[0] was a selection).
|
|
||||||
# And `command_expanded` is False (meaning we didn't replace stages[0] with a command).
|
|
||||||
|
|
||||||
# If we are here, `piped_result` holds the selected item(s).
|
|
||||||
# The loop below iterates `for stage_index, stage_tokens in enumerate(stages):`
|
|
||||||
# But we removed the first stage from `stages`? No.
|
|
||||||
|
|
||||||
# Wait, let's check how `first_stage_selection_indices` is used.
|
|
||||||
# It seems `stages` is modified earlier?
|
|
||||||
# "if stages and stages[0] and stages[0][0].startswith('@'): ... stages.pop(0)"
|
|
||||||
|
|
||||||
# Yes, lines 750-760 (approx) pop the first stage if it is a selection.
|
|
||||||
# So `stages` now contains the REST of the pipeline.
|
|
||||||
# If user typed just `@1`, `stages` is now empty `[]`.
|
|
||||||
|
|
||||||
# So if we want to pipe to `.pipe`, we should append `.pipe` to `stages`.
|
|
||||||
stages.append(['.pipe'])
|
stages.append(['.pipe'])
|
||||||
|
|
||||||
else:
|
else:
|
||||||
|
|||||||
@@ -453,10 +453,10 @@ def _handle_search_result(result: Any, args: Sequence[str], config: Dict[str, An
|
|||||||
if storage_name.lower() == 'hydrus':
|
if storage_name.lower() == 'hydrus':
|
||||||
return _handle_hydrus_file(file_hash, file_title, config, args, mime_type=mime_type)
|
return _handle_hydrus_file(file_hash, file_title, config, args, mime_type=mime_type)
|
||||||
elif storage_name.lower() == 'local':
|
elif storage_name.lower() == 'local':
|
||||||
return _handle_local_file(file_path, file_title, args, file_hash=file_hash)
|
return _handle_local_file(file_path, file_title, config, args, file_hash=file_hash)
|
||||||
elif storage_name.lower() == 'download':
|
elif storage_name.lower() == 'download':
|
||||||
# Downloads are local files
|
# Downloads are local files
|
||||||
return _handle_local_file(file_path, file_title, args, file_hash=file_hash)
|
return _handle_local_file(file_path, file_title, config, args, file_hash=file_hash)
|
||||||
elif storage_name.lower() == 'debrid':
|
elif storage_name.lower() == 'debrid':
|
||||||
# Extract magnet_id from result (search-file stores it in full_metadata or as custom attribute)
|
# Extract magnet_id from result (search-file stores it in full_metadata or as custom attribute)
|
||||||
if not magnet_id:
|
if not magnet_id:
|
||||||
@@ -591,7 +591,7 @@ def _handle_hydrus_file(file_hash: Optional[str], file_title: str, config: Dict[
|
|||||||
return 1
|
return 1
|
||||||
|
|
||||||
|
|
||||||
def _handle_local_file(file_path: Optional[str], file_title: str, args: Sequence[str], file_hash: Optional[str] = None) -> int:
|
def _handle_local_file(file_path: Optional[str], file_title: str, config: Dict[str, Any], args: Sequence[str], file_hash: Optional[str] = None) -> int:
|
||||||
"""Handle file from local storage - auto-play in MPV if media, otherwise open with default app."""
|
"""Handle file from local storage - auto-play in MPV if media, otherwise open with default app."""
|
||||||
if not file_path:
|
if not file_path:
|
||||||
log("Error: No file path provided", file=sys.stderr)
|
log("Error: No file path provided", file=sys.stderr)
|
||||||
|
|||||||
@@ -128,6 +128,17 @@ def _run(result: Any, args: Sequence[str], config: Dict[str, Any]) -> int:
|
|||||||
debug("Failed to pause playback (MPV not running?)", file=sys.stderr)
|
debug("Failed to pause playback (MPV not running?)", file=sys.stderr)
|
||||||
return 1
|
return 1
|
||||||
|
|
||||||
|
# Handle Clear All command (no index provided)
|
||||||
|
if clear_mode and index_arg is None:
|
||||||
|
cmd = {"command": ["playlist-clear"], "request_id": 105}
|
||||||
|
resp = _send_ipc_command(cmd)
|
||||||
|
if resp and resp.get("error") == "success":
|
||||||
|
debug("Playlist cleared")
|
||||||
|
return 0
|
||||||
|
else:
|
||||||
|
debug("Failed to clear playlist (MPV not running?)", file=sys.stderr)
|
||||||
|
return 1
|
||||||
|
|
||||||
# Handle piped input (add to playlist)
|
# Handle piped input (add to playlist)
|
||||||
if result:
|
if result:
|
||||||
# If result is a list of items, add them to playlist
|
# If result is a list of items, add them to playlist
|
||||||
@@ -366,7 +377,7 @@ CMDLET = Cmdlet(
|
|||||||
CmdletArg(
|
CmdletArg(
|
||||||
name="clear",
|
name="clear",
|
||||||
type="flag",
|
type="flag",
|
||||||
description="Remove the selected item from the playlist"
|
description="Remove the selected item, or clear entire playlist if no index provided"
|
||||||
),
|
),
|
||||||
CmdletArg(
|
CmdletArg(
|
||||||
name="list",
|
name="list",
|
||||||
|
|||||||
@@ -54,9 +54,16 @@ def _progress_callback(status: Dict[str, Any]) -> None:
|
|||||||
if event == "downloading":
|
if event == "downloading":
|
||||||
percent = status.get("_percent_str", "?")
|
percent = status.get("_percent_str", "?")
|
||||||
speed = status.get("_speed_str", "?")
|
speed = status.get("_speed_str", "?")
|
||||||
debug(f"Downloading {percent} at {speed}")
|
eta = status.get("_eta_str", "?")
|
||||||
|
# Print progress to stdout with carriage return to update in place
|
||||||
|
sys.stdout.write(f"\r[download] {percent} at {speed} ETA {eta} ")
|
||||||
|
sys.stdout.flush()
|
||||||
elif event == "finished":
|
elif event == "finished":
|
||||||
debug(f"✓ Download finished: {status.get('filename')}")
|
# Clear the progress line
|
||||||
|
sys.stdout.write("\r" + " " * 70 + "\r")
|
||||||
|
sys.stdout.flush()
|
||||||
|
# Log finished message (visible)
|
||||||
|
log(f"✓ Download finished: {status.get('filename')}")
|
||||||
elif event in ("postprocessing", "processing"):
|
elif event in ("postprocessing", "processing"):
|
||||||
debug(f"Post-processing: {status.get('postprocessor')}")
|
debug(f"Post-processing: {status.get('postprocessor')}")
|
||||||
|
|
||||||
@@ -100,8 +107,8 @@ def list_formats(url: str, no_playlist: bool = False, playlist_items: Optional[s
|
|||||||
|
|
||||||
try:
|
try:
|
||||||
ydl_opts = {
|
ydl_opts = {
|
||||||
"quiet": False,
|
"quiet": True,
|
||||||
"no_warnings": False,
|
"no_warnings": True,
|
||||||
"socket_timeout": 30,
|
"socket_timeout": 30,
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -154,9 +161,9 @@ def _build_ytdlp_options(opts: DownloadOptions) -> Dict[str, Any]:
|
|||||||
|
|
||||||
base_options: Dict[str, Any] = {
|
base_options: Dict[str, Any] = {
|
||||||
"outtmpl": outtmpl,
|
"outtmpl": outtmpl,
|
||||||
"quiet": False,
|
"quiet": True,
|
||||||
"no_warnings": False,
|
"no_warnings": True,
|
||||||
"noprogress": False,
|
"noprogress": True,
|
||||||
"socket_timeout": 30,
|
"socket_timeout": 30,
|
||||||
"retries": 10,
|
"retries": 10,
|
||||||
"fragment_retries": 10,
|
"fragment_retries": 10,
|
||||||
|
|||||||
Reference in New Issue
Block a user