summaryrefslogtreecommitdiff
path: root/shared/tests
diff options
context:
space:
mode:
authorTheSiahxyz <164138827+TheSiahxyz@users.noreply.github.com>2026-04-02 10:05:25 +0900
committerTheSiahxyz <164138827+TheSiahxyz@users.noreply.github.com>2026-04-02 10:05:25 +0900
commit2446214389fb8f4644d1a24a19e5e3d7b55e8651 (patch)
treef740f479bf5222b1b093617520e32ac220108253 /shared/tests
parent87bf67bac771181aeb4f4c5bb11fae8f343c12bb (diff)
refactor: replace Binance/ccxt with Alpaca API client for US stocks
Diffstat (limited to 'shared/tests')
-rw-r--r--shared/tests/test_alpaca.py67
-rw-r--r--shared/tests/test_exchange.py55
-rw-r--r--shared/tests/test_models.py10
3 files changed, 69 insertions, 63 deletions
diff --git a/shared/tests/test_alpaca.py b/shared/tests/test_alpaca.py
new file mode 100644
index 0000000..7c8eab1
--- /dev/null
+++ b/shared/tests/test_alpaca.py
@@ -0,0 +1,67 @@
+"""Tests for Alpaca API client."""
+import pytest
+from unittest.mock import AsyncMock, MagicMock
+from shared.alpaca import AlpacaClient
+
+
+@pytest.fixture
+def client():
+ return AlpacaClient(api_key="test-key", api_secret="test-secret", paper=True)
+
+
+def test_client_uses_paper_url(client):
+ assert "paper" in client._base_url
+
+
+def test_client_uses_live_url():
+ c = AlpacaClient(api_key="k", api_secret="s", paper=False)
+ assert "paper" not in c._base_url
+
+
+def test_client_headers(client):
+ h = client.headers
+ assert h["APCA-API-KEY-ID"] == "test-key"
+ assert h["APCA-API-SECRET-KEY"] == "test-secret"
+
+
+@pytest.mark.asyncio
+async def test_get_buying_power(client):
+ mock_response = AsyncMock()
+ mock_response.status = 200
+ mock_response.json = AsyncMock(return_value={"buying_power": "10000.00"})
+ mock_response.__aenter__ = AsyncMock(return_value=mock_response)
+ mock_response.__aexit__ = AsyncMock(return_value=False)
+
+ mock_session = MagicMock()
+ mock_session.closed = False
+ mock_session.request = MagicMock(return_value=mock_response)
+ mock_session.close = AsyncMock()
+ client._session = mock_session
+
+ result = await client.get_buying_power()
+ from decimal import Decimal
+ assert result == Decimal("10000.00")
+ await client.close()
+
+
+@pytest.mark.asyncio
+async def test_submit_moc_order(client):
+ mock_response = AsyncMock()
+ mock_response.status = 200
+ mock_response.json = AsyncMock(return_value={"id": "order-1", "status": "accepted"})
+ mock_response.__aenter__ = AsyncMock(return_value=mock_response)
+ mock_response.__aexit__ = AsyncMock(return_value=False)
+
+ mock_session = MagicMock()
+ mock_session.closed = False
+ mock_session.request = MagicMock(return_value=mock_response)
+ mock_session.close = AsyncMock()
+ client._session = mock_session
+
+ result = await client.submit_moc_order("AAPL", qty=10, side="buy")
+ assert result["id"] == "order-1"
+
+ # Verify the request was made with correct params
+ call_args = mock_session.request.call_args
+ assert call_args[0][0] == "POST"
+ await client.close()
diff --git a/shared/tests/test_exchange.py b/shared/tests/test_exchange.py
deleted file mode 100644
index 95dc7d7..0000000
--- a/shared/tests/test_exchange.py
+++ /dev/null
@@ -1,55 +0,0 @@
-"""Tests for the exchange factory."""
-
-from unittest.mock import patch
-
-import ccxt.async_support as ccxt
-import pytest
-
-from shared.exchange import create_exchange
-
-
-def test_create_exchange_binance():
- """Verify create_exchange returns a ccxt.binance instance."""
- exchange = create_exchange(
- exchange_id="binance",
- api_key="test-key",
- api_secret="test-secret",
- )
- assert isinstance(exchange, ccxt.binance)
- assert exchange.apiKey == "test-key"
- assert exchange.secret == "test-secret"
- assert exchange.enableRateLimit is True
-
-
-def test_create_exchange_unknown():
- """Verify create_exchange raises ValueError for unknown exchange."""
- with pytest.raises(ValueError, match="Unknown exchange 'not_a_real_exchange'"):
- create_exchange(
- exchange_id="not_a_real_exchange",
- api_key="key",
- api_secret="secret",
- )
-
-
-def test_create_exchange_with_sandbox():
- """Verify sandbox mode is activated when sandbox=True."""
- with patch.object(ccxt.binance, "set_sandbox_mode") as mock_sandbox:
- exchange = create_exchange(
- exchange_id="binance",
- api_key="key",
- api_secret="secret",
- sandbox=True,
- )
- mock_sandbox.assert_called_once_with(True)
- assert isinstance(exchange, ccxt.binance)
-
-
-def test_create_exchange_no_sandbox_by_default():
- """Verify sandbox mode is not set when sandbox=False (default)."""
- with patch.object(ccxt.binance, "set_sandbox_mode") as mock_sandbox:
- create_exchange(
- exchange_id="binance",
- api_key="key",
- api_secret="secret",
- )
- mock_sandbox.assert_not_called()
diff --git a/shared/tests/test_models.py b/shared/tests/test_models.py
index e3b9f12..2b8cd5e 100644
--- a/shared/tests/test_models.py
+++ b/shared/tests/test_models.py
@@ -8,15 +8,9 @@ from unittest.mock import patch
def test_settings_defaults():
"""Test that Settings has correct defaults."""
- with patch.dict(
- os.environ,
- {
- "BINANCE_API_KEY": "test_key",
- "BINANCE_API_SECRET": "test_secret",
- },
- ):
- from shared.config import Settings
+ from shared.config import Settings
+ with patch.dict(os.environ, {}, clear=False):
settings = Settings()
assert settings.redis_url == "redis://localhost:6379"
assert settings.database_url == "postgresql://trading:trading@localhost:5432/trading"