finance-data-mcp / tests /test_data_fetcher.py
dlrklc's picture
Initial commit: Gradio MCP app for real-time financial data
7169bc5
"""
Test cases for data fetching module.
Tests edge cases for yfinance data retrieval.
"""
import unittest
from unittest.mock import patch, MagicMock
import pandas as pd
from src.data_fetcher import (
_fetch_stock_data_fast,
get_cached_stock_data,
fetch_historical_data
)
class TestDataFetcher(unittest.TestCase):
"""Test cases for data fetching functions."""
@patch('src.data_fetcher.yf.Ticker')
def test_fetch_stock_data_fast_success(self, mock_ticker):
"""Test successful data fetch."""
# Mock yfinance response
mock_stock = MagicMock()
mock_hist = pd.DataFrame({
'Close': [150, 151],
'Volume': [1000000, 1100000]
})
mock_stock.history.return_value = mock_hist
mock_ticker.return_value = mock_stock
info, hist = _fetch_stock_data_fast("AAPL")
self.assertIsInstance(info, dict)
self.assertIn("longName", info)
self.assertIn("volume", info)
self.assertFalse(hist.empty)
@patch('src.data_fetcher.yf.Ticker')
def test_fetch_stock_data_fast_empty(self, mock_ticker):
"""Test data fetch with empty history."""
mock_stock = MagicMock()
mock_stock.history.return_value = pd.DataFrame()
mock_ticker.return_value = mock_stock
info, hist = _fetch_stock_data_fast("INVALID")
self.assertTrue(hist.empty)
self.assertEqual(info["volume"], 0)
@patch('src.data_fetcher.yf.Ticker')
def test_fetch_stock_data_fast_exception(self, mock_ticker):
"""Test data fetch with exception."""
mock_ticker.side_effect = Exception("Network error")
with self.assertRaises(Exception):
_fetch_stock_data_fast("AAPL")
@patch('src.data_fetcher._fetch_stock_data_fast')
def test_get_cached_stock_data(self, mock_fetch):
"""Test cached data retrieval."""
# Mock return value
mock_info = {"longName": "Apple Inc.", "volume": 1000000}
mock_hist = pd.DataFrame({'Close': [150], 'Volume': [1000000]})
mock_fetch.return_value = (mock_info, mock_hist)
# First call should fetch
info1, hist1 = get_cached_stock_data("AAPL")
self.assertEqual(mock_fetch.call_count, 1)
# Second call should use cache (if within TTL)
info2, hist2 = get_cached_stock_data("AAPL")
# Cache should be used (call count might be same or different based on cache)
self.assertIsInstance(info2, dict)
if __name__ == '__main__':
unittest.main()