Skip to content

Commit c44cc24

Browse files
committed
Address Copilot PR review: reject unknown archive formats, fix case-sensitive check
- Add explanatory comment to empty except KeyError block in _extract_workflow_yml - Use case-insensitive extension matching for local archive detection in workflow add - Reject unknown archive formats with clear error messages instead of silently defaulting to ZIP in preset add --from, extension add --from, download_extension(), and download_pack()
1 parent 0c6cc45 commit c44cc24

3 files changed

Lines changed: 22 additions & 2 deletions

File tree

src/specify_cli/__init__.py

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2643,6 +2643,11 @@ def preset_add(
26432643
console.print(f"[red]Error:[/red] Failed to download: {e}")
26442644
raise typer.Exit(1)
26452645

2646+
if not archive_fmt:
2647+
console.print("[red]Error:[/red] Could not determine archive format from URL or Content-Type.")
2648+
console.print("Ensure the URL points to a .zip or .tar.gz file.")
2649+
raise typer.Exit(1)
2650+
26462651
suffix = ".tar.gz" if archive_fmt == "tar.gz" else ".zip"
26472652
archive_path = Path(tmpdir) / f"preset{suffix}"
26482653
archive_path.write_bytes(archive_data)
@@ -3652,6 +3657,11 @@ def extension_add(
36523657
archive_fmt = _detect_archive_format(from_url, content_type)
36533658
archive_data = response.read()
36543659

3660+
if not archive_fmt:
3661+
console.print("[red]Error:[/red] Could not determine archive format from URL or Content-Type.")
3662+
console.print("Ensure the URL points to a .zip or .tar.gz file.")
3663+
raise typer.Exit(1)
3664+
36553665
suffix = ".tar.gz" if archive_fmt == "tar.gz" else ".zip"
36563666
archive_path = download_dir / f"{extension}-url-download{suffix}"
36573667
archive_path.write_bytes(archive_data)
@@ -4936,7 +4946,7 @@ def _extract_workflow_yml(archive_path: Path, archive_fmt: str) -> bytes:
49364946
if f is not None:
49374947
return f.read()
49384948
except KeyError:
4939-
pass
4949+
pass # Root-level workflow.yml not found; fall through to subdirectory search below.
49404950
# Look in a single top-level subdirectory.
49414951
candidates = [
49424952
m for m in tf.getmembers()
@@ -5099,7 +5109,7 @@ def _validate_and_install_local(yaml_path: Path, source_label: str) -> None:
50995109
_validate_and_install_local(source_path, str(source_path))
51005110
return
51015111
elif source_path.is_file() and (
5102-
source.endswith(".tar.gz") or source.endswith(".tgz") or source.endswith(".zip")
5112+
source.lower().endswith(".tar.gz") or source.lower().endswith(".tgz") or source.lower().endswith(".zip")
51035113
):
51045114
# Local archive file containing workflow.yml
51055115
from .extensions import _detect_archive_format

src/specify_cli/extensions.py

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2151,6 +2151,11 @@ def download_extension(self, extension_id: str, target_dir: Optional[Path] = Non
21512151
raise ExtensionError(f"Failed to save extension archive: {e}")
21522152

21532153
# Choose file extension based on detected format.
2154+
if not archive_fmt:
2155+
raise ExtensionError(
2156+
f"Could not determine archive format for {download_url}. "
2157+
"Ensure the URL points to a .zip or .tar.gz file."
2158+
)
21542159
if archive_fmt == "tar.gz":
21552160
archive_filename = f"{extension_id}-{version}.tar.gz"
21562161
else:

src/specify_cli/presets.py

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2331,6 +2331,11 @@ def download_pack(
23312331
raise PresetError(f"Failed to save preset archive: {e}")
23322332

23332333
# Choose file extension based on detected format.
2334+
if not archive_fmt:
2335+
raise PresetError(
2336+
f"Could not determine archive format for {download_url}. "
2337+
"Ensure the URL points to a .zip or .tar.gz file."
2338+
)
23342339
if archive_fmt == "tar.gz":
23352340
archive_filename = f"{pack_id}-{version}.tar.gz"
23362341
else:

0 commit comments

Comments
 (0)