{"id":15132765,"url":"https://github.com/fedden/poker_ai","last_synced_at":"2025-09-29T01:30:45.438Z","repository":{"id":41431819,"uuid":"233256635","full_name":"fedden/poker_ai","owner":"fedden","description":"🤖 An Open Source Texas Hold'em AI","archived":true,"fork":false,"pushed_at":"2023-04-03T03:00:44.000Z","size":11028,"stargazers_count":1395,"open_issues_count":56,"forks_count":382,"subscribers_count":69,"default_branch":"develop","last_synced_at":"2025-01-16T16:21:02.985Z","etag":null,"topics":["artificial-intelligence","counterfactual-regret-minimization","machine-learning","open-source","pluribus","poker-engine","python","texas-holdem-poker"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"other","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/fedden.png","metadata":{"files":{"readme":"README.md","changelog":"HISTORY.md","contributing":"CONTRIBUTING.md","funding":".github/FUNDING.yml","license":"LICENSE","code_of_conduct":"CODE_OF_CONDUCT.md","threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null},"funding":{"github":null,"patreon":null,"open_collective":null,"ko_fi":null,"tidelift":null,"community_bridge":null,"liberapay":null,"issuehunt":null,"otechie":null,"custom":null}},"created_at":"2020-01-11T15:54:20.000Z","updated_at":"2025-01-16T04:24:21.000Z","dependencies_parsed_at":"2022-08-10T02:23:10.792Z","dependency_job_id":null,"html_url":"https://github.com/fedden/poker_ai","commit_stats":null,"previous_names":[],"tags_count":3,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fedden%2Fpoker_ai","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fedden%2Fpoker_ai/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fedden%2Fpoker_ai/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fedden%2Fpoker_ai/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/fedden","download_url":"https://codeload.github.com/fedden/poker_ai/tar.gz/refs/heads/develop","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":234579583,"owners_count":18855636,"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","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":["artificial-intelligence","counterfactual-regret-minimization","machine-learning","open-source","pluribus","poker-engine","python","texas-holdem-poker"],"created_at":"2024-09-26T04:23:27.548Z","updated_at":"2025-09-29T01:30:40.007Z","avatar_url":"https://github.com/fedden.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"| code-thing      | status        |\n| --------------- | ------------- |\n| master          | [![Build Status](https://travis-ci.org/fedden/poker_ai.svg?branch=master)](https://travis-ci.org/fedden/poker_ai)  |\n| develop         | [![Build Status](https://travis-ci.org/fedden/poker_ai.svg?branch=develop)](https://travis-ci.org/fedden/poker_ai) |\n| maintainability | [![Maintainability](https://api.codeclimate.com/v1/badges/c5a556dae097b809b4d9/maintainability)](https://codeclimate.com/github/fedden/poker_ai/maintainability) |\n| coverage        | [![Test Coverage](https://api.codeclimate.com/v1/badges/c5a556dae097b809b4d9/test_coverage)](https://codeclimate.com/github/fedden/poker_ai/test_coverage) |\n| license         | [![License: GPL v3](https://img.shields.io/badge/License-GPLv3-blue.svg)](https://www.gnu.org/licenses/gpl-3.0) |\n\n[Read the documentation]()\n\n# 🤖 Poker AI\n\nThis repository will contain a best effort open source implementation of a poker AI using the ideas of Counterfactual Regret.\n\n\u003cp align=\"center\"\u003e\n  \u003cimg src=\"https://github.com/fedden/poker_ai/blob/develop/assets/poker.jpg\"\u003e\n\u003c/p\u003e\n\n_Made with love from the developers [Leon](https://www.leonfedden.co.uk) and [Colin](http://www.colinmanko.com/)._\n\n_A special thank you to [worldveil](https://github.com/worldveil) for originally writing [this awesome hand evaluator python2 module](https://github.com/worldveil/deuces), which was ported to python3 and [maintained here](https://github.com/fedden/poker_ai/tree/master/poker_ai/poker/evaluation)._\n\n## Join the Community\n[https://thepoker.ai](https://thepoker.ai)\n\n## Prerequisites\n\nThis repository assumes Python 3.7 or newer is used.\n\n## Installing\n\nEither install from pypi:\n```bash\npip install poker_ai \n```\n\nOr if you want to dev on our code, install the Python package from source by cloning this repo and `pip -e` installing it:\n```bash\ngit clone https://github.com/fedden/poker_ai.git # Though really we should use ssh here!\ncd /path/to/poker_ai\npip install .\n```\n\n## Command Line Interface (CLI)\n\nWe have a CLI that will be installed when you pip install the package. To get help on any option, just add the `--help` flag when invoking the CLI.\n\nHow to get a list of commands that can be run:\n```bash\npoker_ai --help\n``` \n\nYou will need to produce some lookup tables that cluster the various information sets. Here is more information on that:\n```bash\npoker_ai cluster --help\n```\n\nHow to get information on training an agent:\n```bash\npoker_ai train start --help\n```\n\nHow to get information on resuming training:\n```bash\npoker_ai train resume --help\n```\n\nOnce you have an agent, and want to play against it, you can do the following:\n```bash\npoker_ai play --help\n```\n\n## Build a Bot\n\n### Cluster Hero Information\n\nIn poker, the number of card combinations for one player on the river can exceed 56 billion combinations. In order to make this information tractable, we must group together strategically similar situations. We do this with two types of compression: lossy and lossless compression. Currently we only support a 20 card deck without modification.\n\n```bash\npoker_ai cluster\n```\n\nYou'll save the combinations of public information in a file called card_info_lut.joblib located in your project directory.\n\n### Train your bot\n\nWe use MCCFR to learn strategies. The MCCFR algorithm uses iterative self-play to adjust strategy based on regret. \n\n```bash\npoker_ai train start\n```\n\nYou'll create a folder in your project directory with the learned strategy and configuration files, in case you need to resume later.\n\n### Play your bot\n\nFinally, you can play your bot with the following command:\n\n```bash\npoker_ai play\n```\n\nYou'll create a results.yaml file in ~/.poker/. So be sure to see how you stack up against your bot.\n \n## Running tests\n\nWe are working hard on testing our components, but contributions here are always welcome. You can run the tests by cloning the code, changing directory to this repositories root directory (i.e `poker_ai/`) and call the python test library `pytest`:\n```bash\ncd /path/to/poker_ai\npip install pytest\npytest\n```\n\nSee below on how to run the tests from the docker image.\n\n## Building the docker image\n\nWe use a custom docker image for our testing suite. \n\nYou'll need to have computed the pickled card information lookup tables first (the cluster command for poker_ai). We build the images like below, in this case the luts are in './research/blueprint_algo'. First we build the parent image, with all of the dependancies.\n```bash\ndocker build --build-arg LUT_DIR=research/blueprint_algo -f ParentDockerfile -t pokerai .\n```\n\nThen we build the test image.\n```bash\ndocker build -t pokeraitest .\n```\n\nWe then can run the tests with:\n```bash\ndocker run -it pokeraitest pytest \n```\n\nThis is just a note for the developers, but we can push the parent image to the registry with the following (please ensure the version tag that comes after the colon is correct). We want to do this because we need various dependancies for the remote tests, and travis builds the `pokeraitest` image with the current git commit that has just been pushed.\n```bash\ndocker tag pokerai pokerai/pokerai:1.0.0rc1\ndocker push pokerai/pokerai:1.0.0rc1\n```\n\n## Building documentation\n\nDocumentation is hosted, but you can build it yourself if you wish:\n```bash\n# Build the documentation.\ncd /path/to/poker_ai/docs\nmake html\ncd ./_build/html \n# Run a webserver and navigate to localhost and the port (usually 8000) in your browser.\npython -m http.server \n```\n\n## Repository Structure\n\nBelow is a rough structure of the codebase. \n\n```\n├── applications   # Larger applications like the state visualiser sever.\n├── paper          # Main source of info and documentation :)\n├── poker_ai       # Main Python library.\n│   ├── ai         # Stub functions for ai algorithms.\n│   ├── games      # Implementations of poker games as node based objects that\n│   │              # can be traversed in a depth-first recursive manner.\n│   ├── poker      # WIP general code for managing a hand of poker.\n│   ├── terminal   # Code to play against the AI from your console.\n│   └── utils      # Utility code like seed setting.\n├── research       # A directory for research/development scripts \n│                  # to help formulate understanding and ideas.\n└── test           # Python tests.\n    ├── functional # Functional tests that test multiple components \n    │              # together.\n    └── unit       # Individual tests for functions and objects.\n```\n\n## Code Examples\n\nHere are some assorted examples of things that are being built in this repo.\n\n### State based poker traversal\n\nTo perform MCCFR, the core algorithm of poker_ai, we need a class that encodes all of the poker rules, that we can apply an action to which then creates a new game state.\n\n```python\npot = Pot()\nplayers = [\n    ShortDeckPokerPlayer(player_i=player_i, initial_chips=10000, pot=pot)\n    for player_i in range(n_players)\n]\nstate = ShortDeckPokerState(players=players)\nfor action in state.legal_actions:\n    new_state: ShortDeckPokerState = state.apply_action(action)\n```\n\n### Playing against AI in your terminal\n\nWe also have some code to play a round of poker against the AI agents, inside your terminal.\n\nThe characters are a little broken when captured in `asciinema`, but you'll get the idea by watching this video below. Results should be better in your actual terminal!\n\n\u003cp align=\"center\"\u003e\n  \u003ca href=\"https://asciinema.org/a/331234\" target=\"_blank\"\u003e\n    \u003cimg src=\"https://asciinema.org/a/331234.svg\" width=\"500\" /\u003e\n  \u003c/a\u003e\n\u003c/p\u003e\nTo invoke the code, either call the `run_terminal_app` method directly from the `poker_ai.terminal.runner` module, or call from python like so:\n\n```bash\ncd /path/to/poker_ai/dir\npython -m poker_ai.terminal.runner       \\\n  --agent offline                        \\ \n  --pickle_dir ./research/blueprint_algo \\\n  --strategy_path ./research/blueprint_algo/offline_strategy_285800.gz \n```\n\n### Web visualisation code\n\nWe are also working on code to visualise a given instance of the `ShortDeckPokerState`, which looks like this:\n\u003cp align=\"center\"\u003e\n  \u003cimg src=\"https://github.com/fedden/poker_ai-poker-AI/blob/develop/assets/visualisation.png\"\u003e\n\u003c/p\u003e\n\nIt is so we can visualise the AI as it plays, and also debug particular situations visually. The idea as it stands, is a live web-visualisation server like TensorBoard, so you'll just push your current poker game state, and this will be reflected in the visualisations, so you can see what the agents are doing. \n\n[_The frontend code is based on this codepen._](https://codepen.io/Rovak/pen/ExYeQar)\n\nHere is an example of how you could plot the poker game state:\n```python\nfrom plot import PokerPlot\nfrom poker_ai.games.short_deck.player import ShortDeckPokerPlayer\nfrom poker_ai.games.short_deck.state import ShortDeckPokerState\nfrom poker_ai.poker.pot import Pot\n\n\ndef get_state() -\u003e ShortDeckPokerState:\n    \"\"\"Gets a state to visualise\"\"\"\n    n_players = 6\n    pot = Pot()\n    players = [\n        ShortDeckPokerPlayer(player_i=player_i, initial_chips=10000, pot=pot)\n        for player_i in range(n_players)\n    ]\n    return ShortDeckPokerState(\n        players=players, \n        pickle_dir=\"../../research/blueprint_algo/\"\n    )\n\n\npp: PokerPlot = PokerPlot()\n# If you visit http://localhost:5000/ now you will see an empty table.\n\n# ... later on in the code, as proxy for some code that obtains a new state ...\n# Obtain a new state.\nstate: ShortDeckPokerState = get_state()\n# Update the state to be plotted, this is sent via websockets to the frontend.\npp.update_state(state)\n# http://localhost:5000/ will now display a table with 6 players.\n```\n\n### Playing a game of poker\n\nThere are two parts to this repository, the code to manage a game of poker, and the code to train an AI algorithm to play the game of poker. A low level thing to first to is to implement a poker engine class that can manage a game of poker.\n\nThe reason the poker engine is implemented is because it is useful to have a well-integrated poker environment available during the development of the AI algorithm, incase there are tweaks that must be made to accomadate things like the history of state or the replay of a scenario during Monte Carlo Counterfactual Regret Minimisation. \n\nThe following code is how one might program a round of poker that is deterministic using the engine. This engine is now the first pass that will be used support self play.\n\n```python\nfrom poker_ai import utils\nfrom poker_ai.ai.dummy import RandomPlayer\nfrom poker_ai.poker.table import PokerTable\nfrom poker_ai.poker.engine import PokerEngine\nfrom poker_ai.poker.pot import Pot\n\n# Seed so things are deterministic.\nutils.random.seed(42)\n\n# Some settings for the amount of chips.\ninitial_chips_amount = 10000\nsmall_blind_amount = 50\nbig_blind_amount = 100\n\n# Create the pot.\npot = Pot()\n# Instanciate six players that will make random moves, make sure \n# they can reference the pot so they can add chips to it.\nplayers = [\n    RandomPlayer(\n        name=f'player {player_i}',\n        initial_chips=initial_chips_amount,\n        pot=pot)\n    for player_i in range(6)\n]\n# Create the table with the players on it.\ntable = PokerTable(players=players, pot=pot)\n# Create the engine that will manage the poker game lifecycle.\nengine = PokerEngine(\n    table=table,\n    small_blind=small_blind_amount,\n    big_blind=big_blind_amount)\n# Play a round of Texas Hold'em Poker!\nengine.play_one_round()\n```\n\n## Roadmap\n\nThe following todo will change dynamically as my understanding of the algorithms and the poker_ai project evolves. \n\nAt first, the goal is to prototype in Python as iteration will be much easier and quicker. Once there is a working prototype, write in a systems level language like C++ and optimise for performance. \n\n### 1. Game engine iteration.\n_Implement a multiplayer working heads up no limit poker game engine to support the self-play._\n- [x] Lay down the foundation of game objects (player, card etc).\n- [x] Add poker hand evaluation code to the engine.\n- [x] Support a player going all in during betting.\n- [x] Support a player going all in during payouts.\n- [x] Lots of testing for various scenarios to ensure logic is working as expected.\n\n### 2. AI iteration.\n_Iterate on the AI algorithms and the integration into the poker engine._\n- [x] Integrate the AI strategy to support self-play in the multiplayer poker game engine.\n- [x] In the game-engine, allow the replay of any round the current hand to support MCCFR. \n- [x] Implement the creation of the blueprint strategy using Monte Carlo CFR miminisation.\n- [x] Add the real-time search for better strategies during the game.\n\n### 3. Game engine iteration.\n_Strengthen the game engine with more tests and allow users to see live visualisation of game state._\n- [x] Start work on a visualisation server to allow a game state to be displayed. \n- [ ] Triple check that the rules are implemented in the poker engine as described in the supplimentary material.\n- [ ] Work through the coverage, adding more tests, can never have enough.\n\n\u003cp align=\"center\"\u003e\n  \u003cimg src=\"https://github.com/fedden/poker_ai/blob/develop/assets/regret.jpeg\"\u003e\n\u003c/p\u003e\n\n## Contributing\n\nThis is an open effort and help, criticisms and ideas are all welcome. \n\nFirst of all, please check out the [CONTRIBUTING](/CONTRIBUTING.md) guide.\n\nFeel free to start a discussion on the github issues or to reach out to me at leonfedden at gmail dot com. \n\n## License\n\nThe code is provided under the copy-left GPL licence. If you need it under a more permissive license then please contact me at leonfedden at gmail dot com.\n\n## Stargazers over time\n\nWe appreciate you getting this far in the README file! If you like what we are doing, please give us a star and share with your friends! \n\n[![Stargazers over time](https://starchart.cc/fedden/poker_ai.svg)](https://starchart.cc/fedden/poker_ai)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ffedden%2Fpoker_ai","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Ffedden%2Fpoker_ai","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ffedden%2Fpoker_ai/lists"}