feat(stream): require auth on GET /stream/{id} via token query param
The audio stream endpoint was unauthenticated. Add a get_streaming_user dependency that accepts the access token either as a ?token= query param (the browser <audio> element can't send an Authorization header) or a bearer header for native clients. Update streaming tests accordingly and add a test asserting unauthenticated requests are rejected with 401. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -143,7 +143,8 @@ async def test_stream_full(api: AsyncClient) -> None:
|
||||
assert up.status_code == 200
|
||||
track_id = up.json()["track_id"]
|
||||
|
||||
resp = await api.get(f"/api/v1/stream/{track_id}")
|
||||
# Browser <audio> can't send headers — auth rides on the ?token= query param.
|
||||
resp = await api.get(f"/api/v1/stream/{track_id}?token={token}")
|
||||
assert resp.status_code == 200
|
||||
assert resp.content == audio
|
||||
assert resp.headers["content-type"].startswith("audio/mpeg")
|
||||
@@ -164,7 +165,7 @@ async def test_stream_range(api: AsyncClient) -> None:
|
||||
|
||||
resp = await api.get(
|
||||
f"/api/v1/stream/{track_id}",
|
||||
headers={"Range": "bytes=0-9"},
|
||||
headers={"Range": "bytes=0-9", "Authorization": f"Bearer {token}"},
|
||||
)
|
||||
assert resp.status_code == 206
|
||||
assert resp.content == b"0123456789"
|
||||
@@ -173,10 +174,18 @@ async def test_stream_range(api: AsyncClient) -> None:
|
||||
|
||||
|
||||
async def test_stream_not_found(api: AsyncClient) -> None:
|
||||
resp = await api.get("/api/v1/stream/00000000-0000-0000-0000-000000000000")
|
||||
token = await _login(api)
|
||||
resp = await api.get(
|
||||
f"/api/v1/stream/00000000-0000-0000-0000-000000000000?token={token}"
|
||||
)
|
||||
assert resp.status_code == 404
|
||||
|
||||
|
||||
async def test_stream_requires_auth(api: AsyncClient) -> None:
|
||||
resp = await api.get("/api/v1/stream/00000000-0000-0000-0000-000000000000")
|
||||
assert resp.status_code == 401
|
||||
|
||||
|
||||
async def test_upload_requires_auth(api: AsyncClient) -> None:
|
||||
resp = await api.post(
|
||||
"/api/v1/upload",
|
||||
|
||||
Reference in New Issue
Block a user