security: fix #1 — wire SSRF hook into detect_site_type client
detect_site_type constructs a fresh BooruClient._shared_client directly (bypassing the BooruClient.client property) for the /posts.json, /index.php, and /post.json probes. The hooks set here are the ones installed on that initial construction — if detection runs before any BooruClient instance's .client is accessed, the shared singleton must still have SSRF validation and connection logging. This additionally closes finding #16 for the detect client — site detection requests now appear in the connection log instead of being invisible. behavior change from v0.2.5: Test Connection from the site dialog now rejects private-IP targets. Adding a local/RFC1918 booru via the "auto-detect type" dialog will fail with "blocked request target ..." instead of probing it. Explicit api_type selection still goes through the BooruClient.client path, which is also now protected. Audit-Ref: SECURITY_AUDIT.md finding #1 Also-Closes: SECURITY_AUDIT.md finding #16 (detect half) Severity: High
This commit is contained in:
parent
ef95509551
commit
c735db0c68
@ -7,6 +7,7 @@ import logging
|
|||||||
import httpx
|
import httpx
|
||||||
|
|
||||||
from ..config import USER_AGENT
|
from ..config import USER_AGENT
|
||||||
|
from ._safety import validate_public_request
|
||||||
from .danbooru import DanbooruClient
|
from .danbooru import DanbooruClient
|
||||||
from .gelbooru import GelbooruClient
|
from .gelbooru import GelbooruClient
|
||||||
from .moebooru import MoebooruClient
|
from .moebooru import MoebooruClient
|
||||||
@ -28,12 +29,20 @@ async def detect_site_type(
|
|||||||
url = url.rstrip("/")
|
url = url.rstrip("/")
|
||||||
|
|
||||||
from .base import BooruClient as _BC
|
from .base import BooruClient as _BC
|
||||||
# Reuse shared client for site detection
|
# Reuse shared client for site detection. event_hooks mirrors
|
||||||
|
# BooruClient.client so detection requests get the same SSRF
|
||||||
|
# validation and connection logging as regular API calls.
|
||||||
if _BC._shared_client is None or _BC._shared_client.is_closed:
|
if _BC._shared_client is None or _BC._shared_client.is_closed:
|
||||||
_BC._shared_client = httpx.AsyncClient(
|
_BC._shared_client = httpx.AsyncClient(
|
||||||
headers={"User-Agent": USER_AGENT},
|
headers={"User-Agent": USER_AGENT},
|
||||||
follow_redirects=True,
|
follow_redirects=True,
|
||||||
timeout=20.0,
|
timeout=20.0,
|
||||||
|
event_hooks={
|
||||||
|
"request": [
|
||||||
|
validate_public_request,
|
||||||
|
_BC._log_request,
|
||||||
|
],
|
||||||
|
},
|
||||||
limits=httpx.Limits(max_connections=10, max_keepalive_connections=5),
|
limits=httpx.Limits(max_connections=10, max_keepalive_connections=5),
|
||||||
)
|
)
|
||||||
client = _BC._shared_client
|
client = _BC._shared_client
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user