Merge branch 'master' of git://git.assembla.com/fpdb
This commit is contained in:
commit
0166a1857c
|
@ -49,7 +49,7 @@ src_install() {
|
|||
make_desktop_entry ${PN}
|
||||
|
||||
prepgamesdirs
|
||||
fperms +x "${GAMES_DATADIR}"/${PN}/pyfpdb/*.pyw
|
||||
chmod +x ${D}/"${GAMES_DATADIR}"/${PN}/pyfpdb/*.pyw
|
||||
}
|
||||
|
||||
pkg_postinst() {
|
||||
|
|
|
@ -49,7 +49,7 @@ src_install() {
|
|||
make_desktop_entry ${PN}
|
||||
|
||||
prepgamesdirs
|
||||
fperms +x "${GAMES_DATADIR}"/${PN}/pyfpdb/*.pyw
|
||||
chmod +x ${D}/"${GAMES_DATADIR}"/${PN}/pyfpdb/*.pyw
|
||||
}
|
||||
|
||||
pkg_postinst() {
|
||||
|
|
65
packaging/gentoo/fpdb-9999.ebuild
Normal file
65
packaging/gentoo/fpdb-9999.ebuild
Normal file
|
@ -0,0 +1,65 @@
|
|||
# Copyright 1999-2010 Gentoo Foundation
|
||||
# Distributed under the terms of the GNU General Public License v2
|
||||
# created by Steffen Schaumburg, steffen@schaumburger.info
|
||||
|
||||
inherit eutils
|
||||
inherit games
|
||||
inherit git
|
||||
|
||||
EAPI="2"
|
||||
NEED_PYTHON=2.5
|
||||
|
||||
DESCRIPTION="A free/open source tracker/HUD for use with online poker"
|
||||
HOMEPAGE="http://fpdb.wiki.sourceforge.net/"
|
||||
EGIT_REPO_URI="git://git.assembla.com/fpdb.git"
|
||||
|
||||
LICENSE="AGPL-3"
|
||||
SLOT="0"
|
||||
KEYWORDS="~amd64 ~x86"
|
||||
#note: this should work on other architectures too, please send me your experiences
|
||||
|
||||
IUSE="graph mysql postgres sqlite"
|
||||
RDEPEND="
|
||||
mysql? ( virtual/mysql
|
||||
dev-python/mysql-python )
|
||||
postgres? ( dev-db/postgresql-server
|
||||
dev-python/psycopg )
|
||||
sqlite? ( dev-lang/python[sqlite]
|
||||
dev-python/numpy )
|
||||
>=x11-libs/gtk+-2.10
|
||||
dev-python/pygtk
|
||||
graph? ( dev-python/numpy
|
||||
dev-python/matplotlib[gtk] )
|
||||
dev-python/python-xlib
|
||||
dev-python/pytz"
|
||||
DEPEND="${RDEPEND}"
|
||||
|
||||
src_unpack() {
|
||||
git_src_unpack
|
||||
}
|
||||
|
||||
src_install() {
|
||||
insinto "${GAMES_DATADIR}"/${PN}
|
||||
doins -r gfx
|
||||
doins -r pyfpdb
|
||||
doins readme.txt
|
||||
|
||||
exeinto "${GAMES_DATADIR}"/${PN}
|
||||
doexe run_fpdb.py
|
||||
|
||||
dodir "${GAMES_BINDIR}"
|
||||
dosym "${GAMES_DATADIR}"/${PN}/run_fpdb.py "${GAMES_BINDIR}"/${PN}
|
||||
|
||||
newicon gfx/fpdb-icon.png ${PN}.png
|
||||
make_desktop_entry ${PN}
|
||||
|
||||
prepgamesdirs
|
||||
chmod +x ${D}/"${GAMES_DATADIR}"/${PN}/pyfpdb/*.pyw
|
||||
}
|
||||
|
||||
pkg_postinst() {
|
||||
games_pkg_postinst
|
||||
elog "Note that if you really want to use mysql or postgresql you will have to create"
|
||||
elog "the database and user yourself and enter it into the fpdb config."
|
||||
elog "You can find the instructions on the project's website."
|
||||
}
|
|
@ -452,8 +452,8 @@ class Email:
|
|||
self.fetchType = node.getAttribute("fetchType")
|
||||
|
||||
def __str__(self):
|
||||
return " host = %s\n username = %s\n password = %s\n useSsl = %s\n folder = %s\n" \
|
||||
% (self.host, self.username, self.password, self.useSsl, self.folder)
|
||||
return " siteName=%s\n fetchType=%s\n host = %s\n username = %s\n password = %s\n useSsl = %s\n folder = %s\n" \
|
||||
% (self.siteName, self.fetchType, self.host, self.username, self.password, self.useSsl, self.folder)
|
||||
|
||||
class HudUI:
|
||||
def __init__(self, node):
|
||||
|
@ -534,6 +534,39 @@ class GUICashStats(list):
|
|||
|
||||
self.append( [col_name, col_title, disp_all, disp_posn, field_format, field_type, xalignment] )
|
||||
|
||||
def get_defaults(self):
|
||||
"""A list of defaults to be called, should there be no entry in config"""
|
||||
defaults = [ [u'game', u'Game', True, True, u'%s', u'str', 0.0],
|
||||
[u'hand', u'Hand', False, False, u'%s', u'str', 0.0],
|
||||
[u'plposition', u'Posn', False, False, u'%s', u'str', 1.0],
|
||||
[u'pname', u'Name', False, False, u'%s', u'str', 0.0],
|
||||
[u'n', u'Hds', True, True, u'%1.0f', u'str', 1.0],
|
||||
[u'avgseats', u'Seats', False, False, u'%3.1f', u'str', 1.0],
|
||||
[u'vpip', u'VPIP', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'pfr', u'PFR', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'pf3', u'PF3', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'aggfac', u'AggFac', True, True, u'%2.2f', u'str', 1.0],
|
||||
[u'aggfrq', u'AggFreq', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'conbet', u'ContBet', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'rfi', u'RFI', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'steals', u'Steals', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'saw_f', u'Saw_F', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'sawsd', u'SawSD', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'wtsdwsf', u'WtSDwsF', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'wmsd', u'W$SD', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'flafq', u'FlAFq', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'tuafq', u'TuAFq', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'rvafq', u'RvAFq', True, True, u'%3.1f', u'str', 1.0],
|
||||
[u'pofafq', u'PoFAFq', False, False, u'%3.1f', u'str', 1.0],
|
||||
[u'net', u'Net($)', True, True, u'%6.2f', u'cash', 1.0],
|
||||
[u'bbper100', u'bb/100', True, True, u'%4.2f', u'str', 1.0],
|
||||
[u'rake', u'Rake($)', True, True, u'%6.2f', u'cash', 1.0],
|
||||
[u'bb100xr', u'bbxr/100', True, True, u'%4.2f', u'str', 1.0],
|
||||
[u'variance', u'Variance', True, True, u'%5.2f', u'str', 1.0]
|
||||
]
|
||||
for col in defaults:
|
||||
self.append (col)
|
||||
|
||||
# def __str__(self):
|
||||
# s = ""
|
||||
# for l in self:
|
||||
|
@ -595,11 +628,14 @@ class Config:
|
|||
self.db_selected = None # database the user would like to use
|
||||
self.tv = None
|
||||
self.general = General()
|
||||
self.emails = {}
|
||||
self.gui_cash_stats = GUICashStats()
|
||||
|
||||
for gen_node in doc.getElementsByTagName("general"):
|
||||
self.general.add_elements(node=gen_node) # add/overwrite elements in self.general
|
||||
|
||||
if doc.getElementsByTagName("gui_cash_stats") == []:
|
||||
self.gui_cash_stats.get_defaults()
|
||||
for gcs_node in doc.getElementsByTagName("gui_cash_stats"):
|
||||
self.gui_cash_stats.add_elements(node=gcs_node) # add/overwrite elements in self.gui_cash_stats
|
||||
|
||||
|
@ -655,7 +691,8 @@ class Config:
|
|||
|
||||
for email_node in doc.getElementsByTagName("email"):
|
||||
email = Email(node = email_node)
|
||||
self.email = email
|
||||
if email.siteName!="": #FIXME: Why on earth is this needed?
|
||||
self.emails[email.siteName+"_"+email.fetchType]=email
|
||||
|
||||
for hui_node in doc.getElementsByTagName('hud_ui'):
|
||||
hui = HudUI(node = hui_node)
|
||||
|
@ -702,6 +739,12 @@ class Config:
|
|||
if site_node.getAttribute("site_name") == site:
|
||||
return site_node
|
||||
|
||||
def getEmailNode(self, siteName, fetchType):
|
||||
for emailNode in self.doc.getElementsByTagName("email"):
|
||||
if emailNode.getAttribute("siteName") == siteName and emailNode.getAttribute("fetchType") == fetchType:
|
||||
return emailNode
|
||||
#end def getEmailNode
|
||||
|
||||
def getGameNode(self,gameName):
|
||||
"""returns DOM game node for a given game"""
|
||||
for gameNode in self.doc.getElementsByTagName("game"):
|
||||
|
@ -776,6 +819,15 @@ class Config:
|
|||
else:
|
||||
return(l)
|
||||
|
||||
def editEmail(self, siteName, fetchType, newEmail):
|
||||
emailNode = self.getEmailNode(siteName, fetchType)
|
||||
emailNode.setAttribute("host", newEmail.host)
|
||||
emailNode.setAttribute("username", newEmail.username)
|
||||
emailNode.setAttribute("password", newEmail.password)
|
||||
emailNode.setAttribute("folder", newEmail.folder)
|
||||
emailNode.setAttribute("useSsl", newEmail.useSsl)
|
||||
#end def editEmail
|
||||
|
||||
def edit_layout(self, site_name, max, width = None, height = None,
|
||||
fav_seat = None, locations = None):
|
||||
site_node = self.get_site_node(site_name)
|
||||
|
|
|
@ -74,7 +74,7 @@ except ImportError:
|
|||
use_numpy = False
|
||||
|
||||
|
||||
DB_VERSION = 139
|
||||
DB_VERSION = 142
|
||||
|
||||
|
||||
# Variance created as sqlite has a bunch of undefined aggregate functions.
|
||||
|
@ -140,7 +140,7 @@ class Database:
|
|||
, {'tab':'TourneysPlayers', 'col':'playerId', 'drop':0}
|
||||
#, {'tab':'TourneysPlayers', 'col':'tourneyId', 'drop':0} unique indexes not dropped
|
||||
, {'tab':'TourneyTypes', 'col':'siteId', 'drop':0}
|
||||
, {'tab':'Backings', 'col':'tourneysPlayerId', 'drop':0}
|
||||
, {'tab':'Backings', 'col':'tourneysPlayersId', 'drop':0}
|
||||
, {'tab':'Backings', 'col':'playerId', 'drop':0}
|
||||
]
|
||||
, [ # indexes for sqlite (list index 4)
|
||||
|
@ -155,7 +155,7 @@ class Database:
|
|||
, {'tab':'Tourneys', 'col':'tourneyTypeId', 'drop':1}
|
||||
, {'tab':'TourneysPlayers', 'col':'playerId', 'drop':0}
|
||||
, {'tab':'TourneyTypes', 'col':'siteId', 'drop':0}
|
||||
, {'tab':'Backings', 'col':'tourneysPlayerId', 'drop':0}
|
||||
, {'tab':'Backings', 'col':'tourneysPlayersId', 'drop':0}
|
||||
, {'tab':'Backings', 'col':'playerId', 'drop':0}
|
||||
]
|
||||
]
|
||||
|
@ -265,7 +265,7 @@ class Database:
|
|||
#ISOLATION_LEVEL_SERIALIZABLE = 2
|
||||
|
||||
|
||||
if self.backend == self.SQLITE and self.database == ':memory:' and self.wrongDbVersion:
|
||||
if self.backend == self.SQLITE and self.database == ':memory:' and self.wrongDbVersion and self.is_connected():
|
||||
log.info("sqlite/:memory: - creating")
|
||||
self.recreate_tables()
|
||||
self.wrongDbVersion = False
|
||||
|
@ -289,7 +289,8 @@ class Database:
|
|||
|
||||
self.saveActions = False if self.import_options['saveActions'] == False else True
|
||||
|
||||
self.connection.rollback() # make sure any locks taken so far are released
|
||||
if self.is_connected():
|
||||
self.connection.rollback() # make sure any locks taken so far are released
|
||||
#end def __init__
|
||||
|
||||
def dumpDatabase(self):
|
||||
|
@ -342,7 +343,6 @@ class Database:
|
|||
self.db_server = db_params['db-server']
|
||||
self.database = db_params['db-databaseName']
|
||||
self.host = db_params['db-host']
|
||||
self.__connected = True
|
||||
|
||||
def connect(self, backend=None, host=None, database=None,
|
||||
user=None, password=None, create=False):
|
||||
|
@ -363,6 +363,7 @@ class Database:
|
|||
MySQLdb = pool.manage(MySQLdb, pool_size=5)
|
||||
try:
|
||||
self.connection = MySQLdb.connect(host=host, user=user, passwd=password, db=database, use_unicode=True)
|
||||
self.__connected = True
|
||||
#TODO: Add port option
|
||||
except MySQLdb.Error, ex:
|
||||
if ex.args[0] == 1045:
|
||||
|
@ -384,20 +385,21 @@ class Database:
|
|||
# flat out wrong
|
||||
# sqlcoder: This database only connect failed in my windows setup??
|
||||
# Modifed it to try the 4 parameter style if the first connect fails - does this work everywhere?
|
||||
connected = False
|
||||
self.__connected = False
|
||||
if self.host == "localhost" or self.host == "127.0.0.1":
|
||||
try:
|
||||
self.connection = psycopg2.connect(database = database)
|
||||
connected = True
|
||||
self.__connected = True
|
||||
except:
|
||||
# direct connection failed so try user/pass/... version
|
||||
pass
|
||||
if not connected:
|
||||
if not self.is_connected():
|
||||
try:
|
||||
self.connection = psycopg2.connect(host = host,
|
||||
user = user,
|
||||
password = password,
|
||||
database = database)
|
||||
self.__connected = True
|
||||
except Exception, ex:
|
||||
if 'Connection refused' in ex.args[0]:
|
||||
# meaning eg. db not running
|
||||
|
@ -426,6 +428,7 @@ class Database:
|
|||
log.info("Connecting to SQLite: %(database)s" % {'database':self.db_path})
|
||||
if os.path.exists(database) or create:
|
||||
self.connection = sqlite3.connect(self.db_path, detect_types=sqlite3.PARSE_DECLTYPES )
|
||||
self.__connected = True
|
||||
sqlite3.register_converter("bool", lambda x: bool(int(x)))
|
||||
sqlite3.register_adapter(bool, lambda x: "1" if x else "0")
|
||||
self.connection.create_function("floor", 1, math.floor)
|
||||
|
@ -443,9 +446,10 @@ class Database:
|
|||
else:
|
||||
raise FpdbError("unrecognised database backend:"+str(backend))
|
||||
|
||||
self.cursor = self.connection.cursor()
|
||||
self.cursor.execute(self.sql.query['set tx level'])
|
||||
self.check_version(database=database, create=create)
|
||||
if self.is_connected():
|
||||
self.cursor = self.connection.cursor()
|
||||
self.cursor.execute(self.sql.query['set tx level'])
|
||||
self.check_version(database=database, create=create)
|
||||
|
||||
|
||||
def check_version(self, database, create):
|
||||
|
@ -499,6 +503,10 @@ class Database:
|
|||
self.connection.rollback()
|
||||
|
||||
def connected(self):
|
||||
""" now deprecated, use is_connected() instead """
|
||||
return self.__connected
|
||||
|
||||
def is_connected(self):
|
||||
return self.__connected
|
||||
|
||||
def get_cursor(self):
|
||||
|
@ -1442,17 +1450,41 @@ class Database:
|
|||
h_start = self.hero_hudstart_def
|
||||
if v_start is None:
|
||||
v_start = self.villain_hudstart_def
|
||||
|
||||
if self.hero_ids == {}:
|
||||
where = ""
|
||||
where = "WHERE hp.tourneysPlayersId IS NULL"
|
||||
else:
|
||||
where = "where ( hp.playerId not in " + str(tuple(self.hero_ids.values())) \
|
||||
where = "where ((( hp.playerId not in " + str(tuple(self.hero_ids.values())) \
|
||||
+ " and h.startTime > '" + v_start + "')" \
|
||||
+ " or ( hp.playerId in " + str(tuple(self.hero_ids.values())) \
|
||||
+ " and h.startTime > '" + h_start + "')"
|
||||
rebuild_sql = self.sql.query['rebuildHudCache'].replace('<where_clause>', where)
|
||||
|
||||
+ " and h.startTime > '" + h_start + "'))" \
|
||||
+ " AND hp.tourneysPlayersId IS NULL)"
|
||||
rebuild_sql_cash = self.sql.query['rebuildHudCache'].replace('<tourney_insert_clause>', "")
|
||||
rebuild_sql_cash = rebuild_sql_cash.replace('<tourney_select_clause>', "")
|
||||
rebuild_sql_cash = rebuild_sql_cash.replace('<tourney_join_clause>', "")
|
||||
rebuild_sql_cash = rebuild_sql_cash.replace('<tourney_group_clause>', "")
|
||||
rebuild_sql_cash = rebuild_sql_cash.replace('<where_clause>', where)
|
||||
#print "rebuild_sql_cash:",rebuild_sql_cash
|
||||
self.get_cursor().execute(self.sql.query['clearHudCache'])
|
||||
self.get_cursor().execute(rebuild_sql)
|
||||
self.get_cursor().execute(rebuild_sql_cash)
|
||||
|
||||
if self.hero_ids == {}:
|
||||
where = "WHERE hp.tourneysPlayersId >= 0"
|
||||
else:
|
||||
where = "where ((( hp.playerId not in " + str(tuple(self.hero_ids.values())) \
|
||||
+ " and h.startTime > '" + v_start + "')" \
|
||||
+ " or ( hp.playerId in " + str(tuple(self.hero_ids.values())) \
|
||||
+ " and h.startTime > '" + h_start + "'))" \
|
||||
+ " AND hp.tourneysPlayersId >= 0)"
|
||||
rebuild_sql_tourney = self.sql.query['rebuildHudCache'].replace('<tourney_insert_clause>', ",tourneyTypeId")
|
||||
rebuild_sql_tourney = rebuild_sql_tourney.replace('<tourney_select_clause>', ",t.tourneyTypeId")
|
||||
rebuild_sql_tourney = rebuild_sql_tourney.replace('<tourney_join_clause>', """INNER JOIN TourneysPlayers tp ON (tp.id = hp.tourneysPlayersId)
|
||||
INNER JOIN Tourneys t ON (t.id = tp.tourneyId)""")
|
||||
rebuild_sql_tourney = rebuild_sql_tourney.replace('<tourney_group_clause>', ",t.tourneyTypeId")
|
||||
rebuild_sql_tourney = rebuild_sql_tourney.replace('<where_clause>', where)
|
||||
#print "rebuild_sql_tourney:",rebuild_sql_tourney
|
||||
|
||||
self.get_cursor().execute(rebuild_sql_tourney)
|
||||
self.commit()
|
||||
print "Rebuild hudcache took %.1f seconds" % (time() - stime,)
|
||||
except:
|
||||
|
@ -2021,8 +2053,12 @@ class Database:
|
|||
result=cursor.fetchone()
|
||||
|
||||
if result != None:
|
||||
expectedValues = ('comment', 'tourneyName', 'matrixIdProcessed', 'totalRebuyCount', 'totalAddOnCount',
|
||||
'prizepool', 'startTime', 'entries', 'commentTs', 'endTime')
|
||||
if self.backend == Database.PGSQL:
|
||||
expectedValues = ('comment', 'tourneyname', 'matrixIdProcessed', 'totalRebuyCount', 'totalAddOnCount',
|
||||
'prizepool', 'startTime', 'entries', 'commentTs', 'endTime')
|
||||
else:
|
||||
expectedValues = ('comment', 'tourneyName', 'matrixIdProcessed', 'totalRebuyCount', 'totalAddOnCount',
|
||||
'prizepool', 'startTime', 'entries', 'commentTs', 'endTime')
|
||||
updateDb=False
|
||||
resultDict = dict(zip(columnNames, result))
|
||||
|
||||
|
@ -2115,6 +2151,32 @@ class Database:
|
|||
result = c.fetchall()
|
||||
return result
|
||||
#end def getTourneyTypesIds
|
||||
|
||||
def getTourneyInfo(self, siteName, tourneyNo):
|
||||
c = self.get_cursor()
|
||||
c.execute(self.sql.query['getTourneyInfo'], (siteName, tourneyNo))
|
||||
columnNames=c.description
|
||||
|
||||
names=[]
|
||||
for column in columnNames:
|
||||
names.append(column[0])
|
||||
|
||||
data=c.fetchone()
|
||||
return (names,data)
|
||||
#end def getTourneyInfo
|
||||
|
||||
def getTourneyPlayerInfo(self, siteName, tourneyNo, playerName):
|
||||
c = self.get_cursor()
|
||||
c.execute(self.sql.query['getTourneyPlayerInfo'], (siteName, tourneyNo, playerName))
|
||||
columnNames=c.description
|
||||
|
||||
names=[]
|
||||
for column in columnNames:
|
||||
names.append(column[0])
|
||||
|
||||
data=c.fetchone()
|
||||
return (names,data)
|
||||
#end def getTourneyPlayerInfo
|
||||
#end class Database
|
||||
|
||||
# Class used to hold all the data needed to write a hand to the db
|
||||
|
|
|
@ -290,9 +290,11 @@ class DerivedStats():
|
|||
# print "p_actions:", self.pfba(actions), "p_folds:", self.pfba(actions, l=('folds',)), "alliners:", alliners
|
||||
# pas = set.union(self.pfba(actions) - self.pfba(actions, l=('folds',)), alliners)
|
||||
|
||||
# hand.players includes people that are sitting out on some sites.
|
||||
# Those that posted an ante should have been deal cards.
|
||||
p_in = set([x[0] for x in hand.actions['BLINDSANTES']] + [x[0] for x in hand.actions['PREFLOP']])
|
||||
# hand.players includes people that are sitting out on some sites for cash games
|
||||
# actionStreets[1] is 'DEAL', 'THIRD', 'PREFLOP', so any player dealt cards
|
||||
# must act on this street if dealt cards. Almost certainly broken for the 'all-in blind' case
|
||||
# and right now i don't care - CG
|
||||
p_in = set([x[0] for x in hand.actions[hand.actionStreets[1]]])
|
||||
|
||||
for (i, street) in enumerate(hand.actionStreets):
|
||||
actions = hand.actions[street]
|
||||
|
|
|
@ -31,18 +31,23 @@ class Fulltilt(HandHistoryConverter):
|
|||
codepage = ["utf-16", "cp1252", "utf-8"]
|
||||
siteId = 1 # Needs to match id entry in Sites database
|
||||
|
||||
substitutions = {
|
||||
'LEGAL_ISO' : "USD|EUR|GBP|CAD|FPP", # legal ISO currency codes
|
||||
'LS' : "\$|\xe2\x82\xac|" # legal currency symbols - Euro(cp1252, utf-8)
|
||||
}
|
||||
|
||||
# Static regexes
|
||||
re_GameInfo = re.compile('''.*\#(?P<HID>[0-9]+):\s
|
||||
(?:(?P<TOURNAMENT>.+)\s\((?P<TOURNO>\d+)\),\s)?
|
||||
.+
|
||||
-\s(?P<CURRENCY>\$|)?
|
||||
-\s(?P<CURRENCY>[%(LS)s]|)?
|
||||
(?P<SB>[.0-9]+)/
|
||||
\$?(?P<BB>[.0-9]+)\s
|
||||
[%(LS)s]?(?P<BB>[.0-9]+)\s
|
||||
(Ante\s\$?(?P<ANTE>[.0-9]+)\s)?-\s
|
||||
\$?(?P<CAP>[.0-9]+\sCap\s)?
|
||||
[%(LS)s]?(?P<CAP>[.0-9]+\sCap\s)?
|
||||
(?P<LIMIT>(No\sLimit|Pot\sLimit|Limit))?\s
|
||||
(?P<GAME>(Hold\'em|Omaha\sHi|Omaha\sH/L|7\sCard\sStud|Stud\sH/L|Razz|Stud\sHi))
|
||||
''', re.VERBOSE)
|
||||
''' % substitutions, re.VERBOSE)
|
||||
re_SplitHands = re.compile(r"\n\n+")
|
||||
re_TailSplitHands = re.compile(r"(\n\n+)")
|
||||
re_HandInfo = re.compile(r'''.*\#(?P<HID>[0-9]+):\s
|
||||
|
@ -51,29 +56,29 @@ class Fulltilt(HandHistoryConverter):
|
|||
(?P<PLAY>Play\sChip\s|PC)?
|
||||
(?P<TABLE>[-\s\da-zA-Z]+)\s
|
||||
(\((?P<TABLEATTRIBUTES>.+)\)\s)?-\s
|
||||
\$?(?P<SB>[.0-9]+)/\$?(?P<BB>[.0-9]+)\s(Ante\s\$?(?P<ANTE>[.0-9]+)\s)?-\s
|
||||
\$?(?P<CAP>[.0-9]+\sCap\s)?
|
||||
[%(LS)s]?(?P<SB>[.0-9]+)/[%(LS)s]?(?P<BB>[.0-9]+)\s(Ante\s[%(LS)s]?(?P<ANTE>[.0-9]+)\s)?-\s
|
||||
[%(LS)s]?(?P<CAP>[.0-9]+\sCap\s)?
|
||||
(?P<GAMETYPE>[a-zA-Z\/\'\s]+)\s-\s
|
||||
(?P<DATETIME>\d+:\d+:\d+\s(?P<TZ1>\w+)\s-\s\d+/\d+/\d+|\d+:\d+\s(?P<TZ2>\w+)\s-\s\w+\,\s\w+\s\d+\,\s\d+)
|
||||
(?P<PARTIAL>\(partial\))?\n
|
||||
(?:.*?\n(?P<CANCELLED>Hand\s\#(?P=HID)\shas\sbeen\scanceled))?
|
||||
''', re.VERBOSE|re.DOTALL)
|
||||
''' % substitutions, re.VERBOSE|re.DOTALL)
|
||||
re_TourneyExtraInfo = re.compile('''(((?P<TOURNEY_NAME>[^$]+)?
|
||||
(?P<CURRENCY>\$)?(?P<BUYIN>[.0-9]+)?\s*\+\s*\$?(?P<FEE>[.0-9]+)?
|
||||
(?P<CURRENCY>[%(LS)s])?(?P<BUYIN>[.0-9]+)?\s*\+\s*[%(LS)s]?(?P<FEE>[.0-9]+)?
|
||||
(\s(?P<SPECIAL>(KO|Heads\sUp|Matrix\s\dx|Rebuy|Madness)))?
|
||||
(\s(?P<SHOOTOUT>Shootout))?
|
||||
(\s(?P<SNG>Sit\s&\sGo))?
|
||||
(\s\((?P<TURBO>Turbo)\))?)|(?P<UNREADABLE_INFO>.+))
|
||||
''', re.VERBOSE)
|
||||
''' % substitutions, re.VERBOSE)
|
||||
re_Button = re.compile('^The button is in seat #(?P<BUTTON>\d+)', re.MULTILINE)
|
||||
re_PlayerInfo = re.compile('Seat (?P<SEAT>[0-9]+): (?P<PNAME>.{2,15}) \(\$(?P<CASH>[,.0-9]+)\)$', re.MULTILINE)
|
||||
re_TourneysPlayerInfo = re.compile('Seat (?P<SEAT>[0-9]+): (?P<PNAME>.{2,15}) \(\$?(?P<CASH>[,.0-9]+)\)(, is sitting out)?$', re.MULTILINE)
|
||||
re_PlayerInfo = re.compile('Seat (?P<SEAT>[0-9]+): (?P<PNAME>.{2,15}) \([%(LS)s](?P<CASH>[,.0-9]+)\)$' % substitutions, re.MULTILINE)
|
||||
re_TourneysPlayerInfo = re.compile('Seat (?P<SEAT>[0-9]+): (?P<PNAME>.{2,15}) \([%(LS)s]?(?P<CASH>[,.0-9]+)\)(, is sitting out)?$' % substitutions, re.MULTILINE)
|
||||
re_Board = re.compile(r"\[(?P<CARDS>.+)\]")
|
||||
|
||||
#static regex for tourney purpose
|
||||
re_TourneyInfo = re.compile('''Tournament\sSummary\s
|
||||
(?P<TOURNAMENT_NAME>[^$(]+)?\s*
|
||||
((?P<CURRENCY>\$|)?(?P<BUYIN>[.0-9]+)\s*\+\s*\$?(?P<FEE>[.0-9]+)\s)?
|
||||
((?P<CURRENCY>[%(LS)s]|)?(?P<BUYIN>[.0-9]+)\s*\+\s*[%(LS)s]?(?P<FEE>[.0-9]+)\s)?
|
||||
((?P<SPECIAL>(KO|Heads\sUp|Matrix\s\dx|Rebuy|Madness))\s)?
|
||||
((?P<SHOOTOUT>Shootout)\s)?
|
||||
((?P<SNG>Sit\s&\sGo)\s)?
|
||||
|
@ -83,24 +88,24 @@ class Fulltilt(HandHistoryConverter):
|
|||
(?P<GAME>(Hold\'em|Omaha\sHi|Omaha\sH/L|7\sCard\sStud|Stud\sH/L|Razz|Stud\sHi))\s
|
||||
(\((?P<TURBO2>Turbo)\)\s)?
|
||||
(?P<LIMIT>(No\sLimit|Pot\sLimit|Limit))?
|
||||
''', re.VERBOSE)
|
||||
re_TourneyBuyInFee = re.compile("Buy-In: (?P<BUYIN_CURRENCY>\$|)?(?P<BUYIN>[.0-9]+) \+ \$?(?P<FEE>[.0-9]+)")
|
||||
''' % substitutions, re.VERBOSE)
|
||||
re_TourneyBuyInFee = re.compile("Buy-In: (?P<BUYIN_CURRENCY>[%(LS)s]|)?(?P<BUYIN>[.0-9]+) \+ [%(LS)s]?(?P<FEE>[.0-9]+)" % substitutions)
|
||||
re_TourneyBuyInChips = re.compile("Buy-In Chips: (?P<BUYINCHIPS>\d+)")
|
||||
re_TourneyEntries = re.compile("(?P<ENTRIES>\d+) Entries")
|
||||
re_TourneyPrizePool = re.compile("Total Prize Pool: (?P<PRIZEPOOL_CURRENCY>\$|)?(?P<PRIZEPOOL>[.,0-9]+)")
|
||||
re_TourneyRebuyCost = re.compile("Rebuy: (?P<REBUY_CURRENCY>\$|)?(?P<REBUY_COST>[.,0-9]+)")
|
||||
re_TourneyAddOnCost = re.compile("Add-On: (?P<ADDON_CURRENCY>\$|)?(?P<ADDON_COST>[.,0-9]+)")
|
||||
re_TourneyPrizePool = re.compile("Total Prize Pool: (?P<PRIZEPOOL_CURRENCY>[%(LS)s]|)?(?P<PRIZEPOOL>[.,0-9]+)" % substitutions)
|
||||
re_TourneyRebuyCost = re.compile("Rebuy: (?P<REBUY_CURRENCY>[%(LS)s]|)?(?P<REBUY_COST>[.,0-9]+)"% substitutions)
|
||||
re_TourneyAddOnCost = re.compile("Add-On: (?P<ADDON_CURRENCY>[%(LS)s]|)?(?P<ADDON_COST>[.,0-9]+)"% substitutions)
|
||||
re_TourneyRebuyCount = re.compile("performed (?P<REBUY_COUNT>\d+) Rebuy")
|
||||
re_TourneyAddOnCount = re.compile("performed (?P<ADDON_COUNT>\d+) Add-On")
|
||||
re_TourneyRebuysTotal = re.compile("Total Rebuys: (?P<REBUY_TOTAL>\d+)")
|
||||
re_TourneyAddOnsTotal = re.compile("Total Add-Ons: (?P<ADDONS_TOTAL>\d+)")
|
||||
re_TourneyRebuyChips = re.compile("Rebuy Chips: (?P<REBUY_CHIPS>\d+)")
|
||||
re_TourneyAddOnChips = re.compile("Add-On Chips: (?P<ADDON_CHIPS>\d+)")
|
||||
re_TourneyKOBounty = re.compile("Knockout Bounty: (?P<KO_BOUNTY_CURRENCY>\$|)?(?P<KO_BOUNTY_AMOUNT>[.,0-9]+)")
|
||||
re_TourneyKOBounty = re.compile("Knockout Bounty: (?P<KO_BOUNTY_CURRENCY>[%(LS)s]|)?(?P<KO_BOUNTY_AMOUNT>[.,0-9]+)" % substitutions)
|
||||
re_TourneyKoCount = re.compile("received (?P<COUNT_KO>\d+) Knockout Bounty Award(s)?")
|
||||
re_TourneyTimeInfo = re.compile("Tournament started: (?P<STARTTIME>.*)\nTournament ((?P<IN_PROGRESS>is still in progress)?|(finished:(?P<ENDTIME>.*))?)$")
|
||||
|
||||
re_TourneysPlayersSummary = re.compile("^(?P<RANK>(Still Playing|\d+))( - |: )(?P<PNAME>[^\n,]+)(, )?(?P<WINNING_CURRENCY>\$|)?(?P<WINNING>[.\d]+)?", re.MULTILINE)
|
||||
re_TourneysPlayersSummary = re.compile("^(?P<RANK>(Still Playing|\d+))( - |: )(?P<PNAME>[^\n,]+)(, )?(?P<WINNING_CURRENCY>[%(LS)s]|)?(?P<WINNING>[.\d]+)?" % substitutions, re.MULTILINE)
|
||||
re_TourneyHeroFinishingP = re.compile("(?P<HERO_NAME>.*) finished in (?P<HERO_FINISHING_POS>\d+)(st|nd|rd|th) place")
|
||||
|
||||
#TODO: See if we need to deal with play money tourney summaries -- Not right now (they shouldn't pass the re_TourneyInfo)
|
||||
|
@ -127,17 +132,19 @@ class Fulltilt(HandHistoryConverter):
|
|||
# we need to recompile the player regexs.
|
||||
self.compiledPlayers = players
|
||||
player_re = "(?P<PNAME>" + "|".join(map(re.escape, players)) + ")"
|
||||
self.substitutions['PLAYERS'] = player_re
|
||||
|
||||
logging.debug("player_re: " + player_re)
|
||||
self.re_PostSB = re.compile(r"^%s posts the small blind of \$?(?P<SB>[.0-9]+)" % player_re, re.MULTILINE)
|
||||
self.re_PostDead = re.compile(r"^%s posts a dead small blind of \$?(?P<SB>[.0-9]+)" % player_re, re.MULTILINE)
|
||||
self.re_PostBB = re.compile(r"^%s posts (the big blind of )?\$?(?P<BB>[.0-9]+)" % player_re, re.MULTILINE)
|
||||
self.re_Antes = re.compile(r"^%s antes \$?(?P<ANTE>[.0-9]+)" % player_re, re.MULTILINE)
|
||||
self.re_BringIn = re.compile(r"^%s brings in for \$?(?P<BRINGIN>[.0-9]+)" % player_re, re.MULTILINE)
|
||||
self.re_PostBoth = re.compile(r"^%s posts small \& big blinds \[\$? (?P<SBBB>[.0-9]+)" % player_re, re.MULTILINE)
|
||||
self.re_PostSB = re.compile(r"^%(PLAYERS)s posts the small blind of [%(LS)s]?(?P<SB>[.0-9]+)" % self.substitutions, re.MULTILINE)
|
||||
self.re_PostDead = re.compile(r"^%(PLAYERS)s posts a dead small blind of [%(LS)s]?(?P<SB>[.0-9]+)" % self.substitutions, re.MULTILINE)
|
||||
self.re_PostBB = re.compile(r"^%(PLAYERS)s posts (the big blind of )?[%(LS)s]?(?P<BB>[.0-9]+)" % self.substitutions, re.MULTILINE)
|
||||
self.re_Antes = re.compile(r"^%(PLAYERS)s antes [%(LS)s]?(?P<ANTE>[.0-9]+)" % self.substitutions, re.MULTILINE)
|
||||
self.re_BringIn = re.compile(r"^%(PLAYERS)s brings in for [%(LS)s]?(?P<BRINGIN>[.0-9]+)" % self.substitutions, re.MULTILINE)
|
||||
self.re_PostBoth = re.compile(r"^%(PLAYERS)s posts small \& big blinds \[[%(LS)s]? (?P<SBBB>[.0-9]+)" % self.substitutions, re.MULTILINE)
|
||||
self.re_HeroCards = re.compile(r"^Dealt to %s(?: \[(?P<OLDCARDS>.+?)\])?( \[(?P<NEWCARDS>.+?)\])" % player_re, re.MULTILINE)
|
||||
self.re_Action = re.compile(r"^%s(?P<ATYPE> bets| checks| raises to| completes it to| calls| folds)( \$?(?P<BET>[.,\d]+))?" % player_re, re.MULTILINE)
|
||||
self.re_Action = re.compile(r"^%(PLAYERS)s(?P<ATYPE> bets| checks| raises to| completes it to| calls| folds)( [%(LS)s]?(?P<BET>[.,\d]+))?" % self.substitutions, re.MULTILINE)
|
||||
self.re_ShowdownAction = re.compile(r"^%s shows \[(?P<CARDS>.*)\]" % player_re, re.MULTILINE)
|
||||
self.re_CollectPot = re.compile(r"^Seat (?P<SEAT>[0-9]+): %s (\(button\) |\(small blind\) |\(big blind\) )?(collected|showed \[.*\] and won) \(\$?(?P<POT>[.,\d]+)\)(, mucked| with.*)" % player_re, re.MULTILINE)
|
||||
self.re_CollectPot = re.compile(r"^Seat (?P<SEAT>[0-9]+): %(PLAYERS)s (\(button\) |\(small blind\) |\(big blind\) )?(collected|showed \[.*\] and won) \([%(LS)s]?(?P<POT>[.,\d]+)\)(, mucked| with.*)" % self.substitutions, re.MULTILINE)
|
||||
self.re_SitsOut = re.compile(r"^%s sits out" % player_re, re.MULTILINE)
|
||||
self.re_ShownCards = re.compile(r"^Seat (?P<SEAT>[0-9]+): %s (\(button\) |\(small blind\) |\(big blind\) )?(?P<ACT>showed|mucked) \[(?P<CARDS>.*)\].*" % player_re, re.MULTILINE)
|
||||
|
||||
|
@ -177,7 +184,7 @@ class Fulltilt(HandHistoryConverter):
|
|||
'Stud Hi' : ('stud','studhi'),
|
||||
'Stud H/L' : ('stud','studhilo')
|
||||
}
|
||||
currencies = { u' €':'EUR', '$':'USD', '':'T$' }
|
||||
currencies = { u'€':'EUR', '$':'USD', '':'T$' }
|
||||
if mg['CAP']:
|
||||
info['limitType'] = 'cn'
|
||||
else:
|
||||
|
@ -704,5 +711,3 @@ if __name__ == "__main__":
|
|||
|
||||
e = Fulltilt(in_path = options.ipath, out_path = options.opath, follow = options.follow)
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -349,11 +349,11 @@ def main(argv=None):
|
|||
if options.usage == True:
|
||||
#Print usage examples and exit
|
||||
print "USAGE:"
|
||||
print 'PokerStars converter: ./GuiBulkImport -c PokerStars -f filename'
|
||||
print 'Full Tilt converter: ./GuiBulkImport -c "Full Tilt Poker" -f filename'
|
||||
print "Everleaf converter: ./GuiBulkImport -c Everleaf -f filename"
|
||||
print "Absolute converter: ./GuiBulkImport -c Absolute -f filename"
|
||||
print "PartyPoker converter: ./GuiBulkImport -c PartyPoker -f filename"
|
||||
print 'PokerStars converter: ./GuiBulkImport.py -c PokerStars -f filename'
|
||||
print 'Full Tilt converter: ./GuiBulkImport.py -c "Full Tilt Poker" -f filename'
|
||||
print "Everleaf converter: ./GuiBulkImport.py -c Everleaf -f filename"
|
||||
print "Absolute converter: ./GuiBulkImport.py -c Absolute -f filename"
|
||||
print "PartyPoker converter: ./GuiBulkImport.py -c PartyPoker -f filename"
|
||||
sys.exit(0)
|
||||
|
||||
config = Configuration.Config()
|
||||
|
|
154
pyfpdb/GuiImapFetcher.py
Normal file
154
pyfpdb/GuiImapFetcher.py
Normal file
|
@ -0,0 +1,154 @@
|
|||
#!/usr/bin/python
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
#Copyright 2010 Steffen Schaumburg
|
||||
#This program is free software: you can redistribute it and/or modify
|
||||
#it under the terms of the GNU Affero General Public License as published by
|
||||
#the Free Software Foundation, version 3 of the License.
|
||||
#
|
||||
#This program is distributed in the hope that it will be useful,
|
||||
#but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
#MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
#GNU General Public License for more details.
|
||||
#
|
||||
#You should have received a copy of the GNU Affero General Public License
|
||||
#along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#In the "official" distribution you can find the license in agpl-3.0.txt.
|
||||
|
||||
import threading
|
||||
import pygtk
|
||||
pygtk.require('2.0')
|
||||
import gtk
|
||||
from imaplib import IMAP4
|
||||
from socket import gaierror
|
||||
|
||||
import ImapFetcher
|
||||
|
||||
class GuiImapFetcher (threading.Thread):
|
||||
def __init__(self, config, db, sql, mainwin, debug=True):
|
||||
self.config = config
|
||||
self.db = db
|
||||
self.mainVBox = gtk.VBox()
|
||||
|
||||
|
||||
self.buttonsHBox = gtk.HBox()
|
||||
self.mainVBox.pack_end(self.buttonsHBox, expand=False)
|
||||
|
||||
label=gtk.Label("To cancel just close this tab.")
|
||||
self.buttonsHBox.add(label)
|
||||
|
||||
self.saveButton = gtk.Button("_Save")
|
||||
self.saveButton.connect('clicked', self.saveClicked)
|
||||
self.buttonsHBox.add(self.saveButton)
|
||||
|
||||
self.importAllButton = gtk.Button("_Import All")
|
||||
self.importAllButton.connect('clicked', self.importAllClicked)
|
||||
self.buttonsHBox.add(self.importAllButton)
|
||||
|
||||
self.statusLabel=gtk.Label("If you change the config you must save before importing")
|
||||
self.mainVBox.pack_end(self.statusLabel, expand=False, padding=4)
|
||||
|
||||
self.passwords={}
|
||||
self.displayConfig()
|
||||
|
||||
self.mainVBox.show_all()
|
||||
#end def __init__
|
||||
|
||||
def saveClicked(self, widget, data=None):
|
||||
row = self.rowVBox.get_children()
|
||||
columns=row[0].get_children() #TODO: make save capable of handling multiple email entries - not relevant yet as only one entry is useful atm. The rest of this tab works fine for multiple entries though
|
||||
|
||||
siteName=columns[0].get_text()
|
||||
fetchType=columns[1].get_text()
|
||||
code=siteName+"_"+fetchType
|
||||
|
||||
for email in self.config.emails:
|
||||
toSave=self.config.emails[email]
|
||||
break
|
||||
toSave.siteName=siteName
|
||||
toSave.fetchType=fetchType
|
||||
|
||||
toSave.host=columns[2].get_text()
|
||||
toSave.username=columns[3].get_text()
|
||||
|
||||
if columns[4].get_text()=="***":
|
||||
toSave.password=self.passwords[code]
|
||||
else:
|
||||
toSave.password=columns[4].get_text()
|
||||
|
||||
toSave.folder=columns[5].get_text()
|
||||
|
||||
if columns[6].get_active() == 0:
|
||||
toSave.useSsl="True"
|
||||
else:
|
||||
toSave.useSsl="False"
|
||||
|
||||
self.config.editEmail(siteName, fetchType, toSave)
|
||||
self.config.save()
|
||||
#def saveClicked
|
||||
|
||||
def importAllClicked(self, widget, data=None):
|
||||
self.statusLabel.set_label("Starting import. Please wait.") #FIXME: why doesnt this one show?
|
||||
for email in self.config.emails:
|
||||
try:
|
||||
result=ImapFetcher.run(self.config.emails[email], self.db)
|
||||
self.statusLabel.set_label("Finished import without error.")
|
||||
except IMAP4.error as error:
|
||||
if str(error)=="[AUTHENTICATIONFAILED] Authentication failed.":
|
||||
self.statusLabel.set_label("Login to mailserver failed: please check mailserver, username and password")
|
||||
except gaierror as error:
|
||||
if str(error)=="[Errno -2] Name or service not known":
|
||||
self.statusLabel.set_label("Could not connect to mailserver: check mailserver and use SSL settings and internet connectivity")
|
||||
#def importAllClicked
|
||||
|
||||
def get_vbox(self):
|
||||
"""returns the vbox of this thread"""
|
||||
return self.mainVBox
|
||||
#end def get_vbox
|
||||
|
||||
def displayConfig(self):
|
||||
box=gtk.HBox(homogeneous=True)
|
||||
for text in ("Site", "Fetch Type", "Mailserver", "Username", "Password", "Mail Folder", "Use SSL"):
|
||||
label=gtk.Label(text)
|
||||
box.add(label)
|
||||
self.mainVBox.pack_start(box, expand=False)
|
||||
|
||||
self.rowVBox = gtk.VBox()
|
||||
self.mainVBox.add(self.rowVBox)
|
||||
|
||||
for email in self.config.emails:
|
||||
config=self.config.emails[email]
|
||||
box=gtk.HBox(homogeneous=True)
|
||||
|
||||
for field in (config.siteName, config.fetchType):
|
||||
label=gtk.Label(field)
|
||||
box.add(label)
|
||||
|
||||
for field in (config.host, config.username):
|
||||
entry=gtk.Entry()
|
||||
entry.set_text(field)
|
||||
box.add(entry)
|
||||
|
||||
entry=gtk.Entry()
|
||||
self.passwords[email]=config.password
|
||||
entry.set_text("***")
|
||||
box.add(entry)
|
||||
|
||||
entry=gtk.Entry()
|
||||
entry.set_text(config.folder)
|
||||
box.add(entry)
|
||||
|
||||
sslBox = gtk.combo_box_new_text()
|
||||
sslBox.append_text("Yes")
|
||||
sslBox.append_text("No")
|
||||
sslBox.set_active(0)
|
||||
box.add(sslBox)
|
||||
|
||||
#TODO: "run just this one" button
|
||||
|
||||
self.rowVBox.pack_start(box, expand=False)
|
||||
#print
|
||||
|
||||
self.mainVBox.show_all()
|
||||
#end def displayConfig
|
||||
#end class GuiImapFetcher
|
|
@ -86,9 +86,9 @@ class GuiTourneyPlayerStats (GuiPlayerStats.GuiPlayerStats):
|
|||
, ["playerName", False, "Name", 0.0, "%s", "str"] # true not allowed for this line (set in code)
|
||||
, ["tourneyCount", True, "#", 1.0, "%1.0f", "str"]
|
||||
, ["itm", True, "ITM%", 1.0, "%3.2f", "str"]
|
||||
, ["1st", False, "1st", 1.0, "%1.0f", "str"]
|
||||
, ["2nd", True, "2nd", 1.0, "%1.0f", "str"]
|
||||
, ["3rd", True, "3rd", 1.0, "%1.0f", "str"]
|
||||
, ["_1st", False, "1st", 1.0, "%1.0f", "str"]
|
||||
, ["_2nd", True, "2nd", 1.0, "%1.0f", "str"]
|
||||
, ["_3rd", True, "3rd", 1.0, "%1.0f", "str"]
|
||||
, ["unknownRank", True, "Rank?", 1.0, "%1.0f", "str"]
|
||||
, ["spent", True, "Spent", 1.0, "%3.2f", "str"]
|
||||
, ["won", True, "Won", 1.0, "%3.2f", "str"]
|
||||
|
|
139
pyfpdb/GuiTourneyViewer.py
Normal file
139
pyfpdb/GuiTourneyViewer.py
Normal file
|
@ -0,0 +1,139 @@
|
|||
#!/usr/bin/python
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
#Copyright 2010 Steffen Schaumburg
|
||||
#This program is free software: you can redistribute it and/or modify
|
||||
#it under the terms of the GNU Affero General Public License as published by
|
||||
#the Free Software Foundation, version 3 of the License.
|
||||
#
|
||||
#This program is distributed in the hope that it will be useful,
|
||||
#but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
#MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
#GNU General Public License for more details.
|
||||
#
|
||||
#You should have received a copy of the GNU Affero General Public License
|
||||
#along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#In the "official" distribution you can find the license in agpl-3.0.txt.
|
||||
|
||||
import threading
|
||||
import pygtk
|
||||
pygtk.require('2.0')
|
||||
import gtk
|
||||
|
||||
class GuiTourneyViewer (threading.Thread):
|
||||
def __init__(self, config, db, sql, mainwin, debug=True):
|
||||
self.db = db
|
||||
|
||||
self.mainVBox = gtk.VBox()
|
||||
self.interfaceHBox = gtk.HBox()
|
||||
self.mainVBox.pack_start(self.interfaceHBox, expand=False)
|
||||
|
||||
self.siteBox = gtk.combo_box_new_text()
|
||||
for site in config.supported_sites:
|
||||
self.siteBox.append_text(site)
|
||||
self.siteBox.set_active(0)
|
||||
self.interfaceHBox.add(self.siteBox)
|
||||
|
||||
label=gtk.Label("Enter the tourney number you want to display:")
|
||||
self.interfaceHBox.add(label)
|
||||
|
||||
self.entryTourney = gtk.Entry()
|
||||
self.interfaceHBox.add(self.entryTourney)
|
||||
|
||||
self.displayButton = gtk.Button("_Display")
|
||||
self.displayButton.connect('clicked', self.displayClicked)
|
||||
self.interfaceHBox.add(self.displayButton)
|
||||
|
||||
self.entryPlayer = gtk.Entry()
|
||||
self.interfaceHBox.add(self.entryPlayer)
|
||||
|
||||
self.playerButton = gtk.Button("Display _Player")
|
||||
self.playerButton.connect('clicked', self.displayPlayerClicked)
|
||||
self.interfaceHBox.add(self.playerButton)
|
||||
|
||||
self.table = gtk.Table(columns=10, rows=9)
|
||||
self.mainVBox.add(self.table)
|
||||
|
||||
self.mainVBox.show_all()
|
||||
#end def __init__
|
||||
|
||||
def displayClicked(self, widget, data=None):
|
||||
if self.prepare(10, 9):
|
||||
result=self.db.getTourneyInfo(self.siteName, self.tourneyNo)
|
||||
if result[1] == None:
|
||||
self.table.destroy()
|
||||
self.errorLabel=gtk.Label("Tournament not found - please ensure you imported it and selected the correct site")
|
||||
self.mainVBox.add(self.errorLabel)
|
||||
else:
|
||||
x=0
|
||||
y=0
|
||||
for i in range(1,len(result[0])):
|
||||
if y==9:
|
||||
x+=2
|
||||
y=0
|
||||
|
||||
label=gtk.Label(result[0][i])
|
||||
self.table.attach(label,x,x+1,y,y+1)
|
||||
|
||||
if result[1][i]==None:
|
||||
label=gtk.Label("N/A")
|
||||
else:
|
||||
label=gtk.Label(result[1][i])
|
||||
self.table.attach(label,x+1,x+2,y,y+1)
|
||||
|
||||
y+=1
|
||||
self.mainVBox.show_all()
|
||||
#def displayClicked
|
||||
|
||||
def displayPlayerClicked(self, widget, data=None):
|
||||
if self.prepare(4, 5):
|
||||
result=self.db.getTourneyPlayerInfo(self.siteName, self.tourneyNo, self.playerName)
|
||||
if result[1] == None:
|
||||
self.table.destroy()
|
||||
self.errorLabel=gtk.Label("Player or tourney not found - please ensure you imported it and selected the correct site")
|
||||
self.mainVBox.add(self.errorLabel)
|
||||
else:
|
||||
x=0
|
||||
y=0
|
||||
for i in range(1,len(result[0])):
|
||||
if y==5:
|
||||
x+=2
|
||||
y=0
|
||||
|
||||
label=gtk.Label(result[0][i])
|
||||
self.table.attach(label,x,x+1,y,y+1)
|
||||
|
||||
if result[1][i]==None:
|
||||
label=gtk.Label("N/A")
|
||||
else:
|
||||
label=gtk.Label(result[1][i])
|
||||
self.table.attach(label,x+1,x+2,y,y+1)
|
||||
|
||||
y+=1
|
||||
self.mainVBox.show_all()
|
||||
#def displayPlayerClicked
|
||||
|
||||
def get_vbox(self):
|
||||
"""returns the vbox of this thread"""
|
||||
return self.mainVBox
|
||||
#end def get_vbox
|
||||
|
||||
def prepare(self, columns, rows):
|
||||
try: self.errorLabel.destroy()
|
||||
except: pass
|
||||
|
||||
try:
|
||||
self.tourneyNo=int(self.entryTourney.get_text())
|
||||
except ValueError:
|
||||
self.errorLabel=gtk.Label("invalid entry in tourney number - must enter numbers only")
|
||||
self.mainVBox.add(self.errorLabel)
|
||||
return False
|
||||
self.siteName=self.siteBox.get_active_text()
|
||||
self.playerName=self.entryPlayer.get_text()
|
||||
|
||||
self.table.destroy()
|
||||
self.table=gtk.Table(columns=columns, rows=rows)
|
||||
self.mainVBox.add(self.table)
|
||||
return True
|
||||
#end def readInfo
|
||||
#end class GuiTourneyViewer
|
|
@ -11,6 +11,36 @@
|
|||
|
||||
<import callFpdbHud = "True" interval = "10" fastStoreHudCache="False" hhArchiveBase="~/.fpdb/HandHistories/" saveActions="True"></import>
|
||||
|
||||
<gui_cash_stats>
|
||||
<col col_name="game" disp_all="True" disp_posn="True" col_title="Game" xalignment="0.0" field_format="%s" field_type="str" />
|
||||
<col col_name="hand" disp_all="False" disp_posn="False" col_title="Hand" xalignment="0.0" field_format="%s" field_type="str" />
|
||||
<col col_name="plposition" disp_all="False" disp_posn="False" col_title="Posn" xalignment="1.0" field_format="%s" field_type="str" />
|
||||
<col col_name="pname" disp_all="False" disp_posn="False" col_title="Name" xalignment="0.0" field_format="%s" field_type="str" />
|
||||
<col col_name="n" disp_all="True" disp_posn="True" col_title="Hds" xalignment="1.0" field_format="%1.0f" field_type="str" />
|
||||
<col col_name="avgseats" disp_all="False" disp_posn="False" col_title="Seats" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="vpip" disp_all="True" disp_posn="True" col_title="VPIP" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="pfr" disp_all="True" disp_posn="True" col_title="PFR" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="pf3" disp_all="True" disp_posn="True" col_title="PF3" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="aggfac" disp_all="True" disp_posn="True" col_title="AggFac" xalignment="1.0" field_format="%2.2f" field_type="str" />
|
||||
<col col_name="aggfrq" disp_all="True" disp_posn="True" col_title="AggFreq" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="conbet" disp_all="True" disp_posn="True" col_title="ContBet" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="rfi" disp_all="True" disp_posn="True" col_title="RFI" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="steals" disp_all="True" disp_posn="True" col_title="Steals" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="saw_f" disp_all="True" disp_posn="True" col_title="Saw_F" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="sawsd" disp_all="True" disp_posn="True" col_title="SawSD" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="wtsdwsf" disp_all="True" disp_posn="True" col_title="WtSDwsF" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="wmsd" disp_all="True" disp_posn="True" col_title="W$SD" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="flafq" disp_all="True" disp_posn="True" col_title="FlAFq" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="tuafq" disp_all="True" disp_posn="True" col_title="TuAFq" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="rvafq" disp_all="True" disp_posn="True" col_title="RvAFq" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="pofafq" disp_all="False" disp_posn="False" col_title="PoFAFq" xalignment="1.0" field_format="%3.1f" field_type="str" />
|
||||
<col col_name="net" disp_all="True" disp_posn="True" col_title="Net($)" xalignment="1.0" field_format="%6.2f" field_type="cash" />
|
||||
<col col_name="bbper100" disp_all="True" disp_posn="True" col_title="bb/100" xalignment="1.0" field_format="%4.2f" field_type="str" />
|
||||
<col col_name="rake" disp_all="True" disp_posn="True" col_title="Rake($)" xalignment="1.0" field_format="%6.2f" field_type="cash" />
|
||||
<col col_name="bb100xr" disp_all="True" disp_posn="True" col_title="bbxr/100" xalignment="1.0" field_format="%4.2f" field_type="str" />
|
||||
<col col_name="variance" disp_all="True" disp_posn="True" col_title="Variance" xalignment="1.0" field_format="%5.2f" field_type="str" />
|
||||
</gui_cash_stats>
|
||||
|
||||
<!-- These values determine what stats are displayed in the HUD
|
||||
|
||||
The following values define how opponents' stats are done, the first 2 determine
|
||||
|
@ -222,49 +252,46 @@ Left-Drag to Move"
|
|||
</layout>
|
||||
</site>
|
||||
|
||||
<site enabled="False"
|
||||
site_name="Everleaf"
|
||||
table_finder="Everleaf.exe"
|
||||
screen_name="YOUR SCREEN NAME HERE"
|
||||
site_path=""
|
||||
HH_path=""
|
||||
decoder="everleaf_decode_table"
|
||||
converter="EverleafToFpdb"
|
||||
supported_games="holdem">
|
||||
<layout fav_seat="0" height="547" max="8" width="794">
|
||||
<location seat="1" x="640" y="64"> </location>
|
||||
<location seat="2" x="650" y="230"> </location>
|
||||
<location seat="3" x="650" y="385"> </location>
|
||||
<location seat="4" x="588" y="425"> </location>
|
||||
<location seat="5" x="92" y="425"> </location>
|
||||
<location seat="6" x="0" y="373"> </location>
|
||||
<location seat="7" x="0" y="223"> </location>
|
||||
<location seat="8" x="25" y="50"> </location>
|
||||
</layout>
|
||||
<layout fav_seat="0" height="547" max="6" width="794">
|
||||
<location seat="1" x="640" y="58"> </location>
|
||||
<location seat="2" x="654" y="288"> </location>
|
||||
<location seat="3" x="615" y="424"> </location>
|
||||
<location seat="4" x="70" y="421"> </location>
|
||||
<location seat="5" x="0" y="280"> </location>
|
||||
<location seat="6" x="70" y="58"> </location>
|
||||
</layout>
|
||||
<layout fav_seat="0" height="547" max="2" width="794">
|
||||
<location seat="1" x="651" y="288"> </location>
|
||||
<location seat="2" x="10" y="288"> </location>
|
||||
</layout>
|
||||
<layout fav_seat="0" height="547" max="9" width="794">
|
||||
<location seat="1" x="634" y="38"> </location>
|
||||
<location seat="2" x="667" y="184"> </location>
|
||||
<location seat="3" x="667" y="321"> </location>
|
||||
<location seat="4" x="667" y="445"> </location>
|
||||
<location seat="5" x="337" y="459"> </location>
|
||||
<location seat="6" x="0" y="400"> </location>
|
||||
<location seat="7" x="0" y="322"> </location>
|
||||
<location seat="8" x="0" y="181"> </location>
|
||||
<location seat="9" x="70" y="53"> </location>
|
||||
</layout>
|
||||
</site>
|
||||
<site HH_path="C:\Users\WindowsUserName\Documents\EverleafSiteName\HandHistory\PlayerName"
|
||||
bgcolor="#000000"
|
||||
converter="EverleafToFpdb"
|
||||
decoder="everleaf_decode_table"
|
||||
enabled="False"
|
||||
fgcolor="#EEEEEE"
|
||||
hudopacity="0.75"
|
||||
screen_name="PlayerName"
|
||||
site_name="Everleaf"
|
||||
site_path="C:\Users\WindowsUserName\AppData\Roaming\EverleafSiteName\"
|
||||
supported_games="holdem,omahahi,omahahilo"
|
||||
table_finder="Poker.exe">
|
||||
<layout fav_seat="0" height="546" max="6" width="792">
|
||||
<location seat="0" x="0" y="0"> </location>
|
||||
<location seat="1" x="586" y="109"> </location>
|
||||
<location seat="2" x="605" y="283"> </location>
|
||||
<location seat="3" x="544" y="383"> </location>
|
||||
<location seat="4" x="67" y="383"> </location>
|
||||
<location seat="5" x="5" y="284"> </location>
|
||||
<location seat="6" x="61" y="111"> </location>
|
||||
</layout>
|
||||
<layout fav_seat="0" height="546" max="10" width="792">
|
||||
<location seat="0" x="182" y="69"> </location>
|
||||
<location seat="1" x="456" y="74"> </location>
|
||||
<location seat="2" x="630" y="81"> </location>
|
||||
<location seat="3" x="637" y="208"> </location>
|
||||
<location seat="4" x="629" y="347"> </location>
|
||||
<location seat="5" x="412" y="377"> </location>
|
||||
<location seat="6" x="232" y="377"> </location>
|
||||
<location seat="7" x="21" y="349"> </location>
|
||||
<location seat="8" x="4" y="208"> </location>
|
||||
<location seat="9" x="7" y="88"> </location>
|
||||
<location seat="10" x="196" y="69"> </location>
|
||||
</layout>
|
||||
<layout fav_seat="0" height="546" max="2" width="792">
|
||||
<location seat="1" x="651" y="288"> </location>
|
||||
<location seat="2" x="10" y="288"> </location>
|
||||
</layout>
|
||||
|
||||
</site>
|
||||
|
||||
<site enabled="False"
|
||||
site_name="Win2day"
|
||||
|
@ -558,7 +585,9 @@ Left-Drag to Move"
|
|||
<pu pu_name="default">
|
||||
<pu_stat pu_stat_name="playername"> </pu_stat>
|
||||
<pu_stat pu_stat_name="totalprofit"> </pu_stat>
|
||||
<pu_stat pu_stat_name="profit100"> </pu_stat>
|
||||
<pu_stat pu_stat_name="profit100"> </pu_stat>
|
||||
<pu_stat pu_stat_name="bbper100"> </pu_stat>
|
||||
<pu_stat pu_stat_name="BBper100"> </pu_stat>
|
||||
<pu_stat pu_stat_name="n"> </pu_stat>
|
||||
<pu_stat pu_stat_name="vpip"> </pu_stat>
|
||||
<pu_stat pu_stat_name="pfr"> </pu_stat>
|
||||
|
@ -643,6 +672,37 @@ Left-Drag to Move"
|
|||
<hhc site="Carbon" converter="CarbonToFpdb"/>
|
||||
</hhcs>
|
||||
|
||||
<!-- attribute names chosen to be in alphabetic order so that order can be set when retrieved -->
|
||||
<gui_cash_stats>
|
||||
<col col_name="game" col_title="Game" disp_all="True" disp_posn="True" field_format="%s" field_type="str" xalignment="0.0"/>
|
||||
<col col_name="hand" col_title="Hand" disp_all="False" disp_posn="False" field_format="%s" field_type="str" xalignment="0.0"/>
|
||||
<col col_name="plposition" col_title="Posn" disp_all="False" disp_posn="False" field_format="%s" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="pname" col_title="Name" disp_all="False" disp_posn="False" field_format="%s" field_type="str" xalignment="0.0"/>
|
||||
<col col_name="n" col_title="Hds" disp_all="True" disp_posn="True" field_format="%1.0f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="avgseats" col_title="Seats" disp_all="False" disp_posn="False" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="vpip" col_title="VPIP" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="pfr" col_title="PFR" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="pf3" col_title="PF3" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="aggfac" col_title="AggFac" disp_all="True" disp_posn="True" field_format="%2.2f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="aggfrq" col_title="AggFreq" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="conbet" col_title="ContBet" disp_all="False" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="rfi" col_title="RFI" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="steals" col_title="Steals" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="saw_f" col_title="Saw_F" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="sawsd" col_title="SawSD" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="wtsdwsf" col_title="WtSDwsF" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="wmsd" col_title="W$SD" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="flafq" col_title="FlAFq" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="tuafq" col_title="TuAFq" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="rvafq" col_title="RvAFq" disp_all="True" disp_posn="True" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="pofafq" col_title="PoFAFq" disp_all="False" disp_posn="False" field_format="%3.1f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="net" col_title="Net($)" disp_all="True" disp_posn="True" field_format="%6.2f" field_type="cash" xalignment="1.0"/>
|
||||
<col col_name="bbper100" col_title="bb/100" disp_all="True" disp_posn="True" field_format="%4.2f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="rake" col_title="Rake($)" disp_all="True" disp_posn="True" field_format="%6.2f" field_type="cash" xalignment="1.0"/>
|
||||
<col col_name="bb100xr" col_title="bbxr/100" disp_all="True" disp_posn="True" field_format="%4.2f" field_type="str" xalignment="1.0"/>
|
||||
<col col_name="variance" col_title="Variance" disp_all="True" disp_posn="True" field_format="%5.2f" field_type="str" xalignment="1.0"/>
|
||||
</gui_cash_stats>
|
||||
|
||||
<supported_databases>
|
||||
<!-- <database db_name="fpdb" db_server="mysql" db_ip="localhost" db_user="fpdb" db_pass="YOUR MYSQL PASSWORD"></database> -->
|
||||
<database db_ip="localhost" db_server="sqlite" db_name="fpdb.db3" db_user="fpdb" db_pass="fpdb"/>
|
||||
|
|
|
@ -79,13 +79,13 @@ class Hand(object):
|
|||
self.fee = None # the Database code is looking for this one .. ?
|
||||
self.level = None
|
||||
self.mixed = None
|
||||
self.speed = None
|
||||
self.isRebuy = None
|
||||
self.isAddOn = None
|
||||
self.isKO = None
|
||||
self.speed = "Normal"
|
||||
self.isRebuy = False
|
||||
self.isAddOn = False
|
||||
self.isKO = False
|
||||
self.koBounty = None
|
||||
self.isMatrix = None
|
||||
self.isShootout = None
|
||||
self.isMatrix = False
|
||||
self.isShootout = False
|
||||
self.added = None
|
||||
self.addedCurrency = None
|
||||
self.tourneyComment = None
|
||||
|
@ -683,9 +683,15 @@ class HoldemOmahaHand(Hand):
|
|||
hhc.readPlayerStacks(self)
|
||||
hhc.compilePlayerRegexs(self)
|
||||
hhc.markStreets(self)
|
||||
|
||||
if self.cancelled:
|
||||
return
|
||||
hhc.readBlinds(self)
|
||||
|
||||
try: hhc.readBlinds(self)
|
||||
except:
|
||||
print "*** Parse error reading blinds (check compilePlayerRegexs as a likely culprit)", self
|
||||
return
|
||||
|
||||
hhc.readAntes(self)
|
||||
hhc.readButton(self)
|
||||
hhc.readHeroCards(self)
|
||||
|
|
|
@ -41,9 +41,9 @@ import Hand
|
|||
from Exceptions import FpdbParseError
|
||||
import Configuration
|
||||
|
||||
import gettext
|
||||
gettext.install('fpdb')
|
||||
|
||||
#import gettext
|
||||
#trans=gettext.translation("fpdb", "/home/steffen/poker/fpdb-dev/pyfpdb/locale", languages=["de"])
|
||||
#trans.install()
|
||||
|
||||
import pygtk
|
||||
import gtk
|
||||
|
@ -441,6 +441,7 @@ or None if we fail to get the info """
|
|||
pass
|
||||
else:
|
||||
print "unable to read file with any codec in list!", self.in_path
|
||||
self.obs = ""
|
||||
elif self.filetype == "xml":
|
||||
doc = xml.dom.minidom.parse(filename)
|
||||
self.doc = doc
|
||||
|
|
|
@ -33,16 +33,16 @@ def run(config, db):
|
|||
#print "start of IS.run"
|
||||
server=None
|
||||
#try:
|
||||
#print "useSSL",config.email.useSsl,"host",config.email.host
|
||||
if config.email.useSsl:
|
||||
server = IMAP4_SSL(config.email.host)
|
||||
#print "useSSL",config.useSsl,"host",config.host
|
||||
if config.useSsl:
|
||||
server = IMAP4_SSL(config.host)
|
||||
else:
|
||||
server = IMAP4(config.email.host)
|
||||
response = server.login(config.email.username, config.email.password) #TODO catch authentication error
|
||||
server = IMAP4(config.host)
|
||||
response = server.login(config.username, config.password) #TODO catch authentication error
|
||||
print "response to logging in:",response
|
||||
#print "server.list():",server.list() #prints list of folders
|
||||
|
||||
response = server.select(config.email.folder)
|
||||
response = server.select(config.folder)
|
||||
#print "response to selecting INBOX:",response
|
||||
if response[0]!="OK":
|
||||
raise error #TODO: show error message
|
||||
|
|
|
@ -39,8 +39,8 @@ class FpdbParseError(FpdbParseError):
|
|||
class PartyPoker(HandHistoryConverter):
|
||||
sitename = "PartyPoker"
|
||||
codepage = "cp1252"
|
||||
siteId = 9
|
||||
filetype = "text"
|
||||
siteId = 9
|
||||
filetype = "text"
|
||||
sym = {'USD': "\$", }
|
||||
|
||||
# Static regexes
|
||||
|
@ -96,7 +96,7 @@ class PartyPoker(HandHistoryConverter):
|
|||
re_NoSmallBlind = re.compile(
|
||||
'^There is no Small Blind in this hand as the Big Blind '
|
||||
'of the previous hand left the table', re.MULTILINE)
|
||||
|
||||
re_20BBmin = re.compile(r"Table 20BB Min")
|
||||
|
||||
def allHandsAsList(self):
|
||||
list = HandHistoryConverter.allHandsAsList(self)
|
||||
|
@ -185,6 +185,7 @@ class PartyPoker(HandHistoryConverter):
|
|||
|
||||
info = {}
|
||||
m = self._getGameType(handText)
|
||||
m_20BBmin = self.re_20BBmin.search(handText)
|
||||
if m is None:
|
||||
return None
|
||||
|
||||
|
@ -216,7 +217,18 @@ class PartyPoker(HandHistoryConverter):
|
|||
info['type'] = 'ring'
|
||||
|
||||
if info['type'] == 'ring':
|
||||
info['sb'], info['bb'] = ringBlinds(mg['RINGLIMIT'])
|
||||
if m_20BBmin is None:
|
||||
bb = float(mg['RINGLIMIT'])/100.0
|
||||
else:
|
||||
bb = float(mg['RINGLIMIT'])/40.0
|
||||
|
||||
if bb == 0.25:
|
||||
sb = 0.10
|
||||
else:
|
||||
sb = bb/2.0
|
||||
|
||||
info['bb'] = "%.2f" % (bb)
|
||||
info['sb'] = "%.2f" % (sb)
|
||||
info['currency'] = currencies[mg['CURRENCY']]
|
||||
else:
|
||||
info['sb'] = clearMoneyString(mg['SB'])
|
||||
|
@ -291,9 +303,9 @@ class PartyPoker(HandHistoryConverter):
|
|||
if key == 'TABLE':
|
||||
hand.tablename = info[key]
|
||||
if key == 'MTTTABLE':
|
||||
if info[key] != None:
|
||||
hand.tablename = info[key]
|
||||
hand.tourNo = info['TABLE']
|
||||
if info[key] != None:
|
||||
hand.tablename = info[key]
|
||||
hand.tourNo = info['TABLE']
|
||||
if key == 'BUTTON':
|
||||
hand.buttonpos = info[key]
|
||||
if key == 'TOURNO':
|
||||
|
@ -483,13 +495,6 @@ class PartyPoker(HandHistoryConverter):
|
|||
print 'party', 'getTableTitleRe', table_number
|
||||
return table_name
|
||||
|
||||
|
||||
def ringBlinds(ringLimit):
|
||||
"Returns blinds for current limit in cash games"
|
||||
ringLimit = float(clearMoneyString(ringLimit))
|
||||
if ringLimit == 5.: ringLimit = 4.
|
||||
return ('%.2f' % (ringLimit/200.), '%.2f' % (ringLimit/100.) )
|
||||
|
||||
def clearMoneyString(money):
|
||||
"Renders 'numbers' like '1 200' and '2,000'"
|
||||
return money.replace(' ', '').replace(',', '')
|
||||
|
|
|
@ -47,9 +47,13 @@ class PokerStars(HandHistoryConverter):
|
|||
'0.40': ('0.10', '0.20'), '0.50': ('0.10', '0.25'), '1.00': ('0.25', '0.50'),
|
||||
'2.00': ('0.50', '1.00'), '2': ('0.50', '1.00'), '4' : ('1.00', '2.00'),
|
||||
'4.00': ('1.00', '2.00'), '6': ('1.00', '3.00'), '6.00': ('1.00', '3.00'),
|
||||
'10.00': ('2.00', '5.00'), '20.00': ('5.00', '10.00'), '30.00': ('10.00', '15.00'),
|
||||
'60.00': ('15.00', '30.00'), '100.00': ('25.00', '50.00'), '200.00': ('50.00', '100.00'),
|
||||
'400.00': ('100.00', '200.00'), '1000.00': ('250.00', '500.00')}
|
||||
'10.00': ('2.00', '5.00'), '10': ('2.00', '5.00'), '20.00': ('5.00', '10.00'),
|
||||
'20': ('5.00', '10.00'), '30.00': ('10.00', '15.00'), '30': ('10.00', '15.00'),
|
||||
'60.00': ('15.00', '30.00'), '60': ('15.00', '30.00'), '100.00': ('25.00', '50.00'),
|
||||
'100': ('25.00', '50.00'),'200.00': ('50.00', '100.00'), '200': ('50.00', '100.00'),
|
||||
'400.00': ('100.00', '200.00'), '400': ('100.00', '200.00'),'1000.00': ('250.00', '500.00'),
|
||||
'1000': ('250.00', '500.00')
|
||||
}
|
||||
|
||||
limits = { 'No Limit':'nl', 'Pot Limit':'pl', 'Limit':'fl', 'LIMIT':'fl' }
|
||||
games = { # base, category
|
||||
|
@ -74,7 +78,7 @@ class PokerStars(HandHistoryConverter):
|
|||
# here's how I plan to use LS
|
||||
(?P<BUYIN>(?P<BIAMT>[%(LS)s\d\.]+)?\+?(?P<BIRAKE>[%(LS)s\d\.]+)?\+?(?P<BOUNTY>[%(LS)s\d\.]+)?\s?(?P<TOUR_ISO>%(LEGAL_ISO)s)?|Freeroll)\s+)?
|
||||
# close paren of tournament info
|
||||
(?P<MIXED>HORSE|8\-Game|HOSE)?\s?\(?
|
||||
(?P<MIXED>HORSE|8\-Game|HOSE|Mixed PLH/PLO)?\s?\(?
|
||||
(?P<GAME>Hold\'em|Razz|RAZZ|7\sCard\sStud|7\sCard\sStud\sHi/Lo|Omaha|Omaha\sHi/Lo|Badugi|Triple\sDraw\s2\-7\sLowball|5\sCard\sDraw)\s
|
||||
(?P<LIMIT>No\sLimit|Limit|LIMIT|Pot\sLimit)\)?,?\s
|
||||
(-\s)?
|
||||
|
|
154
pyfpdb/SQL.py
154
pyfpdb/SQL.py
|
@ -137,21 +137,21 @@ class Sql:
|
|||
if db_server == 'mysql':
|
||||
self.query['createBackingsTable'] = """CREATE TABLE Backings (
|
||||
id SMALLINT UNSIGNED AUTO_INCREMENT NOT NULL, PRIMARY KEY (id),
|
||||
tourneysPlayerId BIGINT UNSIGNED NOT NULL, FOREIGN KEY (tourneysPlayerId) REFERENCES TourneysPlayers(id),
|
||||
tourneysPlayersId BIGINT UNSIGNED NOT NULL, FOREIGN KEY (tourneysPlayersId) REFERENCES TourneysPlayers(id),
|
||||
playerId INT UNSIGNED NOT NULL, FOREIGN KEY (playerId) REFERENCES Players(id),
|
||||
buyInPercentage FLOAT UNSIGNED NOT NULL,
|
||||
payOffPercentage FLOAT UNSIGNED NOT NULL) ENGINE=INNODB"""
|
||||
elif db_server == 'postgresql':
|
||||
self.query['createBackingsTable'] = """CREATE TABLE Backings (
|
||||
id BIGSERIAL, PRIMARY KEY (id),
|
||||
tourneysPlayerId INT NOT NULL, FOREIGN KEY (tourneysPlayerId) REFERENCES TourneysPlayers(id),
|
||||
tourneysPlayersId INT NOT NULL, FOREIGN KEY (tourneysPlayersId) REFERENCES TourneysPlayers(id),
|
||||
playerId INT NOT NULL, FOREIGN KEY (playerId) REFERENCES Players(id),
|
||||
buyInPercentage FLOAT NOT NULL,
|
||||
payOffPercentage FLOAT NOT NULL)"""
|
||||
elif db_server == 'sqlite':
|
||||
self.query['createBackingsTable'] = """CREATE TABLE Backings (
|
||||
id INTEGER PRIMARY KEY,
|
||||
tourneysPlayerId INT NOT NULL,
|
||||
tourneysPlayersId INT NOT NULL,
|
||||
playerId INT NOT NULL,
|
||||
buyInPercentage REAL UNSIGNED NOT NULL,
|
||||
payOffPercentage REAL UNSIGNED NOT NULL)"""
|
||||
|
@ -543,6 +543,7 @@ class Sql:
|
|||
position CHAR(1),
|
||||
seatNo SMALLINT NOT NULL,
|
||||
sitout BOOLEAN NOT NULL,
|
||||
wentAllInOnStreet SMALLINT,
|
||||
|
||||
card1 smallint NOT NULL, /* 0=none, 1-13=2-Ah 14-26=2-Ad 27-39=2-Ac 40-52=2-As */
|
||||
card2 smallint NOT NULL,
|
||||
|
@ -659,6 +660,7 @@ class Sql:
|
|||
position CHAR(1),
|
||||
seatNo SMALLINT NOT NULL,
|
||||
sitout BOOLEAN NOT NULL,
|
||||
wentAllInOnStreet SMALLINT,
|
||||
|
||||
card1 smallint NOT NULL, /* 0=none, 1-13=2-Ah 14-26=2-Ad 27-39=2-Ac 40-52=2-As */
|
||||
card2 smallint NOT NULL,
|
||||
|
@ -774,6 +776,7 @@ class Sql:
|
|||
position TEXT,
|
||||
seatNo INT NOT NULL,
|
||||
sitout BOOLEAN NOT NULL,
|
||||
wentAllInOnStreet INT,
|
||||
|
||||
card1 INT NOT NULL, /* 0=none, 1-13=2-Ah 14-26=2-Ad 27-39=2-Ac 40-52=2-As */
|
||||
card2 INT NOT NULL,
|
||||
|
@ -915,7 +918,7 @@ class Sql:
|
|||
commentTs timestamp without time zone)"""
|
||||
elif db_server == 'sqlite':
|
||||
self.query['createTourneysPlayersTable'] = """CREATE TABLE TourneysPlayers (
|
||||
id INT PRIMARY KEY,
|
||||
id INTEGER PRIMARY KEY,
|
||||
tourneyId INT,
|
||||
playerId INT,
|
||||
rank INT,
|
||||
|
@ -960,7 +963,7 @@ class Sql:
|
|||
commentTs timestamp without time zone)"""
|
||||
elif db_server == 'sqlite':
|
||||
self.query['createHandsActionsTable'] = """CREATE TABLE HandsActions (
|
||||
id INT PRIMARY KEY,
|
||||
id INTEGER PRIMARY KEY,
|
||||
handsPlayerId BIGINT,
|
||||
street SMALLINT,
|
||||
actionNo SMALLINT,
|
||||
|
@ -1333,8 +1336,6 @@ class Sql:
|
|||
and (p.siteId = %s or %s = -1)
|
||||
"""
|
||||
|
||||
self.query['getSiteId'] = """SELECT id from Sites where name = %s"""
|
||||
|
||||
self.query['get_stats_from_hand'] = """
|
||||
SELECT hc.playerId AS player_id,
|
||||
hp.seatNo AS seat,
|
||||
|
@ -1397,6 +1398,7 @@ class Sql:
|
|||
sum(hc.foldToStreet4CBChance) AS f_cb_opp_4,
|
||||
sum(hc.foldToStreet4CBDone) AS f_cb_4,
|
||||
sum(hc.totalProfit) AS net,
|
||||
sum(gt.bigblind) AS bigblind,
|
||||
sum(hc.street1CheckCallRaiseChance) AS ccr_opp_1,
|
||||
sum(hc.street1CheckCallRaiseDone) AS ccr_1,
|
||||
sum(hc.street2CheckCallRaiseChance) AS ccr_opp_2,
|
||||
|
@ -1425,6 +1427,7 @@ class Sql:
|
|||
INNER JOIN HudCache hc ON ( hc.PlayerId = hp.PlayerId+0
|
||||
AND hc.gametypeId+0 = h.gametypeId+0)
|
||||
INNER JOIN Players p ON (p.id = hp.PlayerId+0)
|
||||
INNER JOIN Gametypes gt ON (gt.id = hc.gametypeId)
|
||||
WHERE h.id = %s
|
||||
AND hc.styleKey > %s
|
||||
/* styleKey is currently 'd' (for date) followed by a yyyymmdd
|
||||
|
@ -1496,6 +1499,7 @@ class Sql:
|
|||
sum(hc.foldToStreet4CBChance) AS f_cb_opp_4,
|
||||
sum(hc.foldToStreet4CBDone) AS f_cb_4,
|
||||
sum(hc.totalProfit) AS net,
|
||||
sum(gt.bigblind) AS bigblind,
|
||||
sum(hc.street1CheckCallRaiseChance) AS ccr_opp_1,
|
||||
sum(hc.street1CheckCallRaiseDone) AS ccr_1,
|
||||
sum(hc.street2CheckCallRaiseChance) AS ccr_opp_2,
|
||||
|
@ -1523,6 +1527,7 @@ class Sql:
|
|||
INNER JOIN HandsPlayers hp ON (hp.handId = h.id)
|
||||
INNER JOIN HudCache hc ON (hc.playerId = hp.playerId)
|
||||
INNER JOIN Players p ON (p.id = hc.playerId)
|
||||
INNER JOIN Gametypes gt ON (gt.id = hc.gametypeId)
|
||||
WHERE h.id = %s
|
||||
AND ( /* 2 separate parts for hero and opponents */
|
||||
( hp.playerId != %s
|
||||
|
@ -1622,6 +1627,7 @@ class Sql:
|
|||
cast(hp2.foldToStreet4CBChance as <signed>integer) AS f_cb_opp_4,
|
||||
cast(hp2.foldToStreet4CBDone as <signed>integer) AS f_cb_4,
|
||||
cast(hp2.totalProfit as <signed>integer) AS net,
|
||||
cast(gt.bigblind as <signed>integer) AS bigblind,
|
||||
cast(hp2.street1CheckCallRaiseChance as <signed>integer) AS ccr_opp_1,
|
||||
cast(hp2.street1CheckCallRaiseDone as <signed>integer) AS ccr_1,
|
||||
cast(hp2.street2CheckCallRaiseChance as <signed>integer) AS ccr_opp_2,
|
||||
|
@ -1651,6 +1657,7 @@ class Sql:
|
|||
INNER JOIN HandsPlayers hp ON (h.id = hp.handId) /* players in this hand */
|
||||
INNER JOIN HandsPlayers hp2 ON (hp2.playerId+0 = hp.playerId+0 AND (hp2.handId = h2.id+0)) /* other hands by these players */
|
||||
INNER JOIN Players p ON (p.id = hp2.PlayerId+0)
|
||||
INNER JOIN Gametypes gt ON (gt.id = h2.gametypeId)
|
||||
WHERE hp.handId = %s
|
||||
/* check activeseats once this data returned (don't want to do that here as it might
|
||||
assume a session ended just because the number of seats dipped for a few hands)
|
||||
|
@ -1724,6 +1731,7 @@ class Sql:
|
|||
cast(hp2.foldToStreet4CBChance as <signed>integer) AS f_cb_opp_4,
|
||||
cast(hp2.foldToStreet4CBDone as <signed>integer) AS f_cb_4,
|
||||
cast(hp2.totalProfit as <signed>integer) AS net,
|
||||
cast(gt.bigblind as <signed>integer) AS bigblind,
|
||||
cast(hp2.street1CheckCallRaiseChance as <signed>integer) AS ccr_opp_1,
|
||||
cast(hp2.street1CheckCallRaiseDone as <signed>integer) AS ccr_1,
|
||||
cast(hp2.street2CheckCallRaiseChance as <signed>integer) AS ccr_opp_2,
|
||||
|
@ -1754,6 +1762,7 @@ class Sql:
|
|||
INNER JOIN HandsPlayers hp2 ON ( hp2.playerId+0 = hp.playerId+0
|
||||
AND hp2.handId = h2.id) /* other hands by these players */
|
||||
INNER JOIN Players p ON (p.id = hp2.PlayerId+0)
|
||||
INNER JOIN Gametypes gt ON (gt.id = h2.gametypeId)
|
||||
WHERE h.id = %s
|
||||
/* check activeseats once this data returned (don't want to do that here as it might
|
||||
assume a session ended just because the number of seats dipped for a few hands)
|
||||
|
@ -1827,6 +1836,7 @@ class Sql:
|
|||
cast(hp2.foldToStreet4CBChance as <signed>integer) AS f_cb_opp_4,
|
||||
cast(hp2.foldToStreet4CBDone as <signed>integer) AS f_cb_4,
|
||||
cast(hp2.totalProfit as <signed>integer) AS net,
|
||||
cast(gt.bigblind as <signed>integer) AS bigblind,
|
||||
cast(hp2.street1CheckCallRaiseChance as <signed>integer) AS ccr_opp_1,
|
||||
cast(hp2.street1CheckCallRaiseDone as <signed>integer) AS ccr_1,
|
||||
cast(hp2.street2CheckCallRaiseChance as <signed>integer) AS ccr_opp_2,
|
||||
|
@ -1857,6 +1867,7 @@ class Sql:
|
|||
INNER JOIN HandsPlayers hp2 ON ( hp2.playerId+0 = hp.playerId+0
|
||||
AND hp2.handId = h2.id) /* other hands by these players */
|
||||
INNER JOIN Players p ON (p.id = hp2.PlayerId+0)
|
||||
INNER JOIN Gametypes gt ON (gt.id = h2.gametypeId)
|
||||
WHERE h.id = %s
|
||||
/* check activeseats once this data returned (don't want to do that here as it might
|
||||
assume a session ended just because the number of seats dipped for a few hands)
|
||||
|
@ -1997,8 +2008,6 @@ class Sql:
|
|||
self.query['getPlayerIdBySite'] = """SELECT id from Players where name = %s AND siteId = %s"""
|
||||
|
||||
# used in *Filters:
|
||||
self.query['getSiteId'] = """SELECT id from Sites where name = %s"""
|
||||
self.query['getGames'] = """SELECT DISTINCT category from Gametypes"""
|
||||
#self.query['getLimits'] = already defined further up
|
||||
self.query['getLimits2'] = """SELECT DISTINCT type, limitType, bigBlind
|
||||
from Gametypes
|
||||
|
@ -2016,6 +2025,7 @@ class Sql:
|
|||
, limitType
|
||||
, bigBlind as bb_or_buyin
|
||||
from Gametypes gt
|
||||
WHERE type = 'ring'
|
||||
order by type, limitType DESC, bb_or_buyin DESC"""
|
||||
|
||||
if db_server == 'mysql':
|
||||
|
@ -2389,7 +2399,7 @@ class Sql:
|
|||
select s.name AS siteName
|
||||
,t.tourneyTypeId AS tourneyTypeId
|
||||
,tt.currency AS currency
|
||||
,(CASE WHEN tt.currency = "USD" THEN tt.buyIn/100.0 ELSE tt.buyIn END) AS buyIn
|
||||
,(CASE WHEN tt.currency = 'USD' THEN tt.buyIn/100.0 ELSE tt.buyIn END) AS buyIn
|
||||
,tt.fee/100.0 AS fee
|
||||
,tt.category AS category
|
||||
,tt.limitType AS limitType
|
||||
|
@ -2397,11 +2407,11 @@ class Sql:
|
|||
,COUNT(1) AS tourneyCount
|
||||
,SUM(CASE WHEN tp.rank > 0 THEN 0 ELSE 1 END) AS unknownRank
|
||||
,SUM(CASE WHEN winnings > 0 THEN 1 ELSE 0 END)/(COUNT(1) - SUM(CASE WHEN tp.rank > 0 THEN 0 ELSE 1 END)) AS itm
|
||||
,SUM(CASE WHEN rank = 1 THEN 1 ELSE 0 END) AS 1st
|
||||
,SUM(CASE WHEN rank = 2 THEN 1 ELSE 0 END) AS 2nd
|
||||
,SUM(CASE WHEN rank = 3 THEN 1 ELSE 0 END) AS 3rd
|
||||
,SUM(CASE WHEN rank = 1 THEN 1 ELSE 0 END) AS _1st
|
||||
,SUM(CASE WHEN rank = 2 THEN 1 ELSE 0 END) AS _2nd
|
||||
,SUM(CASE WHEN rank = 3 THEN 1 ELSE 0 END) AS _3rd
|
||||
,SUM(tp.winnings)/100.0 AS won
|
||||
,SUM(CASE WHEN tt.currency = "USD" THEN (tt.buyIn+tt.fee)/100.0 ELSE tt.buyIn END) AS spent
|
||||
,SUM(CASE WHEN tt.currency = 'USD' THEN (tt.buyIn+tt.fee)/100.0 ELSE tt.buyIn END) AS spent
|
||||
,SUM(tp.winnings)/SUM(tt.buyin+tt.fee)*100.0-100 AS roi
|
||||
,SUM(tp.winnings-(tt.buyin+tt.fee))/100.0/(COUNT(1)-SUM(CASE WHEN tp.rank > 0 THEN 0 ELSE 1 END)) AS profitPerTourney
|
||||
from TourneysPlayers tp
|
||||
|
@ -2416,9 +2426,72 @@ class Sql:
|
|||
,playerName
|
||||
,siteName"""
|
||||
elif db_server == 'postgresql':
|
||||
self.query['tourneyPlayerDetailedStats'] = """TODO"""
|
||||
# sc: itm and profitPerTourney changed to "ELSE 0" to avoid divide by zero error as temp fix
|
||||
# proper fix should use coalesce() or case ... when ... to work in all circumstances
|
||||
self.query['tourneyPlayerDetailedStats'] = """
|
||||
select s.name AS siteName
|
||||
,t.tourneyTypeId AS tourneyTypeId
|
||||
,tt.currency AS currency
|
||||
,(CASE WHEN tt.currency = 'USD' THEN tt.buyIn/100.0 ELSE tt.buyIn END) AS buyIn
|
||||
,tt.fee/100.0 AS fee
|
||||
,tt.category AS category
|
||||
,tt.limitType AS limitType
|
||||
,p.name AS playerName
|
||||
,COUNT(1) AS tourneyCount
|
||||
,SUM(CASE WHEN tp.rank > 0 THEN 0 ELSE 1 END) AS unknownRank
|
||||
,SUM(CASE WHEN winnings > 0 THEN 1 ELSE 0 END)
|
||||
/(COUNT(1) - SUM(CASE WHEN tp.rank > 0 THEN 0 ELSE 0 END)) AS itm
|
||||
,SUM(CASE WHEN rank = 1 THEN 1 ELSE 0 END) AS _1st
|
||||
,SUM(CASE WHEN rank = 2 THEN 1 ELSE 0 END) AS _2nd
|
||||
,SUM(CASE WHEN rank = 3 THEN 1 ELSE 0 END) AS _3rd
|
||||
,SUM(tp.winnings)/100.0 AS won
|
||||
,SUM(CASE WHEN tt.currency = 'USD' THEN (tt.buyIn+tt.fee)/100.0 ELSE tt.buyIn END) AS spent
|
||||
,SUM(tp.winnings)/SUM(tt.buyin+tt.fee)*100.0-100 AS roi
|
||||
,SUM(tp.winnings-(tt.buyin+tt.fee))/100.0
|
||||
/(COUNT(1)-SUM(CASE WHEN tp.rank > 0 THEN 0 ELSE 0 END)) AS profitPerTourney
|
||||
from TourneysPlayers tp
|
||||
inner join Tourneys t on (t.id = tp.tourneyId)
|
||||
inner join TourneyTypes tt on (tt.Id = t.tourneyTypeId)
|
||||
inner join Sites s on (s.Id = tt.siteId)
|
||||
inner join Players p on (p.Id = tp.playerId)
|
||||
where tp.playerId in <nametest> <sitetest>
|
||||
and to_char(t.startTime, 'YYYY-MM-DD HH24:MI:SS') <datestest>
|
||||
group by tourneyTypeId, s.name, playerName, tt.currency, tt.buyin, tt.fee
|
||||
, tt.category, tt.limitType
|
||||
order by tourneyTypeId
|
||||
,playerName
|
||||
,siteName"""
|
||||
elif db_server == 'sqlite':
|
||||
self.query['tourneyPlayerDetailedStats'] = """TODO"""
|
||||
self.query['tourneyPlayerDetailedStats'] = """
|
||||
select s.name AS siteName
|
||||
,t.tourneyTypeId AS tourneyTypeId
|
||||
,tt.currency AS currency
|
||||
,(CASE WHEN tt.currency = 'USD' THEN tt.buyIn/100.0 ELSE tt.buyIn END) AS buyIn
|
||||
,tt.fee/100.0 AS fee
|
||||
,tt.category AS category
|
||||
,tt.limitType AS limitType
|
||||
,p.name AS playerName
|
||||
,COUNT(1) AS tourneyCount
|
||||
,SUM(CASE WHEN tp.rank > 0 THEN 0 ELSE 1 END) AS unknownRank
|
||||
,SUM(CASE WHEN winnings > 0 THEN 1 ELSE 0 END)/(COUNT(1) - SUM(CASE WHEN tp.rank > 0 THEN 0 ELSE 1 END)) AS itm
|
||||
,SUM(CASE WHEN rank = 1 THEN 1 ELSE 0 END) AS _1st
|
||||
,SUM(CASE WHEN rank = 2 THEN 1 ELSE 0 END) AS _2nd
|
||||
,SUM(CASE WHEN rank = 3 THEN 1 ELSE 0 END) AS _3rd
|
||||
,SUM(tp.winnings)/100.0 AS won
|
||||
,SUM(CASE WHEN tt.currency = 'USD' THEN (tt.buyIn+tt.fee)/100.0 ELSE tt.buyIn END) AS spent
|
||||
,SUM(tp.winnings)/SUM(tt.buyin+tt.fee)*100.0-100 AS roi
|
||||
,SUM(tp.winnings-(tt.buyin+tt.fee))/100.0/(COUNT(1)-SUM(CASE WHEN tp.rank > 0 THEN 0 ELSE 1 END)) AS profitPerTourney
|
||||
from TourneysPlayers tp
|
||||
inner join Tourneys t on (t.id = tp.tourneyId)
|
||||
inner join TourneyTypes tt on (tt.Id = t.tourneyTypeId)
|
||||
inner join Sites s on (s.Id = tt.siteId)
|
||||
inner join Players p on (p.Id = tp.playerId)
|
||||
where tp.playerId in <nametest> <sitetest>
|
||||
and datetime(t.startTime) <datestest>
|
||||
group by tourneyTypeId, playerName
|
||||
order by tourneyTypeId
|
||||
,playerName
|
||||
,siteName"""
|
||||
|
||||
if db_server == 'mysql':
|
||||
self.query['playerStats'] = """
|
||||
|
@ -2767,6 +2840,8 @@ class Sql:
|
|||
order by stats.category, stats.limitType, stats.bigBlindDesc desc
|
||||
<orderbyseats>, cast(stats.PlPosition as signed)
|
||||
"""
|
||||
elif db_server == 'sqlite':
|
||||
self.query['playerStatsByPosition'] = ""#TODO
|
||||
else: # assume postgresql
|
||||
self.query['playerStatsByPosition'] = """
|
||||
select /* stats from hudcache */
|
||||
|
@ -2937,7 +3012,7 @@ class Sql:
|
|||
INNER JOIN Players p on (p.Id = hp.playerId)
|
||||
WHERE hp.playerId in <player_test>
|
||||
AND date_format(h.startTime, '%Y-%m-%d') <datestest>
|
||||
AND gt.type is 'ring'
|
||||
AND gt.type LIKE 'ring'
|
||||
ORDER by time"""
|
||||
elif db_server == 'postgresql':
|
||||
self.query['sessionStats'] = """
|
||||
|
@ -2949,7 +3024,7 @@ class Sql:
|
|||
INNER JOIN Players p on (p.Id = hp.playerId)
|
||||
WHERE hp.playerId in <player_test>
|
||||
AND h.startTime <datestest>
|
||||
AND gt.type is 'ring'
|
||||
AND gt.type LIKE 'ring'
|
||||
ORDER by time"""
|
||||
elif db_server == 'sqlite':
|
||||
self.query['sessionStats'] = """
|
||||
|
@ -2978,7 +3053,7 @@ class Sql:
|
|||
,playerId
|
||||
,activeSeats
|
||||
,position
|
||||
,tourneyTypeId
|
||||
<tourney_insert_clause>
|
||||
,styleKey
|
||||
,HDs
|
||||
,wonWhenSeenStreet1
|
||||
|
@ -3068,7 +3143,7 @@ class Sql:
|
|||
when hp.position = '9' then 'E'
|
||||
else 'E'
|
||||
end AS hc_position
|
||||
,t.tourneyTypeId
|
||||
<tourney_select_clause>
|
||||
,date_format(h.startTime, 'd%y%m%d')
|
||||
,count(1)
|
||||
,sum(wonWhenSeenStreet1)
|
||||
|
@ -3142,14 +3217,13 @@ class Sql:
|
|||
,sum(hp.street4Raises)
|
||||
FROM HandsPlayers hp
|
||||
INNER JOIN Hands h ON (h.id = hp.handId)
|
||||
INNER JOIN TourneysPlayers tp ON (tp.id = hp.tourneysPlayersId)
|
||||
INNER JOIN Tourneys t ON (t.id = tp.tourneyId)
|
||||
<tourney_join_clause>
|
||||
<where_clause>
|
||||
GROUP BY h.gametypeId
|
||||
,hp.playerId
|
||||
,h.seats
|
||||
,hc_position
|
||||
,t.tourneyTypeId
|
||||
<tourney_group_clause>
|
||||
,date_format(h.startTime, 'd%y%m%d')
|
||||
"""
|
||||
elif db_server == 'postgresql':
|
||||
|
@ -3159,7 +3233,7 @@ class Sql:
|
|||
,playerId
|
||||
,activeSeats
|
||||
,position
|
||||
,tourneyTypeId
|
||||
<tourney_insert_clause>
|
||||
,styleKey
|
||||
,HDs
|
||||
,wonWhenSeenStreet1
|
||||
|
@ -3249,7 +3323,7 @@ class Sql:
|
|||
when hp.position = '9' then 'E'
|
||||
else 'E'
|
||||
end AS hc_position
|
||||
,t.tourneyTypeId
|
||||
<tourney_select_clause>
|
||||
,'d' || to_char(h.startTime, 'YYMMDD')
|
||||
,count(1)
|
||||
,sum(wonWhenSeenStreet1)
|
||||
|
@ -3323,14 +3397,13 @@ class Sql:
|
|||
,sum(CAST(hp.street4Raises as integer))
|
||||
FROM HandsPlayers hp
|
||||
INNER JOIN Hands h ON (h.id = hp.handId)
|
||||
INNER JOIN TourneysPlayers tp ON (tp.id = hp.tourneysPlayersId)
|
||||
INNER JOIN Tourneys t ON (t.id = tp.tourneyId)
|
||||
<tourney_join_clause>
|
||||
<where_clause>
|
||||
GROUP BY h.gametypeId
|
||||
,hp.playerId
|
||||
,h.seats
|
||||
,hc_position
|
||||
,t.tourneyTypeId
|
||||
<tourney_group_clause>
|
||||
,to_char(h.startTime, 'YYMMDD')
|
||||
"""
|
||||
else: # assume sqlite
|
||||
|
@ -3340,7 +3413,7 @@ class Sql:
|
|||
,playerId
|
||||
,activeSeats
|
||||
,position
|
||||
,tourneyTypeId
|
||||
<tourney_insert_clause>
|
||||
,styleKey
|
||||
,HDs
|
||||
,wonWhenSeenStreet1
|
||||
|
@ -3430,7 +3503,7 @@ class Sql:
|
|||
when hp.position = '9' then 'E'
|
||||
else 'E'
|
||||
end AS hc_position
|
||||
,t.tourneyTypeId
|
||||
<tourney_select_clause>
|
||||
,'d' || substr(strftime('%Y%m%d', h.startTime),3,7)
|
||||
,count(1)
|
||||
,sum(wonWhenSeenStreet1)
|
||||
|
@ -3504,14 +3577,13 @@ class Sql:
|
|||
,sum(CAST(hp.street4Raises as integer))
|
||||
FROM HandsPlayers hp
|
||||
INNER JOIN Hands h ON (h.id = hp.handId)
|
||||
INNER JOIN TourneysPlayers tp ON (tp.id = hp.tourneysPlayersId)
|
||||
INNER JOIN Tourneys t ON (t.id = tp.tourneyId)
|
||||
<tourney_join_clause>
|
||||
<where_clause>
|
||||
GROUP BY h.gametypeId
|
||||
,hp.playerId
|
||||
,h.seats
|
||||
,hc_position
|
||||
,t.tourneyTypeId
|
||||
<tourney_group_clause>
|
||||
,'d' || substr(strftime('%Y%m%d', h.startTime),3,7)
|
||||
"""
|
||||
|
||||
|
@ -3798,6 +3870,22 @@ class Sql:
|
|||
WHERE tt.siteId=%s AND t.siteTourneyNo=%s
|
||||
"""
|
||||
|
||||
self.query['getTourneyInfo'] = """SELECT tt.*, t.*
|
||||
FROM Tourneys t
|
||||
INNER JOIN TourneyTypes tt ON (t.tourneyTypeId = tt.id)
|
||||
INNER JOIN Sites s ON (tt.siteId = s.id)
|
||||
WHERE s.name=%s AND t.siteTourneyNo=%s
|
||||
"""
|
||||
|
||||
self.query['getTourneyPlayerInfo'] = """SELECT tp.*
|
||||
FROM Tourneys t
|
||||
INNER JOIN TourneyTypes tt ON (t.tourneyTypeId = tt.id)
|
||||
INNER JOIN Sites s ON (tt.siteId = s.id)
|
||||
INNER JOIN TourneysPlayers tp ON (tp.tourneyId = t.id)
|
||||
INNER JOIN Players p ON (p.id = tp.playerId)
|
||||
WHERE s.name=%s AND t.siteTourneyNo=%s AND p.name=%s
|
||||
"""
|
||||
|
||||
self.query['insertTourney'] = """INSERT INTO Tourneys
|
||||
(tourneyTypeId, siteTourneyNo, entries, prizepool,
|
||||
startTime, endTime, tourneyName, matrixIdProcessed,
|
||||
|
|
115
pyfpdb/Stats.py
115
pyfpdb/Stats.py
|
@ -48,7 +48,7 @@
|
|||
# 6 For each stat you make add a line to the __main__ function to test it.
|
||||
|
||||
# Standard Library modules
|
||||
#import sys
|
||||
import sys
|
||||
|
||||
# pyGTK modules
|
||||
import pygtk
|
||||
|
@ -60,6 +60,10 @@ import Configuration
|
|||
import Database
|
||||
import Charset
|
||||
|
||||
import logging
|
||||
# logging has been set up in fpdb.py or HUD_main.py, use their settings:
|
||||
log = logging.getLogger("db")
|
||||
|
||||
|
||||
re_Places = re.compile("_[0-9]$")
|
||||
re_Percent = re.compile("%$")
|
||||
|
@ -79,12 +83,23 @@ def do_stat(stat_dict, player = 24, stat = 'vpip'):
|
|||
else:
|
||||
base = stat[0:-2]
|
||||
places = int(stat[-1:])
|
||||
result = eval("%(stat)s(stat_dict, %(player)d)" % {'stat': base, 'player': player})
|
||||
result = (0.0, '0.0', 'notset=0', 'notset=0', '0', 'not set')
|
||||
try:
|
||||
result = eval("%(stat)s(stat_dict, %(player)d)" % {'stat': base, 'player': player})
|
||||
except:
|
||||
pass #
|
||||
log.info("exception getting stat "+base+" for player "+str(player)+str(sys.exc_info()))
|
||||
log.debug("result = %s" % str(result) )
|
||||
|
||||
match = re_Percent.search(result[1])
|
||||
if match is None:
|
||||
result = (result[0], "%.*f" % (places, result[0]), result[2], result[3], result[4], result[5])
|
||||
else:
|
||||
result = (result[0], "%.*f%%" % (places, 100*result[0]), result[2], result[3], result[4], result[5])
|
||||
try:
|
||||
if match is None:
|
||||
result = (result[0], "%.*f" % (places, result[0]), result[2], result[3], result[4], result[5])
|
||||
else:
|
||||
result = (result[0], "%.*f%%" % (places, 100*result[0]), result[2], result[3], result[4], result[5])
|
||||
except:
|
||||
log.info( "error: %s" % str(sys.exc_info()))
|
||||
raise
|
||||
return result
|
||||
|
||||
# OK, for reference the tuple returned by the stat is:
|
||||
|
@ -198,7 +213,7 @@ def wmsd(stat_dict, player):
|
|||
)
|
||||
|
||||
def profit100(stat_dict, player):
|
||||
""" Profit won per 100 hands (no decimal places)."""
|
||||
""" Profit won per 100 hands."""
|
||||
stat = 0.0
|
||||
try:
|
||||
stat = float(stat_dict[player]['net'])/float(stat_dict[player]['n'])
|
||||
|
@ -212,13 +227,57 @@ def profit100(stat_dict, player):
|
|||
except:
|
||||
print "exception calcing p/100: 100 * %d / %d" % (stat_dict[player]['net'], stat_dict[player]['n'])
|
||||
return (stat,
|
||||
'%.0f' % (0),
|
||||
'p=%.0f' % (0),
|
||||
'p/100=%.0f' % (0),
|
||||
'%.0f' % (0.0),
|
||||
'p=%.0f' % (0.0),
|
||||
'p/100=%.0f' % (0.0),
|
||||
'(%d/%d)' % (0, 0),
|
||||
'profit/100hands'
|
||||
)
|
||||
|
||||
def bbper100(stat_dict, player):
|
||||
""" big blinds won per 100 hands."""
|
||||
stat = 0.0
|
||||
try:
|
||||
stat = 100.0 * float(stat_dict[player]['net']) / float(stat_dict[player]['bigblind'])
|
||||
return (stat,
|
||||
'%5.3f' % (stat),
|
||||
'bb100=%5.3f' % (stat),
|
||||
'bb100=%5.3f' % (stat),
|
||||
'(%d,%d)' % (100*stat_dict[player]['net'],stat_dict[player]['bigblind']),
|
||||
'big blinds/100 hands'
|
||||
)
|
||||
except:
|
||||
log.info("exception calcing bb/100: "+str(stat_dict[player]))
|
||||
return (stat,
|
||||
'%.0f' % (0),
|
||||
'bb100=%.0f' % (0),
|
||||
'bb100=%.0f' % (0),
|
||||
'(%f)' % (0),
|
||||
'big blinds/100 hands'
|
||||
)
|
||||
|
||||
def BBper100(stat_dict, player):
|
||||
""" Big Bets won per 100 hands."""
|
||||
stat = 0.0
|
||||
try:
|
||||
stat = 50 * float(stat_dict[player]['net']) / float(stat_dict[player]['bigblind'])
|
||||
return (stat,
|
||||
'%5.3f' % (stat),
|
||||
'BB100=%5.3f' % (stat),
|
||||
'BB100=%5.3f' % (stat),
|
||||
'(%d,%d)' % (100*stat_dict[player]['net'],2*stat_dict[player]['bigblind']),
|
||||
'Big Bets/100 hands'
|
||||
)
|
||||
except:
|
||||
log.info("exception calcing BB/100: "+str(stat_dict[player]))
|
||||
return (stat,
|
||||
'%.0f' % (0.0),
|
||||
'BB100=%.0f' % (0.0),
|
||||
'BB100=%.0f' % (0.0),
|
||||
'(%f)' % (0.0),
|
||||
'Big Bets/100 hands'
|
||||
)
|
||||
|
||||
def saw_f(stat_dict, player):
|
||||
""" Saw flop/4th."""
|
||||
try:
|
||||
|
@ -711,10 +770,10 @@ def ffreq1(stat_dict, player):
|
|||
)
|
||||
except:
|
||||
return (stat,
|
||||
'%3.1f' % (0) + '%',
|
||||
'ff1=%3.1f' % (0) + '%',
|
||||
'ff_1=%3.1f' % (0) + '%',
|
||||
'(%d/%d)' % (0, 0),
|
||||
'NA',
|
||||
'ff1=NA',
|
||||
'ff_1=NA',
|
||||
'(0/0)',
|
||||
'% fold frequency flop/4th'
|
||||
)
|
||||
|
||||
|
@ -782,13 +841,27 @@ def ffreq4(stat_dict, player):
|
|||
)
|
||||
|
||||
if __name__== "__main__":
|
||||
statlist = dir()
|
||||
misslist = [ "Configuration", "Database", "Charset", "codecs", "encoder"
|
||||
, "do_stat", "do_tip", "GInitiallyUnowned", "gtk", "pygtk"
|
||||
, "re", "re_Percent", "re_Places"
|
||||
]
|
||||
statlist = [ x for x in statlist if x not in dir(sys) ]
|
||||
statlist = [ x for x in statlist if x not in dir(codecs) ]
|
||||
statlist = [ x for x in statlist if x not in misslist ]
|
||||
#print "statlist is", statlist
|
||||
|
||||
c = Configuration.Config()
|
||||
#TODO: restore the below code. somehow it creates a version 119 DB but commenting this out makes it print a stat list
|
||||
#db_connection = Database.Database(c)
|
||||
#h = db_connection.get_last_hand()
|
||||
#stat_dict = db_connection.get_stats_from_hand(h, "ring")
|
||||
db_connection = Database.Database(c)
|
||||
h = db_connection.get_last_hand()
|
||||
stat_dict = db_connection.get_stats_from_hand(h, "ring")
|
||||
|
||||
#for player in stat_dict.keys():
|
||||
for player in stat_dict.keys():
|
||||
print "Example stats, player =", player, "hand =", h, ":"
|
||||
for attr in statlist:
|
||||
print " ", do_stat(stat_dict, player=player, stat=attr)
|
||||
break
|
||||
#print "player = ", player, do_stat(stat_dict, player = player, stat = 'vpip')
|
||||
#print "player = ", player, do_stat(stat_dict, player = player, stat = 'pfr')
|
||||
#print "player = ", player, do_stat(stat_dict, player = player, stat = 'wtsd')
|
||||
|
@ -820,11 +893,7 @@ if __name__== "__main__":
|
|||
|
||||
print "\n\nLegal stats:"
|
||||
print "(add _0 to name to display with 0 decimal places, _1 to display with 1, etc)\n"
|
||||
for attr in dir():
|
||||
if attr.startswith('__'): continue
|
||||
if attr in ("Configuration", "Database", "GInitiallyUnowned", "gtk", "pygtk",
|
||||
"player", "c", "db_connection", "do_stat", "do_tip", "stat_dict",
|
||||
"h", "re", "re_Percent", "re_Places"): continue
|
||||
for attr in statlist:
|
||||
print "%-14s %s" % (attr, eval("%s.__doc__" % (attr)))
|
||||
# print " <pu_stat pu_stat_name = \"%s\"> </pu_stat>" % (attr)
|
||||
print
|
||||
|
|
|
@ -20,6 +20,10 @@ import sys
|
|||
import re
|
||||
import Queue
|
||||
|
||||
#import gettext
|
||||
#trans=gettext.translation("fpdb", "locale", ["en_GB"])
|
||||
#trans.install()
|
||||
|
||||
# if path is set to use an old version of python look for a new one:
|
||||
# (does this work in linux?)
|
||||
if os.name == 'nt' and sys.version[0:3] not in ('2.5', '2.6') and '-r' not in sys.argv:
|
||||
|
@ -103,9 +107,10 @@ import GuiPrefs
|
|||
import GuiLogView
|
||||
import GuiDatabase
|
||||
import GuiBulkImport
|
||||
import ImapFetcher
|
||||
import GuiImapFetcher
|
||||
import GuiRingPlayerStats
|
||||
import GuiTourneyPlayerStats
|
||||
import GuiTourneyViewer
|
||||
import GuiPositionalStats
|
||||
import GuiAutoImport
|
||||
import GuiGraphViewer
|
||||
|
@ -785,7 +790,7 @@ class fpdb:
|
|||
<menu action="import">
|
||||
<menuitem action="sethharchive"/>
|
||||
<menuitem action="bulkimp"/>
|
||||
<menuitem action="imapsummaries"/>
|
||||
<menuitem action="imapimport"/>
|
||||
<menuitem action="autoimp"/>
|
||||
</menu>
|
||||
<menu action="viewers">
|
||||
|
@ -794,6 +799,7 @@ class fpdb:
|
|||
<menuitem action="graphs"/>
|
||||
<menuitem action="ringplayerstats"/>
|
||||
<menuitem action="tourneyplayerstats"/>
|
||||
<menuitem action="tourneyviewer"/>
|
||||
<menuitem action="posnstats"/>
|
||||
<menuitem action="sessionstats"/>
|
||||
</menu>
|
||||
|
@ -826,14 +832,15 @@ class fpdb:
|
|||
('import', None, '_Import'),
|
||||
('sethharchive', None, '_Set HandHistory Archive Directory', None, 'Set HandHistory Archive Directory', self.select_hhArchiveBase),
|
||||
('bulkimp', None, '_Bulk Import', '<control>B', 'Bulk Import', self.tab_bulk_import),
|
||||
('imapsummaries', None, '_Import Tourney Summaries through eMail/IMAP', '<control>I', 'Auto Import and HUD', self.import_imap_summaries),
|
||||
('imapimport', None, '_Import through eMail/IMAP', '<control>I', 'Import through eMail/IMAP', self.tab_imap_import),
|
||||
('viewers', None, '_Viewers'),
|
||||
('autoimp', None, '_Auto Import and HUD', '<control>A', 'Auto Import and HUD', self.tab_auto_import),
|
||||
('hudConfigurator', None, '_HUD Configurator', '<control>H', 'HUD Configurator', self.diaHudConfigurator),
|
||||
('graphs', None, '_Graphs', '<control>G', 'Graphs', self.tabGraphViewer),
|
||||
('ringplayerstats', None, 'Ring _Player Stats (tabulated view)', '<control>P', 'Ring Player Stats (tabulated view)', self.tab_ring_player_stats),
|
||||
('tourneyplayerstats', None, '_Tourney Player Stats (tabulated view, mysql only)', '<control>T', 'Tourney Player Stats (tabulated view, mysql only)', self.tab_tourney_player_stats),
|
||||
('posnstats', None, 'P_ositional Stats (tabulated view)', '<control>O', 'Positional Stats (tabulated view)', self.tab_positional_stats),
|
||||
('tourneyplayerstats', None, '_Tourney Player Stats (tabulated view)', '<control>T', 'Tourney Player Stats (tabulated view, mysql only)', self.tab_tourney_player_stats),
|
||||
('tourneyviewer', None, 'Tourney _Viewer', None, 'Tourney Viewer)', self.tab_tourney_viewer_stats),
|
||||
('posnstats', None, 'P_ositional Stats (tabulated view, not on sqlite)', '<control>O', 'Positional Stats (tabulated view)', self.tab_positional_stats),
|
||||
('sessionstats', None, 'Session Stats', None, 'Session Stats', self.tab_session_stats),
|
||||
('database', None, '_Database'),
|
||||
('maintaindbs', None, '_Maintain Databases', None, 'Maintain Databases', self.dia_maintain_dbs),
|
||||
|
@ -857,10 +864,6 @@ class fpdb:
|
|||
return menubar
|
||||
#end def get_menu
|
||||
|
||||
def import_imap_summaries(self, widget, data=None):
|
||||
result=ImapFetcher.run(self.config, self.db)
|
||||
#print "import imap summaries result:", result
|
||||
#end def import_imap_summaries
|
||||
|
||||
def load_profile(self, create_db = False):
|
||||
"""Loads profile from the provided path name."""
|
||||
|
@ -891,7 +894,7 @@ class fpdb:
|
|||
self.settings.update(self.config.get_import_parameters())
|
||||
self.settings.update(self.config.get_default_paths())
|
||||
|
||||
if self.db is not None and self.db.connected:
|
||||
if self.db is not None and self.db.is_connected():
|
||||
self.db.disconnect()
|
||||
|
||||
self.sql = SQL.Sql(db_server = self.settings['db-server'])
|
||||
|
@ -914,6 +917,8 @@ class fpdb:
|
|||
if err_msg is not None:
|
||||
self.db = None
|
||||
self.warning_box(err_msg)
|
||||
if self.db is not None and not self.db.is_connected():
|
||||
self.db = None
|
||||
|
||||
# except FpdbMySQLFailedError:
|
||||
# self.warning_box("Unable to connect to MySQL! Is the MySQL server running?!", "FPDB ERROR")
|
||||
|
@ -954,7 +959,7 @@ class fpdb:
|
|||
self.main_vbox.pack_end(self.status_bar, False, True, 0)
|
||||
self.status_bar.show()
|
||||
|
||||
if self.db is not None and self.db.connected:
|
||||
if self.db is not None and self.db.is_connected():
|
||||
self.status_bar.set_text("Status: Connected to %s database named %s on host %s"
|
||||
% (self.db.get_backend_name(),self.db.database, self.db.host))
|
||||
# rollback to make sure any locks are cleared:
|
||||
|
@ -988,12 +993,12 @@ class fpdb:
|
|||
if self.db!=None:
|
||||
if self.db.backend==self.db.MYSQL_INNODB:
|
||||
try:
|
||||
if self.db is not None and self.db.connected():
|
||||
if self.db is not None and self.db.is_connected():
|
||||
self.db.disconnect()
|
||||
except _mysql_exceptions.OperationalError: # oh, damn, we're already disconnected
|
||||
pass
|
||||
else:
|
||||
if self.db is not None and self.db.connected():
|
||||
if self.db is not None and self.db.is_connected():
|
||||
self.db.disconnect()
|
||||
else:
|
||||
pass
|
||||
|
@ -1021,6 +1026,13 @@ class fpdb:
|
|||
bulk_tab=new_import_thread.get_vbox()
|
||||
self.add_and_display_tab(bulk_tab, "Bulk Import")
|
||||
|
||||
def tab_imap_import(self, widget, data=None):
|
||||
new_thread = GuiImapFetcher.GuiImapFetcher(self.config, self.db, self.sql, self.window)
|
||||
self.threads.append(new_thread)
|
||||
tab=new_thread.get_vbox()
|
||||
self.add_and_display_tab(tab, "IMAP Import")
|
||||
#end def tab_import_imap_summaries
|
||||
|
||||
def tab_ring_player_stats(self, widget, data=None):
|
||||
new_ps_thread = GuiRingPlayerStats.GuiRingPlayerStats(self.config, self.sql, self.window)
|
||||
self.threads.append(new_ps_thread)
|
||||
|
@ -1033,6 +1045,12 @@ class fpdb:
|
|||
ps_tab=new_ps_thread.get_vbox()
|
||||
self.add_and_display_tab(ps_tab, "Tourney Player Stats")
|
||||
|
||||
def tab_tourney_viewer_stats(self, widget, data=None):
|
||||
new_thread = GuiTourneyViewer.GuiTourneyViewer(self.config, self.db, self.sql, self.window)
|
||||
self.threads.append(new_thread)
|
||||
tab=new_thread.get_vbox()
|
||||
self.add_and_display_tab(tab, "Tourney Viewer")
|
||||
|
||||
def tab_positional_stats(self, widget, data=None):
|
||||
new_ps_thread = GuiPositionalStats.GuiPositionalStats(self.config, self.sql)
|
||||
self.threads.append(new_ps_thread)
|
||||
|
@ -1047,14 +1065,17 @@ class fpdb:
|
|||
|
||||
def tab_main_help(self, widget, data=None):
|
||||
"""Displays a tab with the main fpdb help screen"""
|
||||
mh_tab=gtk.Label("""Welcome to Fpdb!
|
||||
mh_tab=gtk.Label("""Fpdb needs translators!
|
||||
If you speak another language and have a few minutes or more to spare get in touch by emailing steffen@schaumburger.info
|
||||
|
||||
Welcome to Fpdb!
|
||||
To be notified of new snapshots and releases go to https://lists.sourceforge.net/lists/listinfo/fpdb-announce and subscribe.
|
||||
If you want to follow development more closely go to https://lists.sourceforge.net/lists/listinfo/fpdb-main and subscribe.
|
||||
|
||||
This program is currently in an alpha-state, so our database format is still sometimes changed.
|
||||
You should therefore always keep your hand history files so that you can re-import after an update, if necessary.
|
||||
|
||||
For documentation please visit our website at http://fpdb.sourceforge.net/.
|
||||
For documentation please visit our website/wiki at http://fpdb.sourceforge.net/.
|
||||
If you need help click on Contact - Get Help on our website.
|
||||
Please note that default.conf is no longer needed nor used, all configuration now happens in HUD_config.xml.
|
||||
|
||||
|
|
|
@ -0,0 +1,41 @@
|
|||
***** Hand History For Game 9423586142 *****
|
||||
0.01/0.02 Texas Hold'em Game Table (NL) - Mon Jul 12 13:38:32 EDT 2010
|
||||
Table 20BB Min Speed #1775757 (Real Money) -- Seat 1 is the button
|
||||
Total number of players : 9/9
|
||||
Seat 1: Player1 ($0.95)
|
||||
Seat 2: Player2 ($0.57)
|
||||
Seat 3: Player3 ($0.86)
|
||||
Seat 4: Player4 ($1.71)
|
||||
Seat 5: Player5 ($1.76)
|
||||
Seat 6: Player6 ($0.44)
|
||||
Seat 7: Player7 ($0.76)
|
||||
Seat 8: Player8 ($0.68)
|
||||
Seat 9: Player9 ($0.38)
|
||||
Player2 posts small blind (0.01)
|
||||
Player3 posts big blind (0.02)
|
||||
** Dealing down cards **
|
||||
Dealt to Player5 [ Tc, 9d ]
|
||||
Player5 folds
|
||||
Player6 calls (0.02)
|
||||
Player8 folds
|
||||
Player9 folds
|
||||
Player1 folds
|
||||
Player2 calls (0.01)
|
||||
Player3 raises 0.06 to 0.08
|
||||
Player6 calls (0.06)
|
||||
Player2 folds
|
||||
** Dealing Flop ** : [ 5s, 7h, 6h ]
|
||||
Player3 bets (0.13)
|
||||
Player6 folds
|
||||
** Summary **
|
||||
Main Pot: $0.18 Rake: $0
|
||||
Board: [ 5s 7h 6h ]
|
||||
Player1 balance $0.95, didn't bet (folded)
|
||||
Player2 balance $0.55, lost $0.02 (folded)
|
||||
Player3 balance $0.96, bet $0.21, collected $0.31, net +$0.1
|
||||
Player4 balance $1.71, sits out
|
||||
Player5 balance $1.76, didn't bet (folded)
|
||||
Player6 balance $0.36, lost $0.08 (folded)
|
||||
Player7 balance $0.76, sits out
|
||||
Player8 balance $0.68, didn't bet (folded)
|
||||
Player9 balance $0.38, didn't bet (folded)
|
|
@ -0,0 +1,63 @@
|
|||
Game #9485557849 starts.
|
||||
|
||||
#Game No : 9485557849
|
||||
***** Hand History for Game 9485557849 *****
|
||||
$0.80 USD NL Texas Hold'em - Saturday, July 31, 13:52:16 EDT 2010
|
||||
Table 20BB Min Speed #1770998 (Real Money)
|
||||
Seat 1 is the button
|
||||
Total number of players : 4/9
|
||||
Seat 3: FErki84 ( $1.64 USD )
|
||||
Seat 5: Vandercasses ( $0.01 USD )
|
||||
Seat 9: jeremyho888 ( $1.02 USD )
|
||||
Seat 1: sergeodem ( $1.20 USD )
|
||||
FErki84 posts small blind [$0.01 USD].
|
||||
Vandercasses posts big blind [$0.01 USD].
|
||||
** Dealing down cards **
|
||||
Dealt to FErki84 [ 8h Kc ]
|
||||
jeremyho888 folds
|
||||
sergeodem calls [$0.02 USD]
|
||||
FErki84 calls [$0.01 USD]
|
||||
** Dealing Flop ** [ Td, 7c, 9h ]
|
||||
FErki84 checks
|
||||
sergeodem checks
|
||||
** Dealing Turn ** [ 3h ]
|
||||
FErki84 checks
|
||||
sergeodem checks
|
||||
** Dealing River ** [ Jc ]
|
||||
FErki84 bets [$0.04 USD]
|
||||
sergeodem folds
|
||||
FErki84 shows [ 8h, Kc ]a straight, Seven to Jack.
|
||||
Vandercasses doesn't show [ Ts, Jd ]two pairs, Jacks and Tens.
|
||||
FErki84 wins $0.06 USD from the side pot 1 with a straight, Seven to Jack.
|
||||
FErki84 wins $0.03 USD from the main pot with a straight, Seven to Jack.
|
||||
Vandercasses has left the table.
|
||||
|
||||
Game #9498788316 starts.
|
||||
|
||||
#Game No : 9498788316
|
||||
***** Hand History for Game 9498788316 *****
|
||||
$1.60 USD NL Texas Hold'em - Wednesday, August 04, 15:02:33 EDT 2010
|
||||
Table 20BB Min #1847547 (No DP) (Real Money)
|
||||
Seat 2 is the button
|
||||
Total number of players : 5/6
|
||||
Seat 5: CepguTbIu999 ( $1.60 USD )
|
||||
Seat 1: Daytona_955 ( $2.45 USD )
|
||||
Seat 4: FErki84 ( $2.18 USD )
|
||||
Seat 2: anjl2009 ( $2.80 USD )
|
||||
Seat 3: lukeman2 ( $0.01 USD )
|
||||
lukeman2 posts small blind [$0.01 USD].
|
||||
FErki84 posts big blind [$0.04 USD].
|
||||
** Dealing down cards **
|
||||
Dealt to FErki84 [ 6s 2c ]
|
||||
CepguTbIu999 folds
|
||||
Daytona_955 folds
|
||||
anjl2009 folds
|
||||
** Dealing Flop ** [ 9d, Ah, 3h ]
|
||||
** Dealing Turn ** [ Js ]
|
||||
** Dealing River ** [ Kc ]
|
||||
lukeman2 shows [ 5h, 5s ]a pair of Fives.
|
||||
FErki84 shows [ 6s, 2c ]high card Ace.
|
||||
FErki84 wins $0.03 USD from the side pot 1 with high card, Ace.
|
||||
lukeman2 wins $0.02 USD from the main pot with a pair of Fives.
|
||||
lukeman2 has left the table.
|
||||
|
|
@ -1,5 +1,5 @@
|
|||
fpdb database dump
|
||||
DB version=136
|
||||
DB version=142
|
||||
|
||||
###################
|
||||
Table Autorates
|
||||
|
@ -44,7 +44,7 @@ empty table
|
|||
###################
|
||||
Table Settings
|
||||
###################
|
||||
version=136
|
||||
version=142
|
||||
|
||||
|
||||
###################
|
||||
|
|
|
@ -0,0 +1,37 @@
|
|||
***** Hand History For Game 9336845949 *****
|
||||
30/60 Tourney Texas Hold'em Game Table (NL) (STT Tournament #52792286) - Sun Jun 13 12:21:39 EDT 2010
|
||||
Table 174827 (Real Money) -- Seat 6 is the button
|
||||
Total number of players : 6/6
|
||||
Seat 1: Player1 (1520)
|
||||
Seat 2: Player2 (1540)
|
||||
Seat 3: Player3 (2120)
|
||||
Seat 4: Player4 (2460)
|
||||
Seat 5: Player5 (2600)
|
||||
Seat 6: Player6 (1760)
|
||||
Player1 posts small blind (30)
|
||||
Player2 posts big blind (60)
|
||||
** Dealing down cards **
|
||||
Dealt to Player5 [ Jc, Js ]
|
||||
Player3 folds
|
||||
Player4 folds
|
||||
Player6 folds
|
||||
Player1 calls (210)
|
||||
Player2 folds
|
||||
** Dealing Flop ** : [ 4h, 7d, 5c ]
|
||||
Player1 checks
|
||||
Player1 calls (450)
|
||||
** Dealing Turn ** : [ Kd ]
|
||||
Player1 checks
|
||||
Player1 calls (830)
|
||||
Player1 is all-In.
|
||||
** Dealing River ** : [ Jd ]
|
||||
Creating Main Pot with 3100 with Player1
|
||||
** Summary **
|
||||
Main Pot: 3100
|
||||
Board: [ 4h 7d 5c Kd Jd ]
|
||||
Player1 balance 0, lost 1520 [ Ks 6c ] [ a pair of kings -- Ks,Kd,Jd,7d,6c ]
|
||||
Player2 balance 1480, lost 60 (folded)
|
||||
Player3 balance 2120, didn't bet (folded)
|
||||
Player4 balance 2460, didn't bet (folded)
|
||||
Player5 balance 4180, bet 1520, collected 3100, net +1580 [ Jc Js ] [ three of a kind, jacks -- Kd,Jc,Js,Jd,7d ]
|
||||
Player6 balance 1760, didn't bet (folded)
|
Loading…
Reference in New Issue
Block a user