{"id":30448318,"url":"https://github.com/gsidsid/ancilla","last_synced_at":"2025-09-01T06:37:01.389Z","repository":{"id":270060017,"uuid":"909157642","full_name":"gsidsid/ancilla","owner":"gsidsid","description":"A Polygon.io and FRED-based financial data library for backtesting trading strategies.","archived":false,"fork":false,"pushed_at":"2025-01-08T06:39:11.000Z","size":2233,"stargazers_count":0,"open_issues_count":0,"forks_count":1,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-07-20T05:02:47.510Z","etag":null,"topics":["backtesting","finance","polygon-io","python","quantitative","trading"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/gsidsid.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2024-12-27T22:09:38.000Z","updated_at":"2025-01-08T06:38:57.000Z","dependencies_parsed_at":"2024-12-30T09:39:29.210Z","dependency_job_id":null,"html_url":"https://github.com/gsidsid/ancilla","commit_stats":null,"previous_names":["gsidsid/quant-toys","gsidsid/ancilla"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/gsidsid/ancilla","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gsidsid%2Fancilla","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gsidsid%2Fancilla/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gsidsid%2Fancilla/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gsidsid%2Fancilla/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/gsidsid","download_url":"https://codeload.github.com/gsidsid/ancilla/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gsidsid%2Fancilla/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":271746824,"owners_count":24813588,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-08-23T02:00:09.327Z","response_time":69,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["backtesting","finance","polygon-io","python","quantitative","trading"],"created_at":"2025-08-23T12:06:41.631Z","updated_at":"2025-08-23T12:06:42.173Z","avatar_url":"https://github.com/gsidsid.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Ancilla\nA Polygon.io and FRED-based financial data library for backtesting trading strategies.\n\n\u003cp\u003e\n    \u003ca href=\"https://pypi.python.org/pypi/ancilla\" alt=\"PyPI\"\u003e\n        \u003cimg src=\"https://img.shields.io/pypi/v/ancilla.svg\" /\u003e\u003c/a\u003e\n    \u003ca href=\"https://github.com/gsidsid/ancilla\" alt=\"License\"\u003e\n        \u003cimg src=\"https://img.shields.io/github/license/gsidsid/ancilla\" /\u003e\u003c/a\u003e\n\u003c/p\u003e\n\nAncilla is a straightforward Python library for querying/visualizing financial data and executing backtests to survey trading strategies. Under the hood, Ancilla uses Polygon.io to fetch historical stock and options data, and FRED, the official data source for the Federal Reserve, to fetch interest rates.\n\n## Installation\n\n```\npip install ancilla\n```\n\nCreate a `.env` file in the root directory with\n```\nPOLYGON_API_KEY=your_api_key\nFRED_API_KEY=your_api_key\n```\n\nUsing Ancilla requires paid Polygon.io data subscriptions, which can be obtained [here](https://polygon.io/), and a free FRED API key, which can be obtained [here](https://fred.stlouisfed.org/).\n\n## Usage\n\n```python\n# experiments/test_backtest.py\nfrom datetime import datetime\nfrom typing import Dict, Any\nimport pytz\nimport os\nimport dotenv\n\nfrom ancilla.backtesting.configuration import CommissionConfig, SlippageConfig\nfrom ancilla.backtesting import Backtest, Strategy\nfrom ancilla.providers import PolygonDataProvider\n\ndotenv.load_dotenv()\n\n\nclass HoldSpyStrategy(Strategy):\n    \"\"\"Simple test strategy that buys and holds SPY.\"\"\"\n\n    def __init__(self, data_provider, position_size: float = 0.2):\n        super().__init__(data_provider, name=\"hold_spy\")\n        self.position_size = position_size\n        self.entry_prices = {}  # Track entry prices for each ticker\n\n    def on_data(self, timestamp: datetime, market_data: Dict[str, Any]) -\u003e None:\n        \"\"\"Buy and hold stocks with basic position sizing.\"\"\"\n        self.logger.debug(f\"Processing market data for {timestamp}\")\n        for ticker, data in market_data.items():\n            # Log market data\n            self.logger.debug(f\"{ticker} price: ${data['close']:.2f}\")\n\n            # Skip if we already have a position\n            if ticker in self.portfolio.positions:\n                continue\n\n            # Calculate position size based on portfolio value\n            portfolio_value = self.portfolio.get_total_value()\n            position_value = portfolio_value * self.position_size\n            shares = int(position_value / data[\"close\"])\n\n            if shares \u003e 0:\n                # Open position\n                self.logger.info(\n                    f\"Opening position in {ticker}: {shares} shares @ ${data['close']:.2f}\"\n                )\n                success = self.engine.buy_stock(ticker=ticker, quantity=shares)\n                if success:\n                    self.entry_prices[ticker] = data[\"close\"]\n                    self.logger.info(f\"Successfully opened position in {ticker}\")\n                else:\n                    self.logger.warning(f\"Failed to open position in {ticker}\")\n\n\nif __name__ == \"__main__\":\n    # Initialize data provider\n    api_key = os.getenv(\"POLYGON_API_KEY\")\n    if not api_key:\n        raise ValueError(\"POLYGON_API_KEY environment variable not set\")\n\n    data_provider = PolygonDataProvider(api_key)\n\n    # Create strategy\n    strategy = HoldSpyStrategy(\n        data_provider=data_provider, position_size=0.5  # 50% of portfolio per position\n    )\n\n    # Set up test parameters\n    tickers = [\"SPY\"]  # Reduced ticker list for testing\n    start_date = datetime(2023, 1, 1, tzinfo=pytz.UTC)\n    end_date = datetime(2024, 12, 31, tzinfo=pytz.UTC)  # Shorter test period\n\n    # Initialize backtest engine\n    simple_backtest = Backtest(\n        strategy=strategy,\n        initial_capital=100000,\n        frequency=\"1hour\",\n        start_date=start_date,\n        end_date=end_date,\n        tickers=tickers,\n        commission_config=CommissionConfig(\n            min_commission=1.0, per_share=0.005, per_contract=0.65, percentage=0.0001\n        ),\n        slippage_config=SlippageConfig(\n            base_points=1.0, vol_impact=0.1, spread_factor=0.5, market_impact=0.05\n        ),\n    )\n\n    # Run backtest\n    results = simple_backtest.run()\n\n    # Plot results\n    results.plot(include_drawdown=True)\n```\n\n## Features\n\n- A Polygon.io data wrapper with retries \u0026 automatic caching\n- Basic visualizations for IV surfaces, liquidity, and price data\n- Backtesting for equities and options\n  - Batch requests and data caching for speed\n  - Configurable strategy frequency (30min, 1hour, etc.)\n  - Models slippage, commissions, price impact\n  - Fill probability based on volume (or deterministic fills for testing)\n  - Adjusts stock prices for splits and dividends, pays dividends\n  - Monthly interest using accurate rates\n  - Automatic ITM options exercise and assignment\n  - Detailed trade history visualizations, performance metrics, logs\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgsidsid%2Fancilla","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fgsidsid%2Fancilla","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgsidsid%2Fancilla/lists"}