5274c6943617a570914f15e6ab03a6d6383d6991
[poker.git] / bots / hole_bot.py
1 #!/usr/bin/python
2
3 """Go all (or not) depending on whats in the hole.
4 """
5
6 import logging
7 import os
8 import sys
9
10
11 class RunComplete (Exception):
12     """Raised after receiving the `END` tag to abort execution.
13     """
14     pass
15
16
17 class HoleBot (object):
18     def __init__(self, stdin=None, stdout=None, log_level=logging.WARN):
19         if stdin == None:
20             stdin = sys.stdin
21         self.stdin = stdin
22         if stdout == None:
23             stdout = sys.stdout
24         self.stdout = stdout
25         log_file = '%s_%d.log' % (self.__class__.__name__, os.getpid())
26         logging.basicConfig(filename=log_file, level=log_level)
27         self.log = logging
28
29     def run(self):
30         state = self._initial_state()
31         while True:
32             line = self.stdin.readline().strip()
33             if not line:
34                 continue  # skip blank lines
35             tag,type,data = self._parse(line)
36             try:
37                 self._process(tag, type, data, state)
38             except RunComplete:
39                 break
40
41     def _parse(self, line):
42         self.log.debug('read: %s' % line)
43         fields = line.split(' ')
44         try:
45             tag  = fields[0]
46             type = fields[1]
47             data = fields[2:]
48         except:
49             self.log.debug('tag only: %s' % str(fields))
50             tag  = fields[0]
51             type = data = None
52         self.log.debug('parsed tag %s, type %s, data %s'
53                        % (repr(tag), repr(type), repr(data)))
54         return (tag, type, data)
55
56     def _process(self, tag, type, data, state):
57         if tag == 'END':
58             raise RunComplete
59         elif tag == 'MOVE':
60             bet = self._bet(state)
61             self.log.info('bet %s' % bet)
62             self.stdout.write('%s\n' % bet)
63             self.stdout.flush()
64         elif tag == 'INFO' and type == 'HOLE':
65             self._process_hole(data, state)
66             self.log.info('processed hole %s, state: %s' % (data, state))
67
68     def _initial_state(self):
69         return {'all_in': False}
70
71     def _bet(self, state):
72         if state['all_in']:
73             bet = 'A'
74         else:
75             bet = 'f'
76         state['all_in'] = False
77         return bet
78
79     def _process_hole(self, data, state):
80         raise NotImplementedError