gabriel / muse public
test_transport_push_mpack_presign.py python
107 lines 4.5 KB
Raw
sha256:79ffe87f5fe2ec146e35f05521218bbf54dffdb0440c07f970bad05f16efb89f chore: merge main — carry all urllib/typing/test fixes from dev Sonnet 4.6 minor ⚠ breaking 19 days ago
1 """TDD — HttpTransport.push_mpack_presign: client-side Step 1 of the mpack push protocol.
2
3 PP-1 Happy path: POST returns {upload_url, mpack_key} — both echoed back correctly.
4 PP-2 The POST body contains mpack_key == blob_id(mpack_bytes) and correct size_bytes.
5 PP-3 The POST is sent to /{owner}/{slug}/push/mpack-presign.
6 PP-4 Non-200 response raises TransportError.
7 PP-5 Response missing upload_url raises TransportError.
8 """
9 from __future__ import annotations
10
11 from unittest.mock import patch
12
13 import msgpack
14 import pytest
15
16 from muse.core.transport import HttpTransport, TransportError
17 from muse.core.types import blob_id
18
19 _URL = "https://staging.musehub.ai/gabriel/muse"
20 _UPLOAD_URL = "https://minio.example.com/mpacks/sha256:abc?sig=fake"
21
22
23 def _presign_response(mpack_key: str, upload_url: str = _UPLOAD_URL) -> bytes:
24 return msgpack.packb(
25 {"upload_url": upload_url, "mpack_key": mpack_key},
26 use_bin_type=True,
27 )
28
29
30 def _mock_urllib_do(body: bytes, status: int = 200) -> "Callable[..., bytes]":
31 calls: list[tuple[str, str, dict, bytes | None]] = []
32
33 def _side_effect(method: str, url: str, headers: "dict[str, str]", data: "bytes | None" = None, **kwargs: "str | int | bool") -> bytes:
34 calls.append((method, url, headers, data))
35 if status >= 400:
36 raise TransportError(f"HTTP {status}", status)
37 return body
38
39 _side_effect.calls = calls
40 return _side_effect
41
42
43 # ── PP-1 ──────────────────────────────────────────────────────────────────────
44
45 def test_pp1_happy_path_returns_upload_url_and_mpack_key() -> None:
46 mpack_bytes = b"fake mpack content"
47 mpack_key = blob_id(mpack_bytes)
48 do = _mock_urllib_do(_presign_response(mpack_key))
49
50 with patch("muse.core.transport._urllib_do", side_effect=do):
51 result = HttpTransport().push_mpack_presign(_URL, None, mpack_bytes)
52
53 assert result["upload_url"] == _UPLOAD_URL
54 assert result["mpack_key"] == mpack_key
55
56
57 # ── PP-2 ──────────────────────────────────────────────────────────────────────
58
59 def test_pp2_post_body_contains_correct_key_and_size() -> None:
60 mpack_bytes = b"x" * 512
61 mpack_key = blob_id(mpack_bytes)
62 do = _mock_urllib_do(_presign_response(mpack_key))
63
64 with patch("muse.core.transport._urllib_do", side_effect=do):
65 HttpTransport().push_mpack_presign(_URL, None, mpack_bytes)
66
67 _, _, _, sent_data = do.calls[0]
68 payload = msgpack.unpackb(sent_data, raw=False)
69 assert payload["mpack_key"] == mpack_key
70 assert payload["size_bytes"] == 512
71
72
73 # ── PP-3 ──────────────────────────────────────────────────────────────────────
74
75 def test_pp3_posts_to_correct_endpoint() -> None:
76 mpack_bytes = b"data"
77 mpack_key = blob_id(mpack_bytes)
78 do = _mock_urllib_do(_presign_response(mpack_key))
79
80 with patch("muse.core.transport._urllib_do", side_effect=do):
81 HttpTransport().push_mpack_presign(_URL, None, mpack_bytes)
82
83 _, url, _, _ = do.calls[0]
84 assert url.endswith("/push/mpack-presign")
85
86
87 # ── PP-4 ──────────────────────────────────────────────────────────────────────
88
89 def test_pp4_non_200_raises_transport_error() -> None:
90 do = _mock_urllib_do(b"quota exceeded", status=429)
91
92 with patch("muse.core.transport._urllib_do", side_effect=do):
93 with pytest.raises(TransportError):
94 HttpTransport().push_mpack_presign(_URL, None, b"bytes")
95
96
97 # ── PP-5 ──────────────────────────────────────────────────────────────────────
98
99 def test_pp5_missing_upload_url_raises_transport_error() -> None:
100 mpack_bytes = b"data"
101 mpack_key = blob_id(mpack_bytes)
102 bad_resp = msgpack.packb({"mpack_key": mpack_key}, use_bin_type=True)
103 do = _mock_urllib_do(bad_resp)
104
105 with patch("muse.core.transport._urllib_do", side_effect=do):
106 with pytest.raises(TransportError, match="upload_url"):
107 HttpTransport().push_mpack_presign(_URL, None, mpack_bytes)
File History 2 commits
sha256:79ffe87f5fe2ec146e35f05521218bbf54dffdb0440c07f970bad05f16efb89f chore: merge main — carry all urllib/typing/test fixes from dev Sonnet 4.6 minor 19 days ago
sha256:0bea7600d1eee83e87950be49933b1006fa9dc2c71e7c4ee748d324f61138156 chore: bump version to 0.2.0rc11; fix typing audit violatio… Sonnet 4.6 minor 19 days ago