unsloth/tests/studio/test_tauri_python_tool_images.py
oobabooga 0ca37e57ad
Some checks are pending
Core / Core (HF=default + TRL=default) (push) Waiting to run
Core / Core (HF=4.57.6 + TRL<1) (push) Waiting to run
Core / Core (HF=latest + TRL=latest) (push) Waiting to run
Local Agent Guides CI / connection (codex) (push) Waiting to run
Local Agent Guides CI / connection (hermes) (push) Waiting to run
Local Agent Guides CI / connection (openclaw) (push) Waiting to run
Local Agent Guides CI / connection (opencode) (push) Waiting to run
Core / llama.cpp build + smoke (push) Waiting to run
Lint CI / Source lint (Python + shell + YAML + JSON + safety nets) (push) Waiting to run
Local Agent Guides CI / prompt-cache (gemma-3-270m) (push) Waiting to run
Local Agent Guides CI / connection (claude) (push) Waiting to run
Local Agent Guides CI / connection (pi) (push) Waiting to run
Local Agent Guides CI / file-edit (claude) (push) Waiting to run
Local Agent Guides CI / file-edit (codex) (push) Waiting to run
Local Agent Guides CI / resume (pi) (push) Waiting to run
Lockfile supply-chain audit / lockfile supply-chain audit (push) Waiting to run
Local Agent Guides CI / file-edit (hermes) (push) Waiting to run
Local Agent Guides CI / file-edit (openclaw) (push) Waiting to run
Local Agent Guides CI / file-edit (opencode) (push) Waiting to run
Local Agent Guides CI / file-edit (pi) (push) Waiting to run
Local Agent Guides CI / resume (claude) (push) Waiting to run
Local Agent Guides CI / resume (codex) (push) Waiting to run
Local Agent Guides CI / resume (opencode) (push) Waiting to run
Scorecard supply-chain security / Scorecard analysis (push) Waiting to run
Security audit / pip scan-packages :: extras (push) Waiting to run
Security audit / pip scan-packages :: studio (push) Waiting to run
Security audit / pip scan-packages :: hf-stack (push) Waiting to run
Security audit / npm scan-packages (Unsloth frontend tarballs) (push) Waiting to run
Security audit / workflow-trigger lint (pull_request_target / cache-poisoning) (push) Waiting to run
Security audit / pytest tests/security (push) Waiting to run
Security audit / npm provenance + new install-script diff (push) Waiting to run
Backend CI / (Python 3.10) (push) Waiting to run
Backend CI / (Python 3.11) (push) Waiting to run
Backend CI / (Python 3.12) (push) Waiting to run
Backend CI / (Python 3.13) (push) Waiting to run
Security audit / advisory audit (pip + npm + cargo) (push) Waiting to run
Unsloth API CI / Unsloth API & Auth Tests (push) Waiting to run
Unsloth export capability / capability (windows-latest) (push) Waiting to run
Unsloth export capability / capability (ubuntu-latest) (push) Waiting to run
Windows Unsloth API CI / Unsloth API & Auth Tests (push) Waiting to run
Windows Unsloth GGUF CI / GGUF inference smoke (API, tools, vision) (push) Waiting to run
Windows Unsloth GGUF CI / Unsloth install + inference without Visual Studio (push) Waiting to run
Backend CI / Repo tests (CPU) (push) Waiting to run
Frontend CI / Frontend build + bundle sanity (push) Waiting to run
Unsloth GGUF CI / OpenAI, Anthropic API tests (push) Waiting to run
Unsloth GGUF CI / Tool calling Tests (push) Waiting to run
Unsloth GGUF CI / JSON, images (push) Waiting to run
Unsloth load-orchestrator CI / test (push) Waiting to run
Mac Studio GGUF CI / GGUF inference smoke (API, tools, vision) (push) Waiting to run
Mac Studio Install Matrix CI / Install + load (macos-15) (push) Waiting to run
Mac Studio Install Matrix CI / Install + load (macos-26) (push) Waiting to run
Mac Studio Install Matrix CI / Install + load (macos-15-intel) (push) Waiting to run
Mac Studio Install Matrix CI / Install + load (macos-26-intel) (push) Waiting to run
Mac Studio UI + API + Update CI / Chat UI, API and Update Tests (push) Waiting to run
Unsloth Tauri CI / Tauri Linux debug build (no codesign) (push) Waiting to run
Unsloth Tauri CI / Rust unit tests (windows) (push) Waiting to run
Unsloth UI CI / Chat UI Tests (push) Waiting to run
Unsloth Update CI / Unsloth Updating Tests (push) Waiting to run
Windows Unsloth UI CI / Chat UI Tests (push) Waiting to run
Wheel CI / Wheel build + content sanity + import smoke (push) Waiting to run
Windows Unsloth GGUF CI / GPU prebuilt resolves without Visual Studio (push) Waiting to run
Windows Unsloth GGUF CI / setup.ps1 unit tests (VS 2026 / CMake guard) (push) Waiting to run
Windows Unsloth GGUF CI / real-VS detection (VS 2022) (push) Waiting to run
Windows Unsloth GGUF CI / real-VS detection (VS 2026) (push) Waiting to run
Windows Unsloth GGUF CI / VC++ runtime detect + install round-trip (windows-2025-vs2026) (push) Waiting to run
Windows Unsloth GGUF CI / VC++ runtime detect + install round-trip (windows-latest) (push) Waiting to run
Windows Unsloth Update CI / Unsloth Updating Tests (push) Waiting to run
Desktop: block HTTP loopback requests from untrusted images (#8046)
2026-08-07 18:56:26 -03:00

61 lines
2.5 KiB
Python

# SPDX-License-Identifier: AGPL-3.0-only
# Copyright 2026-present the Unsloth AI Inc. team. All rights reserved. See /studio/LICENSE.AGPL-3.0
"""Packaged desktop routing contract for Python tool images."""
import json
from pathlib import Path
REPO = Path(__file__).resolve().parents[2]
PYTHON_TOOL_UI = REPO / "studio/frontend/src/components/assistant-ui/tool-ui-python.tsx"
TAURI_CONFIG = REPO / "studio/src-tauri/tauri.conf.json"
PLAYWRIGHT_TEST = REPO / "tests/studio/playwright_tauri_python_tool_images.py"
def test_python_tool_images_use_authenticated_blob_urls() -> None:
source = PYTHON_TOOL_UI.read_text(encoding = "utf-8")
assert 'import { authFetch } from "@/features/auth";' in source
assert "authFetch(" in source
assert "pythonToolImagePath(sessionId, filename)" in source
assert "new AbortController()" in source
assert "new IntersectionObserver(" in source
assert "URL.createObjectURL(blob)" in source
assert "URL.revokeObjectURL(objectUrl)" in source
assert "controller.abort()" in source
assert "apiUrl(`/api/inference/sandbox/" not in source
def test_desktop_csp_has_no_explicit_http_loopback_image_source() -> None:
config = json.loads(TAURI_CONFIG.read_text(encoding = "utf-8"))
csp = config["app"]["security"]["csp"]
directives = {
parts[0]: parts[1:] for directive in csp.split(";") if (parts := directive.strip().split())
}
loopback = [
source for source in directives["img-src"] if "127.0.0.1" in source or "localhost" in source
]
assert loopback == []
assert "blob:" in directives["img-src"]
# The boundary is the HTTP Studio backend regression. Ordinary remote
# HTTPS images remain supported, including HTTPS loopback if its certificate
# is trusted by the host.
assert "https:" in directives["img-src"]
# Trusted frontend fetches and artifact frames still use their existing
# backend channels. Only ordinary image elements lose loopback access.
assert "http://127.0.0.1:*" in directives["connect-src"]
assert "http://127.0.0.1:*" in directives["frame-src"]
def test_redirect_regression_has_a_real_browser_probe() -> None:
source = PLAYWRIGHT_TEST.read_text(encoding = "utf-8")
assert "sync_playwright" in source
assert "https://redirect.invalid/attacker.png" in source
assert '"/sensitive/redirect.png"' in source
assert '"https://127.0.0.1:9443/sensitive/direct.png"' in source
assert "https_loopback_requests == 1" in source
assert "URL.createObjectURL" in source