Merge pull request #343 from Bortlesboat/codex/use-sandboxed-safari-cookie-path
fix: prefer sandboxed Safari cookie path
This commit is contained in:
@@ -107,7 +107,18 @@ def extract_safari_cookies_macos(
|
|||||||
if sys.platform != "darwin":
|
if sys.platform != "darwin":
|
||||||
return None
|
return None
|
||||||
|
|
||||||
cookie_path = Path.home() / "Library" / "Cookies" / "Cookies.binarycookies"
|
cookie_paths = [
|
||||||
|
Path.home()
|
||||||
|
/ "Library"
|
||||||
|
/ "Containers"
|
||||||
|
/ "com.apple.Safari"
|
||||||
|
/ "Data"
|
||||||
|
/ "Library"
|
||||||
|
/ "Cookies"
|
||||||
|
/ "Cookies.binarycookies",
|
||||||
|
Path.home() / "Library" / "Cookies" / "Cookies.binarycookies",
|
||||||
|
]
|
||||||
|
cookie_path = next((path for path in cookie_paths if path.exists()), cookie_paths[0])
|
||||||
|
|
||||||
try:
|
try:
|
||||||
raw = cookie_path.read_bytes()
|
raw = cookie_path.read_bytes()
|
||||||
|
|||||||
@@ -160,25 +160,95 @@ class TestErrorPaths:
|
|||||||
result = extract_safari_cookies_macos("x.com", ["auth_token"])
|
result = extract_safari_cookies_macos("x.com", ["auth_token"])
|
||||||
assert result is None
|
assert result is None
|
||||||
|
|
||||||
|
def test_prefers_sandboxed_safari_cookie_path(
|
||||||
|
self, tmp_path: Path, x_cookies_file: bytes
|
||||||
|
):
|
||||||
|
sandbox_dir = (
|
||||||
|
tmp_path
|
||||||
|
/ "Library"
|
||||||
|
/ "Containers"
|
||||||
|
/ "com.apple.Safari"
|
||||||
|
/ "Data"
|
||||||
|
/ "Library"
|
||||||
|
/ "Cookies"
|
||||||
|
)
|
||||||
|
sandbox_dir.mkdir(parents=True)
|
||||||
|
(sandbox_dir / "Cookies.binarycookies").write_bytes(x_cookies_file)
|
||||||
|
|
||||||
|
legacy_dir = tmp_path / "Library" / "Cookies"
|
||||||
|
legacy_dir.mkdir(parents=True)
|
||||||
|
legacy_data = _build_binary_cookies_file(
|
||||||
|
[_build_page([_build_cookie_record(".x.com", "auth_token", "legacy")])]
|
||||||
|
)
|
||||||
|
(legacy_dir / "Cookies.binarycookies").write_bytes(legacy_data)
|
||||||
|
|
||||||
|
with patch(
|
||||||
|
"scripts.lib.safari_cookies.Path.home", return_value=tmp_path
|
||||||
|
), patch("scripts.lib.safari_cookies.sys") as mock_sys:
|
||||||
|
mock_sys.platform = "darwin"
|
||||||
|
mock_sys.stderr = sys.stderr
|
||||||
|
result = extract_safari_cookies_macos("x.com", ["auth_token", "ct0"])
|
||||||
|
|
||||||
|
assert result is not None
|
||||||
|
assert result["auth_token"] == "test_auth_abc123"
|
||||||
|
assert result["ct0"] == "test_ct0_xyz789"
|
||||||
|
|
||||||
|
def test_falls_back_to_legacy_safari_cookie_path(self, tmp_path: Path):
|
||||||
|
# Sandboxed path is intentionally NOT created — only the legacy path exists.
|
||||||
|
legacy_dir = tmp_path / "Library" / "Cookies"
|
||||||
|
legacy_dir.mkdir(parents=True)
|
||||||
|
legacy_data = _build_binary_cookies_file(
|
||||||
|
[_build_page([_build_cookie_record(".x.com", "auth_token", "legacy_auth")])]
|
||||||
|
)
|
||||||
|
(legacy_dir / "Cookies.binarycookies").write_bytes(legacy_data)
|
||||||
|
|
||||||
|
sandbox_path = (
|
||||||
|
tmp_path
|
||||||
|
/ "Library"
|
||||||
|
/ "Containers"
|
||||||
|
/ "com.apple.Safari"
|
||||||
|
/ "Data"
|
||||||
|
/ "Library"
|
||||||
|
/ "Cookies"
|
||||||
|
/ "Cookies.binarycookies"
|
||||||
|
)
|
||||||
|
assert not sandbox_path.exists()
|
||||||
|
|
||||||
|
with patch(
|
||||||
|
"scripts.lib.safari_cookies.Path.home", return_value=tmp_path
|
||||||
|
), patch("scripts.lib.safari_cookies.sys") as mock_sys:
|
||||||
|
mock_sys.platform = "darwin"
|
||||||
|
mock_sys.stderr = sys.stderr
|
||||||
|
result = extract_safari_cookies_macos("x.com", ["auth_token"])
|
||||||
|
|
||||||
|
assert result is not None
|
||||||
|
assert result["auth_token"] == "legacy_auth"
|
||||||
|
|
||||||
def test_permission_denied(self, tmp_path: Path, capsys):
|
def test_permission_denied(self, tmp_path: Path, capsys):
|
||||||
cookie_dir = tmp_path / "Library" / "Cookies"
|
cookie_dir = (
|
||||||
|
tmp_path
|
||||||
|
/ "Library"
|
||||||
|
/ "Containers"
|
||||||
|
/ "com.apple.Safari"
|
||||||
|
/ "Data"
|
||||||
|
/ "Library"
|
||||||
|
/ "Cookies"
|
||||||
|
)
|
||||||
cookie_dir.mkdir(parents=True)
|
cookie_dir.mkdir(parents=True)
|
||||||
cookie_file = cookie_dir / "Cookies.binarycookies"
|
cookie_file = cookie_dir / "Cookies.binarycookies"
|
||||||
cookie_file.write_bytes(b"cook")
|
cookie_file.write_bytes(b"cook")
|
||||||
cookie_file.chmod(0o000)
|
|
||||||
|
|
||||||
try:
|
with patch(
|
||||||
with patch(
|
"scripts.lib.safari_cookies.Path.home", return_value=tmp_path
|
||||||
"scripts.lib.safari_cookies.Path.home", return_value=tmp_path
|
), patch("scripts.lib.safari_cookies.sys") as mock_sys, patch.object(
|
||||||
), patch("scripts.lib.safari_cookies.sys") as mock_sys:
|
Path, "read_bytes", side_effect=PermissionError
|
||||||
mock_sys.platform = "darwin"
|
):
|
||||||
mock_sys.stderr = sys.stderr
|
mock_sys.platform = "darwin"
|
||||||
result = extract_safari_cookies_macos("x.com", ["auth_token"])
|
mock_sys.stderr = sys.stderr
|
||||||
assert result is None
|
result = extract_safari_cookies_macos("x.com", ["auth_token"])
|
||||||
captured = capsys.readouterr()
|
assert result is None
|
||||||
assert "Full Disk Access" in captured.err
|
captured = capsys.readouterr()
|
||||||
finally:
|
assert "Full Disk Access" in captured.err
|
||||||
cookie_file.chmod(0o644)
|
|
||||||
|
|
||||||
def test_truncated_magic_only(self):
|
def test_truncated_magic_only(self):
|
||||||
result = _parse_binary_cookies(b"cook", "x.com", ["auth_token"])
|
result = _parse_binary_cookies(b"cook", "x.com", ["auth_token"])
|
||||||
|
|||||||
Reference in New Issue
Block a user