Merge branch 'master' of git://git.assembla.com/fpdb-eric into eric

This commit is contained in:
Steffen Schaumburg 2011-04-06 23:27:57 +02:00
commit e9cdc96ae4
174 changed files with 42588 additions and 14286 deletions

112
packaging/announce-0.22.txt Normal file
View File

@ -0,0 +1,112 @@
Hello everyone,
The new fpdb release 0.22 is now available for download as source or as packages/installers for Debian, Gentoo, Ubuntu and Windows.
This version brings many improvements and bugfixes. A quick word on our version naming: We have decided to stop using the usual alpha/beta/rc release system as it doesn't suit fpdb's development style and resources. From now on all releases are created equal (ie. considered "testing"). If they proof themselves we declare them "stable" and make them the default download on sourceforge. If you wish to be notified of new releases or stabilisation please subscribe to the fpdb-announe mailing list (see Links further down). Since this version has been available for some time we consider it stable and recommend all users to update.
So... what is FPDB?
===================
FPDB (Free Poker Database) is a free/open source suite of steadily growing tools to track and analyse your online poker game. FPDB is able to import the hand histories that poker sites write to your computer and to store additional data from each hand in a database for use in later analysis.
FPDB is ambitious, intending to support all games. Currently we support flop based games (Holdem, Omaha, Omaha Hi/Lo), stud games (7 Card Stud, 7 Card Stud Hi/Lo, and Razz) and draw games (Triple Draw Lowball, 5 Card Draw) on most major poker sites.
FPDB provides a Heads Up Display (HUD), Profit Grapher and Stats viewers with a list of features that is growing.
What's changed
==============
417 changesets (incl. merges) have gone in since 0.21-rc2. Some of the improvements are:
New stats:
Three bet: name="three_B" (note this stat was previously "three_B_0")
Four bet: name="four_B"
Cold four bet: name="cfour_B"
Squeeze bet preflop: name="squeeze"
Fold to three bet preflop: name="f_3bet"
Fold to four bet preflop: name="f_4bet"
Steal Success : name="s_steal"
Pokerstars Home Games now supported
Everest now supported
Winamax now supported
Translation progress:
Complete: English, Hungarian. If you notice an untranslated string in any output please let us know.
Partial: French (85%), German (32%), Polish (27%), Spanish (17%), Russian (6%).
Significant work on the underlying HUD code, including hud dragging and table closing
Problems where some stats became > 100% are now fixed
sqlite database performance improvements (sqlite is the default database for fpdb)
pokerstars.it tournament HUD now working
Cap games added to filter options
Initial work to support Rush poker - this will need further testing and improvement before we can release it. One or two testers would be welcome, please PM gimick if you want to help.
Various updates and fixes when importing Hand histories.
Party freeroll tournaments now recognised.
Stars 20/40 limit and FTP 1k/2k limit now recognised.
Initial work on a Stove function for holdem (see the viewers menu)
The windows exe has been upgraded from python 2.6 to python 2.7.
Where to get it
===============
Please note that you will have to either recreate your database or use a new one if you're updating from 0.21-rc2 or older. Fpdb will warn you if your database is incompatible and will not work unless you recreate or use a different one.
Config files from 0.20 and later should work. Please report if you have problems with config files from that version or later.
You can find checksums (MD5 and SHA512) in the download folder.
To download: http://sourceforge.net/projects/fpdb/files/fpdb/0.22/
Links
=====
To be notified by email of new versions you can subscribe to our announce mailing list here: https://lists.sourceforge.net/lists/listinfo/fpdb-announce
Link to fpdb website (wiki) http://fpdb.wiki.sourceforge.net/
Features page: http://sourceforge.net/apps/mediawiki/fpdb/index.php?title=Features
How to install&setup fpdb in 5 Minutes with the Windows installer: http://sf.net/projects/fpdb/files/fpdb/help/ Choose exe021install.avi (18mb, no sound)
Installation instructions are available from: http://sourceforge.net/apps/mediawiki/fpdb/index.php?title=Installation
Getting Started Instructions: http://sourceforge.net/apps/mediawiki/fpdb/index.php?title=Getting_Started
FAQ: http://sourceforge.net/apps/mediawiki/fpdb/index.php?title=FAQ
Screenshots: http://sourceforge.net/apps/mediawiki/fpdb/index.php?title=Screenshots
How to help
===========
Join us in IRC (see below) and say you want to do something :)
How to get help
===============
Please also see the "Bug reports" section below to enable us to help you.
These are listed in order of usefulness - the 2+2 thread in particular is rather chaotic so if we miss your post feel free to bring it up again
1) Chat/IRC
One of the developers is usually around, but it is IRC. Dont get discouraged because we didn't answer within 10 minutes, once we do you've probably got our full attention.
This link takes you to a website where you can talk to us directly: http://webchat.freenode.net/?channels=fpdb
Alternatively use can use any IRC client to connect to #fpdb on freenode.net
2) Mailing List
Visit http://lists.sourceforge.net/lists/listinfo/fpdb-main to subscribe to the development&support mailing list and send us an email
3) The monster 2+2 forum thread (registration required).
http://forumserver.twoplustwo.com/16...2009-a-273001/ Please dont let the size of the thread phase you. It is monitored and sends email notifications to some of the developers. (Note: If you play poker and don't frequent the 2+2 forums, you may want to become better acquainted. Its a bit daunting at first, but well worth the effort)
Bug reports
===========
When you do report issues, try to make it easier for us help you. We usually need at least the following information:
- Operating system and version (e.g. Ubuntu 10.10 or Windows XP)
- Database type (MySQL, SQLite, PostgreSQL)
- Install method (exe, tarball, deb, git, ebuild)
- Fpdb version
- Site name and gametype (e.g. $10 Pokerstars Razz SnG)
You can find most of these details for easy copy&paste in the Help menu under About.
Important known problems
========================
Hud will not work if using postgres database - fixed in 0.23
PKR is not working correctly
Special information for Windows installations
=============================================
First-time installs will need to download and install the C++ runtime executable from Microsoft.
Windows 7 and windows Vista users will need to set fpdb.exe and hud_main.exe to run as administrator (see http://sourceforge.net/apps/mediawiki/fpdb/index.php?title=Install_in_Windows)
Contributors
============
Code/translations: Worros, Donoban, Nutomatic, Steffen, Chaz Littlejohn, Scott Wolchok, tribumarchal, Erki Ferenc, Eric Blade, atinm, Mika Bostrom, Robert Wielinga, Chris Moore, Gerko de Roo, Gimick
Special shoutout to Eleatic Stranger who has written an initial converter for Carbon poker, without ever having played on the site!
Documentation: RSOAndrew, Buggernaut, ChazDazzle
Testers and everyone answering forum questions - xaviax, Dog, uncooper etc. You know who you are.
Hand History donations: Quite a few people on this list now. Every donation for alternate sites and various corner cases is appreciated.
And a particular thanks to all the libraries, interpreters etc. that we use to create fpdb!

View File

@ -1,3 +1,15 @@
free-poker-tools (0.22-1) unstable; urgency=low
* New release: 0.22
-- Mika Bostrom <bostik@iki.fi> Sun, 13 Mar 2011 05:15:24 +0200
free-poker-tools (0.21-1) unstable; urgency=low
* New release: 0.21
-- Mika Bostrom <bostik@iki.fi> Mon, 28 Feb 2011 04:09:57 +0200
free-poker-tools (0.21~rc2) unstable; urgency=low
* Second 0.21 release-candidate

View File

@ -10,14 +10,14 @@ inherit eutils games
DESCRIPTION="A free/open source tracker/HUD for use with online poker"
HOMEPAGE="http://fpdb.wiki.sourceforge.net/"
SRC_URI="mirror://sourceforge/${PN}/Snapshots/${P}.tar.bz2"
SRC_URI="mirror://sourceforge/${PN}/${PV}/${P}.tar.bz2"
LICENSE="AGPL-3"
SLOT="0"
KEYWORDS="~amd64 ~x86"
#note: this should work on other architectures too, please send me your experiences
#note: fpdb has only been tested on x86 and amd64, but should work on other arches, too
IUSE="graph mysql postgres sqlite linguas_de linguas_hu linguas_fr"
IUSE="graph mysql postgres sqlite linguas_de linguas_es linguas_fr linguas_hu linguas_it linguas_pl linguas_ru"
RDEPEND="
mysql? ( virtual/mysql
dev-python/mysql-python )
@ -39,8 +39,32 @@ src_install() {
doins -r gfx || die "failed to install gfx directory"
doins -r pyfpdb || die "failed to install pyfpdb directory"
if use linguas_de; then
msgfmt pyfpdb/locale/fpdb-de_DE.po -o pyfpdb/locale/de.mo || die "failed to create German mo file"
fi
if use linguas_es; then
msgfmt pyfpdb/locale/fpdb-es_ES.po -o pyfpdb/locale/es.mo || die "failed to create Spanish mo file"
fi
if use linguas_fr; then
msgfmt pyfpdb/locale/fpdb-fr_FR.po -o pyfpdb/locale/fr.mo || die "failed to create French mo file"
fi
if use linguas_hu; then
msgfmt pyfpdb/locale/fpdb-hu_HU.po -o pyfpdb/locale/hu.mo || die "failed to create hungarian mo file"
msgfmt pyfpdb/locale/fpdb-hu_HU.po -o pyfpdb/locale/hu.mo || die "failed to create Hungarian mo file"
fi
if use linguas_it; then
msgfmt pyfpdb/locale/fpdb-it_IT.po -o pyfpdb/locale/it.mo || die "failed to create Italian mo file"
fi
if use linguas_pl; then
msgfmt pyfpdb/locale/fpdb-pl_PL.po -o pyfpdb/locale/pl.mo || die "failed to create Polish mo file"
fi
if use linguas_ru; then
msgfmt pyfpdb/locale/fpdb-ru_RU.po -o pyfpdb/locale/ru.mo || die "failed to create Russian mo file"
fi
domo pyfpdb/locale/*.mo || die "failed to install mo files"

View File

@ -1,60 +0,0 @@
# Copyright 1999-2011 Gentoo Foundation
# Distributed under the terms of the GNU General Public License v2
# $Header: $
#TODO: Header, add cdecimal
EAPI="2"
inherit eutils games
DESCRIPTION="A free/open source tracker/HUD for use with online poker"
HOMEPAGE="http://fpdb.wiki.sourceforge.net/"
SRC_URI="mirror://sourceforge/${PN}/${PV}/${P}.tar.bz2"
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_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}
fperms +x "${GAMES_DATADIR}"/${PN}/pyfpdb/*.pyw
prepgamesdirs
}
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."
}

View File

@ -15,8 +15,9 @@ EGIT_REPO_URI="git://git.assembla.com/fpdb.git"
LICENSE="AGPL-3"
SLOT="0"
KEYWORDS=""
#note: fpdb has only been tested on x86 and amd64, but should work on other arches, too
IUSE="graph mysql postgres sqlite linguas_de linguas_hu linguas_fr"
IUSE="graph mysql postgres sqlite linguas_de linguas_es linguas_fr linguas_hu linguas_it linguas_pl linguas_ru"
RDEPEND="
mysql? ( virtual/mysql
dev-python/mysql-python )
@ -29,7 +30,7 @@ RDEPEND="
graph? ( dev-python/numpy
dev-python/matplotlib[gtk] )
dev-python/python-xlib
dev-python/pytz"
x11-apps/xwininfo"
DEPEND="${RDEPEND}"
src_unpack() {
@ -38,29 +39,49 @@ src_unpack() {
src_install() {
insinto "${GAMES_DATADIR}"/${PN}
doins -r gfx
doins -r pyfpdb
doins -r gfx || die "failed to install gfx directory"
doins -r pyfpdb || die "failed to install pyfpdb directory"
if use linguas_de; then
msgfmt pyfpdb/locale/fpdb-de_DE.po -o pyfpdb/locale/de.mo
msgfmt pyfpdb/locale/fpdb-de_DE.po -o pyfpdb/locale/de.mo || die "failed to create German mo file"
fi
if use linguas_es; then
msgfmt pyfpdb/locale/fpdb-es_ES.po -o pyfpdb/locale/es.mo || die "failed to create Spanish mo file"
fi
if use linguas_fr; then
msgfmt pyfpdb/locale/fpdb-fr_FR.po -o pyfpdb/locale/fr.mo || die "failed to create French mo file"
fi
if use linguas_hu; then
msgfmt pyfpdb/locale/fpdb-hu_HU.po -o pyfpdb/locale/hu.mo
msgfmt pyfpdb/locale/fpdb-hu_HU.po -o pyfpdb/locale/hu.mo || die "failed to create Hungarian mo file"
fi
domo pyfpdb/locale/*.mo
if use linguas_it; then
msgfmt pyfpdb/locale/fpdb-it_IT.po -o pyfpdb/locale/it.mo || die "failed to create Italian mo file"
fi
doins readme.txt
if use linguas_pl; then
msgfmt pyfpdb/locale/fpdb-pl_PL.po -o pyfpdb/locale/pl.mo || die "failed to create Polish mo file"
fi
if use linguas_ru; then
msgfmt pyfpdb/locale/fpdb-ru_RU.po -o pyfpdb/locale/ru.mo || die "failed to create Russian mo file"
fi
domo pyfpdb/locale/*.mo || die "failed to install mo files"
doins readme.txt || die "failed to install readme.txt file"
exeinto "${GAMES_DATADIR}"/${PN}
doexe run_fpdb.py
doexe run_fpdb.py || die "failed to install executable run_fpdb.py"
dodir "${GAMES_BINDIR}"
dosym "${GAMES_DATADIR}"/${PN}/run_fpdb.py "${GAMES_BINDIR}"/${PN}
dosym "${GAMES_DATADIR}"/${PN}/run_fpdb.py "${GAMES_BINDIR}"/${PN} || die "failed to create symlink for starting fpdb"
newicon gfx/fpdb-icon.png ${PN}.png
make_desktop_entry ${PN}
newicon gfx/fpdb-icon.png ${PN}.png || die "failed to install fpdb icon"
make_desktop_entry ${PN} || die "failed to create desktop entry"
fperms +x "${GAMES_DATADIR}"/${PN}/pyfpdb/*.pyw
prepgamesdirs

View File

@ -138,7 +138,7 @@ class Absolute(HandHistoryConverter):
if not m:
tmp = handText[0:100]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
@ -349,7 +349,7 @@ class Absolute(HandHistoryConverter):
bet = action.group('BET').replace(',', '')
hand.addComplete( street, action.group('PNAME'), bet)
else:
logging.debug(_("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'),action.group('ATYPE')))
logging.debug(_("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'), action.group('ATYPE')))
def readShowdownActions(self, hand):

View File

@ -1,134 +0,0 @@
#!/usr/bin/env python
# -*- coding: utf-8 -*-
#Copyright 2009-2011 Grigorij Indigirkin
#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.
#TODO: gettextify if file is used again
from decimal_wrapper import Decimal
from sqlalchemy import types
from sqlalchemy.orm.exc import NoResultFound
from sqlalchemy.exc import IntegrityError
import Card
class CardColumn(types.TypeDecorator):
"""Stores cards as smallints
Automatically converts values like '9h' to smallint
>>> CardColumn().process_bind_param( 'Td', '' )
22
>>> CardColumn().process_bind_param( u'Td', '' )
22
>>> CardColumn().process_bind_param( 22, '' )
22
>>> CardColumn().process_result_value( 22, '' )
'Td'
"""
impl = types.SmallInteger
def process_bind_param(self, value, dialect):
if value is None or isinstance(value, int):
return value
elif isinstance(value, basestring) and len(value) == 2:
return Card.encodeCard(str(value))
else:
raise Exception, "Incorrect card value: " + repr(value)
def process_result_value(self, value, dialect):
return Card.valueSuitFromCard( value )
class MoneyColumn(types.TypeDecorator):
"""Stores money: bets, pots, etc
Understands:
Decimal as real amount
int as amount mupliplied by 100
string as decimal
Returns Decimal
>>> MoneyColumn().process_bind_param( 230, '' )
230
>>> MoneyColumn().process_bind_param( Decimal('2.30'), '' )
230
>>> MoneyColumn().process_bind_param( '2.30', '' )
230
>>> MoneyColumn().process_result_value( 230, '' )
Decimal('2.3')
"""
impl = types.Integer
def process_bind_param(self, value, dialect):
if value is None or isinstance(value, int):
return value
elif isinstance(value, basestring) or isinstance(value, Decimal):
return int(Decimal(value)*100)
else:
raise Exception, "Incorrect amount:" + repr(value)
def process_result_value(self, value, dialect):
if value is None:
return None
return Decimal(value)/100
class BigIntColumn(types.TypeDecorator, types.Integer):
"""Representing db-independent big integer """
# Integer inheritance required for auto_increment flag
impl = types.Integer
def load_dialect_impl(self, dialect):
from sqlalchemy import databases
if dialect.name == 'mysql':
return databases.mysql.MSBigInteger()
elif dialect.name == 'postgres':
return databases.mysql.PGBigInteger()
return types.Integer()
class MappedBase(object):
"""Provide dummy contrcutor"""
def __init__(self, **kwargs):
for k, v in kwargs.iteritems():
setattr(self, k, v)
def get_columns_names(self):
return [i.name for i in self._sa_class_manager.mapper.c]
def get_or_create(klass, session, **kwargs):
"""
Looks up an object with the given kwargs, creating one if necessary.
Returns a tuple of (object, created), where created is a boolean
specifying whether an object was created.
"""
assert kwargs, \
'get_or_create() must be passed at least one keyword argument'
try:
return session.query(klass).filter_by(**kwargs).one(), False
except NoResultFound:
try:
obj = klass(**kwargs)
session.add(obj)
session.flush()
return obj, True
except IntegrityError:
return session.query(klass).filter_by(**kwargs).one(), False

View File

@ -1,484 +0,0 @@
#!/usr/bin/env python
# -*- coding: utf-8 -*-
#Copyright 2009-2011 Grigorij Indigirkin
#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.
"""@package AlchemyMappings
This package contains all classes to be mapped and mappers themselves
"""
#TODO: gettextify if file is used again
import logging
import re
from decimal_wrapper import Decimal
from sqlalchemy.orm import mapper, relation, reconstructor
from sqlalchemy.sql import select
from collections import defaultdict
from AlchemyTables import *
from AlchemyFacilities import get_or_create, MappedBase
from DerivedStats import DerivedStats
from Exceptions import IncompleteHandError, FpdbError
class Player(MappedBase):
"""Class reflecting Players db table"""
@staticmethod
def get_or_create(session, siteId, name):
return get_or_create(Player, session, siteId=siteId, name=name)[0]
def __str__(self):
return '<Player "%s" on %s>' % (self.name, self.site and self.site.name)
class Gametype(MappedBase):
"""Class reflecting Gametypes db table"""
@staticmethod
def get_or_create(session, siteId, gametype):
map = zip(
['type', 'base', 'category', 'limitType', 'smallBlind', 'bigBlind', 'smallBet', 'bigBet', 'currency'],
['type', 'base', 'category', 'limitType', 'sb', 'bb', 'dummy', 'dummy', 'currency'])
gametype = dict([(new, gametype.get(old)) for new, old in map ])
hilo = "h"
if gametype['category'] in ('studhilo', 'omahahilo'):
hilo = "s"
elif gametype['category'] in ('razz','27_3draw','badugi'):
hilo = "l"
gametype['hiLo'] = hilo
for f in ['smallBlind', 'bigBlind', 'smallBet', 'bigBet']:
if gametype[f] is None:
gametype[f] = 0
gametype[f] = int(Decimal(gametype[f])*100)
gametype['siteId'] = siteId
return get_or_create(Gametype, session, **gametype)[0]
class HandActions(object):
"""Class reflecting HandsActions db table"""
def initFromImportedHand(self, hand, actions):
self.hand = hand
self.actions = {}
for street, street_actions in actions.iteritems():
self.actions[street] = []
for v in street_actions:
hp = hand.handplayers_by_name[v[0]]
self.actions[street].append({'street': street, 'pid': hp.id, 'seat': hp.seatNo, 'action':v})
@property
def flat_actions(self):
actions = []
for street in self.hand.allStreets:
actions += self.actions[street]
return actions
class HandInternal(DerivedStats):
"""Class reflecting Hands db table"""
def parseImportedHandStep1(self, hand):
"""Extracts values to insert into from hand returned by HHC. No db is needed he"""
hand.players = hand.getAlivePlayers()
# also save some data for step2. Those fields aren't in Hands table
self.siteId = hand.siteId
self.gametype_dict = hand.gametype
self.attachHandPlayers(hand)
self.attachActions(hand)
self.assembleHands(hand)
self.assembleHandsPlayers(hand)
def parseImportedHandStep2(self, session):
"""Fetching ids for gametypes and players"""
gametype = Gametype.get_or_create(session, self.siteId, self.gametype_dict)
self.gametypeId = gametype.id
for hp in self.handPlayers:
hp.playerId = Player.get_or_create(session, self.siteId, hp.name).id
def getPlayerByName(self, name):
if not hasattr(self, 'handplayers_by_name'):
self.handplayers_by_name = {}
for hp in self.handPlayers:
pname = getattr(hp, 'name', None) or hp.player.name
self.handplayers_by_name[pname] = hp
return self.handplayers_by_name[name]
def attachHandPlayers(self, hand):
"""Fill HandInternal.handPlayers list. Create self.handplayers_by_name"""
hand.noSb = getattr(hand, 'noSb', None)
if hand.noSb is None and self.gametype_dict['base']=='hold':
saw_sb = False
for action in hand.actions[hand.actionStreets[0]]: # blindsantes
if action[1] == 'posts' and action[2] == 'small blind' and action[0] is not None:
saw_sb = True
hand.noSb = saw_sb
self.handplayers_by_name = {}
for seat, name, chips in hand.players:
p = HandPlayer(hand = self, imported_hand=hand, seatNo=seat,
name=name, startCash=chips)
self.handplayers_by_name[name] = p
def attachActions(self, hand):
"""Create HandActions object"""
a = HandActions()
a.initFromImportedHand(self, hand.actions)
def parseImportedTournament(self, hand, session):
"""Fetching tourney, its type and players
Must be called after Step2
"""
if self.gametype_dict['type'] != 'tour': return
# check for consistense
for i in ('buyin', 'tourNo'):
if not hasattr(hand, i):
raise IncompleteHandError(
"Field '%s' required for tournaments" % i, self.id, hand )
# repair old-style buyin value
m = re.match('\$(\d+)\+\$(\d+)', hand.buyin)
if m is not None:
hand.buyin, self.fee = m.groups()
# fetch tourney type
tour_type_hand2db = {
'buyin': 'buyin',
'fee': 'fee',
'speed': 'speed',
'maxSeats': 'maxseats',
'knockout': 'isKO',
'rebuy': 'isRebuy',
'addOn': 'isAddOn',
'shootout': 'isShootout',
'matrix': 'isMatrix',
'sng': 'isSNG',
}
tour_type_index = dict([
( i_db, getattr(hand, i_hand, None) )
for i_db, i_hand in tour_type_hand2db.iteritems()
])
tour_type_index['siteId'] = self.siteId
tour_type = TourneyType.get_or_create(session, **tour_type_index)
# fetch and update tourney
tour = Tourney.get_or_create(session, hand.tourNo, tour_type.id)
cols = tour.get_columns_names()
for col in cols:
hand_val = getattr(hand, col, None)
if col in ('id', 'tourneyTypeId', 'comment', 'commentTs') or hand_val is None:
continue
db_val = getattr(tour, col, None)
if db_val is None:
setattr(tour, col, hand_val)
elif col == 'koBounty':
setattr(tour, col, max(db_val, hand_val))
elif col == 'tourStartTime' and hand.startTime:
setattr(tour, col, min(db_val, hand.startTime))
if tour.entries is None and tour_type.sng:
tour.entries = tour_type.maxSeats
# fetch and update tourney players
for hp in self.handPlayers:
tp = TourneysPlayer.get_or_create(session, tour.id, hp.playerId)
# FIXME: other TourneysPlayers should be added here
session.flush()
def isDuplicate(self, session):
"""Checks if current hand already exists in db
siteHandNo ans gametypeId have to be setted
"""
return session.query(HandInternal).filter_by(
siteHandNo=self.siteHandNo, gametypeId=self.gametypeId).count()!=0
def __str__(self):
s = list()
for i in self._sa_class_manager.mapper.c:
s.append('%25s %s' % (i, getattr(self, i.name)))
s+=['', '']
for i,p in enumerate(self.handPlayers):
s.append('%d. %s' % (i, p.name or '???'))
s.append(str(p))
return '\n'.join(s)
@property
def boardcards(self):
cards = []
for i in range(5):
cards.append(getattr(self, 'boardcard%d' % (i+1), None))
return filter(bool, cards)
@property
def HandClass(self):
"""Return HoldemOmahaHand or something like this"""
import Hand
if self.gametype.base == 'hold':
return Hand.HoldemOmahaHand
elif self.gametype.base == 'draw':
return Hand.DrawHand
elif self.gametype.base == 'stud':
return Hand.StudHand
raise Exception("Unknow gametype.base: '%s'" % self.gametype.base)
@property
def allStreets(self):
return self.HandClass.allStreets
@property
def actionStreets(self):
return self.HandClass.actionStreets
class HandPlayer(MappedBase):
"""Class reflecting HandsPlayers db table"""
def __init__(self, **kwargs):
if 'imported_hand' in kwargs and 'seatNo' in kwargs:
imported_hand = kwargs.pop('imported_hand')
self.position = self.getPosition(imported_hand, kwargs['seatNo'])
super(HandPlayer, self).__init__(**kwargs)
@reconstructor
def init_on_load(self):
self.name = self.player.name
@staticmethod
def getPosition(hand, seat):
"""Returns position value like 'B', 'S', '0', '1', ...
>>> class A(object): pass
...
>>> A.noSb = False
>>> A.maxseats = 6
>>> A.buttonpos = 2
>>> A.gametype = {'base': 'hold'}
>>> A.players = [(i, None, None) for i in (2, 4, 5, 6)]
>>> HandPlayer.getPosition(A, 6) # cut off
'1'
>>> HandPlayer.getPosition(A, 2) # button
'0'
>>> HandPlayer.getPosition(A, 4) # SB
'S'
>>> HandPlayer.getPosition(A, 5) # BB
'B'
>>> A.noSb = True
>>> HandPlayer.getPosition(A, 5) # MP3
'2'
>>> HandPlayer.getPosition(A, 6) # cut off
'1'
>>> HandPlayer.getPosition(A, 2) # button
'0'
>>> HandPlayer.getPosition(A, 4) # BB
'B'
"""
from itertools import chain
if hand.gametype['base'] == 'stud':
# FIXME: i've never played stud so plz check & del comment \\grindi
bringin = None
for action in chain(*[self.actions[street] for street in hand.allStreets]):
if action[1]=='bringin':
bringin = action[0]
break
if bringin is None:
raise Exception, "Cannot find bringin"
# name -> seat
bringin = int(filter(lambda p: p[1]==bringin, bringin)[0])
seat = (int(seat) - int(bringin))%int(hand.maxseats)
return str(seat)
else:
seats_occupied = sorted([seat_ for seat_, name, chips in hand.players], key=int)
if hand.buttonpos not in seats_occupied:
# i.e. something like
# Seat 3: PlayerX ($0), is sitting out
# The button is in seat #3
hand.buttonpos = max(seats_occupied,
key = lambda s: int(s)
if int(s) <= int(hand.buttonpos)
else int(s) - int(hand.maxseats)
)
seats_occupied = sorted(seats_occupied,
key = lambda seat_: (
- seats_occupied.index(seat_)
+ seats_occupied.index(hand.buttonpos)
+ 2) % len(seats_occupied)
)
# now (if SB presents) seats_occupied contains seats in order: BB, SB, BU, CO, MP3, ...
if hand.noSb:
# fix order in the case nosb
seats_occupied = seats_occupied[1:] + seats_occupied[0:1]
seats_occupied.insert(1, -1)
seat = seats_occupied.index(seat)
if seat == 0:
return 'B'
elif seat == 1:
return 'S'
else:
return str(seat-2)
@property
def cards(self):
cards = []
for i in range(7):
cards.append(getattr(self, 'card%d' % (i+1), None))
return filter(bool, cards)
def __str__(self):
s = list()
for i in self._sa_class_manager.mapper.c:
s.append('%45s %s' % (i, getattr(self, i.name)))
return '\n'.join(s)
class Site(object):
"""Class reflecting Players db table"""
INITIAL_DATA = [
(1 , 'Full Tilt Poker','FT'),
(2 , 'PokerStars', 'PS'),
(3 , 'Everleaf', 'EV'),
(4 , 'Win2day', 'W2'),
(5 , 'OnGame', 'OG'),
(6 , 'UltimateBet', 'UB'),
(7 , 'Betfair', 'BF'),
(8 , 'Absolute', 'AB'),
(9 , 'PartyPoker', 'PP'),
(10, 'Partouche', 'PA'),
(11, 'Carbon', 'CA'),
(12, 'PKR', 'PK'),
]
INITIAL_DATA_KEYS = ('id', 'name', 'code')
INITIAL_DATA_DICTS = [ dict(zip(INITIAL_DATA_KEYS, datum)) for datum in INITIAL_DATA ]
@classmethod
def insert_initial(cls, connection):
connection.execute(sites_table.insert(), cls.INITIAL_DATA_DICTS)
class Tourney(MappedBase):
"""Class reflecting Tourneys db table"""
@classmethod
def get_or_create(cls, session, siteTourneyNo, tourneyTypeId):
"""Fetch tourney by index or creates one if none. """
return get_or_create(cls, session, siteTourneyNo=siteTourneyNo,
tourneyTypeId=tourneyTypeId)[0]
class TourneyType(MappedBase):
"""Class reflecting TourneyType db table"""
@classmethod
def get_or_create(cls, session, **kwargs):
"""Fetch tourney type by index or creates one if none
Required kwargs:
buyin fee speed maxSeats knockout
rebuy addOn shootout matrix sng currency
"""
return get_or_create(cls, session, **kwargs)[0]
class TourneysPlayer(MappedBase):
"""Class reflecting TourneysPlayers db table"""
@classmethod
def get_or_create(cls, session, tourneyId, playerId):
"""Fetch tourney player by index or creates one if none """
return get_or_create(cls, session, tourneyId=tourneyId, playerId=playerId)
class Version(object):
"""Provides read/write access for version var"""
CURRENT_VERSION = 120 # db version for current release
# 119 - first alchemy version
# 120 - add m_factor
conn = None
ver = None
def __init__(self, connection=None):
if self.__class__.conn is None:
self.__class__.conn = connection
@classmethod
def is_wrong(cls):
return cls.get() != cls.CURRENT_VERSION
@classmethod
def get(cls):
if cls.ver is None:
try:
cls.ver = cls.conn.execute(select(['version'], settings_table)).fetchone()[0]
except:
return None
return cls.ver
@classmethod
def set(cls, value):
if cls.conn.execute(settings_table.select()).rowcount==0:
cls.conn.execute(settings_table.insert(), version=value)
else:
cls.conn.execute(settings_table.update().values(version=value))
cls.ver = value
@classmethod
def set_initial(cls):
cls.set(cls.CURRENT_VERSION)
mapper (Gametype, gametypes_table, properties={
'hands': relation(HandInternal, backref='gametype'),
})
mapper (Player, players_table, properties={
'playerHands': relation(HandPlayer, backref='player'),
'playerTourney': relation(TourneysPlayer, backref='player'),
})
mapper (Site, sites_table, properties={
'gametypes': relation(Gametype, backref = 'site'),
'players': relation(Player, backref = 'site'),
'tourneyTypes': relation(TourneyType, backref = 'site'),
})
mapper (HandActions, hands_actions_table, properties={})
mapper (HandInternal, hands_table, properties={
'handPlayers': relation(HandPlayer, backref='hand'),
'actions_all': relation(HandActions, backref='hand', uselist=False),
})
mapper (HandPlayer, hands_players_table, properties={})
mapper (Tourney, tourneys_table)
mapper (TourneyType, tourney_types_table, properties={
'tourneys': relation(Tourney, backref='type'),
})
mapper (TourneysPlayer, tourneys_players_table)
class LambdaKeyDict(defaultdict):
"""Operates like defaultdict but passes key argument to the factory function"""
def __missing__(key):
return self.default_factory(key)

View File

@ -1,460 +0,0 @@
#!/usr/bin/env python
# -*- coding: utf-8 -*-
#Copyright 2009-2011 Grigorij Indigirkin
#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.
"""@package AlchemyTables
Contains all sqlalchemy tables
"""
#TODO: gettextify if file is used again
from sqlalchemy import Table, Float, Column, Integer, String, MetaData, \
ForeignKey, Boolean, SmallInteger, DateTime, Text, Index, CHAR, \
PickleType, Unicode
from AlchemyFacilities import CardColumn, MoneyColumn, BigIntColumn
metadata = MetaData()
autorates_table = Table('Autorates', metadata,
Column('id', Integer, primary_key=True, nullable=False),
Column('playerId', Integer, ForeignKey("Players.id"), nullable=False),
Column('gametypeId', SmallInteger, ForeignKey("Gametypes.id"), nullable=False),
Column('description', String(50), nullable=False),
Column('shortDesc', CHAR(8), nullable=False),
Column('ratingTime', DateTime, nullable=False),
Column('handCount', Integer, nullable=False),
mysql_charset='utf8',
mysql_engine='InnoDB',
)
gametypes_table = Table('Gametypes', metadata,
Column('id', SmallInteger, primary_key=True),
Column('siteId', SmallInteger, ForeignKey("Sites.id"), nullable=False), # SMALLINT
Column('currency', String(4), nullable=False), # varchar(4) NOT NULL
Column('type', String(4), nullable=False), # char(4) NOT NULL
Column('base', String(4), nullable=False), # char(4) NOT NULL
Column('category', String(9), nullable=False), # varchar(9) NOT NULL
Column('limitType', CHAR(2), nullable=False), # char(2) NOT NULL
Column('hiLo', CHAR(1), nullable=False), # char(1) NOT NULL
Column('smallBlind', Integer(3)), # int
Column('bigBlind', Integer(3)), # int
Column('smallBet', Integer(3), nullable=False), # int NOT NULL
Column('bigBet', Integer(3), nullable=False), # int NOT NULL
mysql_charset='utf8',
mysql_engine='InnoDB',
)
hands_table = Table('Hands', metadata,
Column('id', BigIntColumn, primary_key=True),
Column('tableName', String(30), nullable=False),
Column('siteHandNo', BigIntColumn, nullable=False),
Column('gametypeId', SmallInteger, ForeignKey('Gametypes.id'), nullable=False),
Column('startTime', DateTime, nullable=False),
Column('importTime', DateTime, nullable=False),
Column('seats', SmallInteger, nullable=False),
Column('maxSeats', SmallInteger, nullable=False),
Column('boardcard1', CardColumn),
Column('boardcard2', CardColumn),
Column('boardcard3', CardColumn),
Column('boardcard4', CardColumn),
Column('boardcard5', CardColumn),
Column('texture', SmallInteger),
Column('playersVpi', SmallInteger, nullable=False),
Column('playersAtStreet1', SmallInteger, nullable=False, default=0),
Column('playersAtStreet2', SmallInteger, nullable=False, default=0),
Column('playersAtStreet3', SmallInteger, nullable=False, default=0),
Column('playersAtStreet4', SmallInteger, nullable=False, default=0),
Column('playersAtShowdown',SmallInteger, nullable=False),
Column('street0Raises', SmallInteger, nullable=False),
Column('street1Raises', SmallInteger, nullable=False),
Column('street2Raises', SmallInteger, nullable=False),
Column('street3Raises', SmallInteger, nullable=False),
Column('street4Raises', SmallInteger, nullable=False),
Column('street1Pot', MoneyColumn),
Column('street2Pot', MoneyColumn),
Column('street3Pot', MoneyColumn),
Column('street4Pot', MoneyColumn),
Column('showdownPot', MoneyColumn),
Column('comment', Text),
Column('commentTs', DateTime),
mysql_charset='utf8',
mysql_engine='InnoDB',
)
Index('siteHandNo', hands_table.c.siteHandNo, hands_table.c.gametypeId, unique=True)
hands_actions_table = Table('HandsActions', metadata,
Column('id', BigIntColumn, primary_key=True, nullable=False),
Column('handId', BigIntColumn, ForeignKey("Hands.id"), nullable=False),
Column('actions', PickleType, nullable=False),
mysql_charset='utf8',
mysql_engine='InnoDB',
)
hands_players_table = Table('HandsPlayers', metadata,
Column('id', BigIntColumn, primary_key=True),
Column('handId', BigIntColumn, ForeignKey("Hands.id"), nullable=False),
Column('playerId', Integer, ForeignKey("Players.id"), nullable=False),
Column('startCash', MoneyColumn),
Column('position', CHAR(1)), #CHAR(1)
Column('seatNo', SmallInteger, nullable=False), #SMALLINT NOT NULL
Column('card1', CardColumn), #smallint NOT NULL,
Column('card2', CardColumn), #smallint NOT NULL
Column('card3', CardColumn), #smallint
Column('card4', CardColumn), #smallint
Column('card5', CardColumn), #smallint
Column('card6', CardColumn), #smallint
Column('card7', CardColumn), #smallint
Column('startCards', SmallInteger), #smallint
Column('m_factor', Integer), # null for ring games
Column('ante', MoneyColumn), #INT
Column('winnings', MoneyColumn, nullable=False, default=0), #int NOT NULL
Column('rake', MoneyColumn, nullable=False, default=0), #int NOT NULL
Column('totalProfit', MoneyColumn), #INT
Column('comment', Text), #text
Column('commentTs', DateTime), #DATETIME
Column('tourneysPlayersId', BigIntColumn, ForeignKey("TourneysPlayers.id"),), #BIGINT UNSIGNED
Column('tourneyTypeId', Integer, ForeignKey("TourneyTypes.id"),), #SMALLINT UNSIGNED
Column('wonWhenSeenStreet1',Float), #FLOAT
Column('wonWhenSeenStreet2',Float), #FLOAT
Column('wonWhenSeenStreet3',Float), #FLOAT
Column('wonWhenSeenStreet4',Float), #FLOAT
Column('wonAtSD', Float), #FLOAT
Column('street0VPI', Boolean), #BOOLEAN
Column('street0Aggr', Boolean), #BOOLEAN
Column('street0_3BChance', Boolean), #BOOLEAN
Column('street0_3BDone', Boolean), #BOOLEAN
Column('street0_4BChance', Boolean), #BOOLEAN
Column('street0_4BDone', Boolean), #BOOLEAN
Column('other3BStreet0', Boolean), #BOOLEAN
Column('other4BStreet0', Boolean), #BOOLEAN
Column('street1Seen', Boolean), #BOOLEAN
Column('street2Seen', Boolean), #BOOLEAN
Column('street3Seen', Boolean), #BOOLEAN
Column('street4Seen', Boolean), #BOOLEAN
Column('sawShowdown', Boolean), #BOOLEAN
Column('street1Aggr', Boolean), #BOOLEAN
Column('street2Aggr', Boolean), #BOOLEAN
Column('street3Aggr', Boolean), #BOOLEAN
Column('street4Aggr', Boolean), #BOOLEAN
Column('otherRaisedStreet0',Boolean), #BOOLEAN
Column('otherRaisedStreet1',Boolean), #BOOLEAN
Column('otherRaisedStreet2',Boolean), #BOOLEAN
Column('otherRaisedStreet3',Boolean), #BOOLEAN
Column('otherRaisedStreet4',Boolean), #BOOLEAN
Column('foldToOtherRaisedStreet0', Boolean), #BOOLEAN
Column('foldToOtherRaisedStreet1', Boolean), #BOOLEAN
Column('foldToOtherRaisedStreet2', Boolean), #BOOLEAN
Column('foldToOtherRaisedStreet3', Boolean), #BOOLEAN
Column('foldToOtherRaisedStreet4', Boolean), #BOOLEAN
Column('stealAttemptChance', Boolean), #BOOLEAN
Column('stealAttempted', Boolean), #BOOLEAN
Column('foldBbToStealChance', Boolean), #BOOLEAN
Column('foldedBbToSteal', Boolean), #BOOLEAN
Column('foldSbToStealChance', Boolean), #BOOLEAN
Column('foldedSbToSteal', Boolean), #BOOLEAN
Column('street1CBChance', Boolean), #BOOLEAN
Column('street1CBDone', Boolean), #BOOLEAN
Column('street2CBChance', Boolean), #BOOLEAN
Column('street2CBDone', Boolean), #BOOLEAN
Column('street3CBChance', Boolean), #BOOLEAN
Column('street3CBDone', Boolean), #BOOLEAN
Column('street4CBChance', Boolean), #BOOLEAN
Column('street4CBDone', Boolean), #BOOLEAN
Column('foldToStreet1CBChance', Boolean), #BOOLEAN
Column('foldToStreet1CBDone', Boolean), #BOOLEAN
Column('foldToStreet2CBChance', Boolean), #BOOLEAN
Column('foldToStreet2CBDone', Boolean), #BOOLEAN
Column('foldToStreet3CBChance', Boolean), #BOOLEAN
Column('foldToStreet3CBDone', Boolean), #BOOLEAN
Column('foldToStreet4CBChance', Boolean), #BOOLEAN
Column('foldToStreet4CBDone', Boolean), #BOOLEAN
Column('street1CheckCallRaiseChance',Boolean), #BOOLEAN
Column('street1CheckCallRaiseDone', Boolean), #BOOLEAN
Column('street2CheckCallRaiseChance',Boolean), #BOOLEAN
Column('street2CheckCallRaiseDone', Boolean), #BOOLEAN
Column('street3CheckCallRaiseChance',Boolean), #BOOLEAN
Column('street3CheckCallRaiseDone', Boolean), #BOOLEAN
Column('street4CheckCallRaiseChance',Boolean), #BOOLEAN
Column('street4CheckCallRaiseDone', Boolean), #BOOLEAN
Column('street0Calls', SmallInteger), #TINYINT
Column('street1Calls', SmallInteger), #TINYINT
Column('street2Calls', SmallInteger), #TINYINT
Column('street3Calls', SmallInteger), #TINYINT
Column('street4Calls', SmallInteger), #TINYINT
Column('street0Bets', SmallInteger), #TINYINT
Column('street1Bets', SmallInteger), #TINYINT
Column('street2Bets', SmallInteger), #TINYINT
Column('street3Bets', SmallInteger), #TINYINT
Column('street4Bets', SmallInteger), #TINYINT
Column('street0Raises', SmallInteger), #TINYINT
Column('street1Raises', SmallInteger), #TINYINT
Column('street2Raises', SmallInteger), #TINYINT
Column('street3Raises', SmallInteger), #TINYINT
Column('street4Raises', SmallInteger), #TINYINT
Column('actionString', String(15)), #VARCHAR(15)
mysql_charset='utf8',
mysql_engine='InnoDB',
)
hud_cache_table = Table('HudCache', metadata,
Column('id', BigIntColumn, primary_key=True),
Column('gametypeId', SmallInteger, ForeignKey("Gametypes.id"), nullable=False), # SMALLINT
Column('playerId', Integer, ForeignKey("Players.id"), nullable=False), # SMALLINT
Column('activeSeats', SmallInteger, nullable=False), # SMALLINT NOT NULL
Column('position', CHAR(1)), # CHAR(1)
Column('tourneyTypeId', Integer, ForeignKey("TourneyTypes.id") ), # SMALLINT
Column('styleKey', CHAR(7), nullable=False), # CHAR(7) NOT NULL
Column('m_factor', Integer),
Column('HDs', Integer, nullable=False), # INT NOT NULL
Column('wonWhenSeenStreet1', Float), # FLOAT
Column('wonWhenSeenStreet2', Float), # FLOAT
Column('wonWhenSeenStreet3', Float), # FLOAT
Column('wonWhenSeenStreet4', Float), # FLOAT
Column('wonAtSD', Float), # FLOAT
Column('street0VPI', Integer), # INT
Column('street0Aggr', Integer), # INT
Column('street0_3BChance', Integer), # INT
Column('street0_3BDone', Integer), # INT
Column('street0_4BChance', Integer), # INT
Column('street0_4BDone', Integer), # INT
Column('other3BStreet0', Integer), # INT
Column('other4BStreet0', Integer), # INT
Column('street1Seen', Integer), # INT
Column('street2Seen', Integer), # INT
Column('street3Seen', Integer), # INT
Column('street4Seen', Integer), # INT
Column('sawShowdown', Integer), # INT
Column('street1Aggr', Integer), # INT
Column('street2Aggr', Integer), # INT
Column('street3Aggr', Integer), # INT
Column('street4Aggr', Integer), # INT
Column('otherRaisedStreet0', Integer), # INT
Column('otherRaisedStreet1', Integer), # INT
Column('otherRaisedStreet2', Integer), # INT
Column('otherRaisedStreet3', Integer), # INT
Column('otherRaisedStreet4', Integer), # INT
Column('foldToOtherRaisedStreet0', Integer), # INT
Column('foldToOtherRaisedStreet1', Integer), # INT
Column('foldToOtherRaisedStreet2', Integer), # INT
Column('foldToOtherRaisedStreet3', Integer), # INT
Column('foldToOtherRaisedStreet4', Integer), # INT
Column('stealAttemptChance', Integer), # INT
Column('stealAttempted', Integer), # INT
Column('foldBbToStealChance', Integer), # INT
Column('foldedBbToSteal', Integer), # INT
Column('foldSbToStealChance', Integer), # INT
Column('foldedSbToSteal', Integer), # INT
Column('street1CBChance', Integer), # INT
Column('street1CBDone', Integer), # INT
Column('street2CBChance', Integer), # INT
Column('street2CBDone', Integer), # INT
Column('street3CBChance', Integer), # INT
Column('street3CBDone', Integer), # INT
Column('street4CBChance', Integer), # INT
Column('street4CBDone', Integer), # INT
Column('foldToStreet1CBChance', Integer), # INT
Column('foldToStreet1CBDone', Integer), # INT
Column('foldToStreet2CBChance', Integer), # INT
Column('foldToStreet2CBDone', Integer), # INT
Column('foldToStreet3CBChance', Integer), # INT
Column('foldToStreet3CBDone', Integer), # INT
Column('foldToStreet4CBChance', Integer), # INT
Column('foldToStreet4CBDone', Integer), # INT
Column('totalProfit', Integer), # INT
Column('street1CheckCallRaiseChance', Integer), # INT
Column('street1CheckCallRaiseDone', Integer), # INT
Column('street2CheckCallRaiseChance', Integer), # INT
Column('street2CheckCallRaiseDone', Integer), # INT
Column('street3CheckCallRaiseChance', Integer), # INT
Column('street3CheckCallRaiseDone', Integer), # INT
Column('street4CheckCallRaiseChance', Integer), # INT
Column('street4CheckCallRaiseDone', Integer), # INT
Column('street0Calls', Integer), # INT
Column('street1Calls', Integer), # INT
Column('street2Calls', Integer), # INT
Column('street3Calls', Integer), # INT
Column('street4Calls', Integer), # INT
Column('street0Bets', Integer), # INT
Column('street1Bets', Integer), # INT
Column('street2Bets', Integer), # INT
Column('street3Bets', Integer), # INT
Column('street4Bets', Integer), # INT
Column('street0Raises', Integer), # INT
Column('street1Raises', Integer), # INT
Column('street2Raises', Integer), # INT
Column('street3Raises', Integer), # INT
Column('street4Raises', Integer), # INT
mysql_charset='utf8',
mysql_engine='InnoDB',
)
players_table = Table('Players', metadata,
Column('id', Integer, primary_key=True),
Column('name', Unicode(32), nullable=False), # VARCHAR(32) CHARACTER SET utf8 NOT NULL
Column('siteId', SmallInteger, ForeignKey("Sites.id"), nullable=False), # SMALLINT
Column('comment', Text), # text
Column('commentTs', DateTime), # DATETIME
mysql_charset='utf8',
mysql_engine='InnoDB',
)
Index('name', players_table.c.name, players_table.c.siteId, unique=True)
settings_table = Table('Settings', metadata,
Column('version', SmallInteger, nullable=False),
mysql_charset='utf8',
mysql_engine='InnoDB',
)
sites_table = Table('Sites', metadata,
Column('id', SmallInteger, primary_key=True),
Column('name', String(32), nullable=False), # varchar(32) NOT NULL
Column('code', String(2), nullable=False), # char(2) NOT NULL
mysql_charset='utf8',
mysql_engine='InnoDB',
)
tourneys_table = Table('Tourneys', metadata,
Column('id', Integer, primary_key=True),
Column('tourneyTypeId', Integer, ForeignKey("TourneyTypes.id"), nullable=False, default=1),
Column('siteTourneyNo', BigIntColumn, nullable=False), # BIGINT NOT NULL
Column('entries', Integer), # INT NOT NULL
Column('prizepool', Integer), # INT NOT NULL
Column('tourStartTime', DateTime), # DATETIME NOT NULL
Column('tourEndTime', DateTime), # DATETIME
Column('tourneyName', String(40)), # varchar(40)
# Mask use : 1=Positionnal Winnings|2=Match1|4=Match2|...|pow(2,n)=Matchn
Column('matrixIdProcessed',SmallInteger, default=0), # TINYINT UNSIGNED DEFAULT 0
Column('totalRebuyCount', Integer, default=0), # INT DEFAULT 0
Column('totalAddOnCount', Integer, default=0), # INT DEFAULT 0
Column('comment', Text), # TEXT
Column('commentTs', DateTime), # DATETIME
mysql_charset='utf8',
mysql_engine='InnoDB',
)
Index('siteTourneyNo', tourneys_table.c.siteTourneyNo, tourneys_table.c.tourneyTypeId, unique=True)
tourney_types_table = Table('TourneyTypes', metadata,
Column('id', Integer, primary_key=True),
Column('siteId', SmallInteger, ForeignKey("Sites.id"), nullable=False),
Column('currency', String(4), nullable=False), # varchar(4) NOT NULL
Column('buyin', Integer, nullable=False), # INT NOT NULL
Column('fee', Integer, nullable=False), # INT NOT NULL
Column('buyInChips', Integer, nullable=False), # INT NOT NULL
Column('maxSeats', Boolean, nullable=False, default=-1), # INT NOT NULL DEFAULT -1
Column('rebuy', Boolean, nullable=False, default=False), # BOOLEAN NOT NULL DEFAULT False
Column('rebuyCost', Integer), # INT
Column('rebuyChips', Integer), # INT
Column('addOn', Boolean, nullable=False, default=False), # BOOLEAN NOT NULL DEFAULT False
Column('addOnCost', Integer), # INT
Column('addOnChips', Integer), # INT
Column('knockout', Boolean, nullable=False, default=False), # BOOLEAN NOT NULL DEFAULT False
Column('koBounty', Integer), # INT
Column('speed', String(10)), # varchar(10)
Column('shootout', Boolean, nullable=False, default=False), # BOOLEAN NOT NULL DEFAULT False
Column('matrix', Boolean, nullable=False, default=False), # BOOLEAN NOT NULL DEFAULT False
Column('sng', Boolean, nullable=False, default=False), # BOOLEAN NOT NULL DEFAULT False
Column('satellite', Boolean, nullable=False, default=False), # BOOLEAN NOT NULL DEFAULT False
Column('doubleOrNothing', Boolean, nullable=False, default=False), # BOOLEAN NOT NULL DEFAULT False
Column('guarantee', Integer, nullable=False, default=0), # INT NOT NULL DEFAULT 0
mysql_charset='utf8',
mysql_engine='InnoDB',
)
Index('tourneyTypes_all',
tourney_types_table.c.siteId, tourney_types_table.c.buyin, tourney_types_table.c.fee,
tourney_types_table.c.maxSeats, tourney_types_table.c.knockout, tourney_types_table.c.rebuy,
tourney_types_table.c.addOn, tourney_types_table.c.speed,
tourney_types_table.c.shootout, tourney_types_table.c.matrix, tourney_types_table.c.sng)
tourneys_players_table = Table('TourneysPlayers', metadata,
Column('id', BigIntColumn, primary_key=True),
Column('tourneyId', Integer, ForeignKey("Tourneys.id"), nullable=False),
Column('playerId', Integer, ForeignKey("Players.id"), nullable=False),
Column('rank', Integer), # INT NOT NULL
Column('winnings', Integer), # INT NOT NULL
Column('winningsCurrency', Text), # TEXT
Column('rebuyCount', Integer, default=0), # INT DEFAULT 0
Column('addOnCount', Integer, default=0), # INT DEFAULT 0
Column('koCount', Integer, default=0), # INT DEFAULT 0
Column('comment', Text), # TEXT
Column('commentTs', DateTime), # DATETIME
mysql_charset='utf8',
mysql_engine='InnoDB',
)
Index('tourneyId', tourneys_players_table.c.tourneyId, tourneys_players_table.c.playerId, unique=True)
def sss():
"Debug function. Returns (config, sql, db)"
import Configuration, SQL, Database, os
class Dummy(object):
pass
self = Dummy()
self.config = Configuration.Config()
self.settings = {}
if (os.sep=="/"):
self.settings['os']="linuxmac"
else:
self.settings['os']="windows"
self.settings.update(self.config.get_db_parameters())
self.settings.update(self.config.get_import_parameters())
self.settings.update(self.config.get_default_paths())
self.sql = SQL.Sql( db_server = self.settings['db-server'])
self.db = Database.Database(self.config, sql = self.sql)
return self.config, self.sql, self.db

View File

@ -74,7 +74,7 @@ class Betfair(HandHistoryConverter):
if not m:
tmp = handText[0:100]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
mg = m.groupdict()
@ -196,7 +196,7 @@ class Betfair(HandHistoryConverter):
elif action.group('ATYPE') == 'checks':
hand.addCheck( street, action.group('PNAME'))
else:
sys.stderr.write(_("DEBUG: ") + _("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'),action.group('ATYPE')))
sys.stderr.write(_("DEBUG: ") + _("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'), action.group('ATYPE')))
def readShowdownActions(self, hand):

View File

@ -128,7 +128,7 @@ or None if we fail to get the info """
except AttributeError:
tmp = handText[0:100]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
self.info = {}
@ -264,7 +264,7 @@ or None if we fail to get the info """
elif action.group('ATYPE') == 'ALL_IN':
hand.addAllIn(street, player, action.group('BET'))
else:
logging.debug(_("Unimplemented readAction: '%s' '%s'") % (action.group('PSEAT'),action.group('ATYPE')))
logging.debug(_("Unimplemented readAction: '%s' '%s'") % (action.group('PSEAT'), action.group('ATYPE')))
def readShowdownActions(self, hand):
for shows in self.re_ShowdownAction.finditer(hand.handText):

View File

@ -101,36 +101,6 @@ def twoStartCardString(card):
#print "twoStartCardString(", card ,") = " + ret
return ret
def fourStartCards(value1, suit1, value2, suit2, value3, suit3, value4, suit4):
""" Function to convert 4 value,suit pairs into a Omaha style starting hand,
haven't decided how to encode this yet """
# This doesn't actually do anything yet - CG
# What combinations do we need to store? just cards: AA23? some suits as well e.g. when
# double suited ATcKTd? Lots more possible combos than holdem :-( 270K vs 1326? not sure
# Probably need to use this field as a key into some other table - sc
#AAKKds
#AAKKs
#AAKKr
# Is probably what we are looking for
# mct:
# my maths says there are 4 classes of suitedness
# SSSS SSSx SSxy SSHH
# encode them as follows:
# SSSS (K, J, 6, 3)
# - 13C4 = 715 possibilities
# SSSx (K, J, 6),(3)
# - 13C3 * 13 = 3718 possibilities
# SSxy (K, J),(6),(3)
# - 13C2 * 13*13 = 13182 possibilities
# SSHH (K, J),(6, 3)
# - 13C2 * 13C2 = 6084 possibilities
# Needless to say they won't fit on a 13x13 grid.
# The actual number of hands in each class is far greater
return(0)
def cardFromValueSuit(value, suit):
""" 0=none, 1-13=2-Ah 14-26=2-Ad 27-39=2-Ac 40-52=2-As """
if suit == 'h': return(value-1)

View File

@ -78,7 +78,6 @@ def get_exec_path():
def get_config(file_name, fallback = True):
"""Looks in cwd and in self.default_config_path for a config file."""
# look for example file even if not used here, path is returned to caller
config_found,example_found,example_copy = False,False,False
config_path, example_path = None,None
@ -88,17 +87,17 @@ def get_config(file_name, fallback = True):
config_path = os.path.join(exec_dir, 'pyfpdb', file_name)
else:
config_path = os.path.join(exec_dir, file_name)
# print "config_path=", config_path
#print "config_path=", config_path
if os.path.exists(config_path): # there is a file in the cwd
config_found = True # so we use it
else: # no file in the cwd, look where it should be in the first place
default_dir = get_default_config_path()
config_path = os.path.join(default_dir, file_name)
# print "config path 2=", config_path
#print "config path 2=", config_path
if os.path.exists(config_path):
config_found = True
# Example configuration for debian package
# Example configuration for debian package
if os.name == 'posix':
# If we're on linux, try to copy example from the place
# debian package puts it; get_default_config_path() creates
@ -111,13 +110,20 @@ def get_config(file_name, fallback = True):
example_copy = True
msg = _("Config file has been created at %s.\n") % config_path
logging.info(msg)
except IOError:
try:
example_path = file_name + '.example'
shutil.copyfile(example_path, config_path)
example_copy = True
msg = _("Config file has been created at %s.\n") % config_path
logging.info(msg)
except IOError:
pass
# OK, fall back to the .example file, should be in the start dir
elif os.path.exists(file_name + ".example"):
try:
print ""
#print ""
example_path = file_name + ".example"
check_dir(default_dir)
if not config_found and fallback:
@ -167,7 +173,7 @@ def get_logger(file_name, config = "config", fallback = False, log_dir=None, log
log = logging.getLogger()
# but it looks like default is no output :-( maybe because all the calls name a module?
log.debug(_("Default logger initialised for %s") % file)
print(_("Default logger initialised for %s") % file)
#print(_("Default logger initialised for %s") % file)
return log
def check_dir(path, create = True):
@ -308,7 +314,7 @@ class Site:
self.layout = {}
self.emails = {}
print _("Loading site"), self.site_name
#print _("Loading site"), self.site_name
for layout_node in node.getElementsByTagName('layout'):
lo = Layout(layout_node)
@ -484,19 +490,18 @@ class Import:
def __init__(self, node):
self.node = node
self.interval = node.getAttribute("interval")
self.callFpdbHud = node.getAttribute("callFpdbHud")
self.hhArchiveBase = node.getAttribute("hhArchiveBase")
self.sessionTimeout = node.getAttribute("sessionTimeout")
self.ResultsDirectory = node.getAttribute("ResultsDirectory")
self.hhBulkPath = node.getAttribute("hhBulkPath")
self.saveActions = string_to_bool(node.getAttribute("saveActions"), default=False)
self.cacheSessions = string_to_bool(node.getAttribute("cacheSessions"), default=False)
self.sessionTimeout = string_to_bool(node.getAttribute("sessionTimeout"), default=30)
self.saveActions = string_to_bool(node.getAttribute("saveActions") , default=False)
self.cacheSessions = string_to_bool(node.getAttribute("cacheSessions") , default=False)
self.callFpdbHud = string_to_bool(node.getAttribute("callFpdbHud") , default=False)
self.fastStoreHudCache = string_to_bool(node.getAttribute("fastStoreHudCache"), default=False)
self.saveStarsHH = string_to_bool(node.getAttribute("saveStarsHH"), default=False)
self.saveStarsHH = string_to_bool(node.getAttribute("saveStarsHH") , default=False)
def __str__(self):
return " interval = %s\n callFpdbHud = %s\n hhArchiveBase = %s\n saveActions = %s\n fastStoreHudCache = %s\nResultsDirectory = %s" \
% (self.interval, self.callFpdbHud, self.hhArchiveBase, self.saveActions, self.cacheSessions, self.sessionTimeout, self.fastStoreHudCache, self.ResultsDirectory)
return " interval = %s\n callFpdbHud = %s\n saveActions = %s\n fastStoreHudCache = %s\nResultsDirectory = %s" \
% (self.interval, self.callFpdbHud, self.saveActions, self.cacheSessions, self.sessionTimeout, self.fastStoreHudCache, self.ResultsDirectory)
class HudUI:
def __init__(self, node):
@ -626,20 +631,20 @@ class RawHands:
if node==None:
self.save="error"
self.compression="none"
print _("missing config section raw_hands")
#print _("missing config section raw_hands")
else:
save=node.getAttribute("save")
if save in ("none", "error", "all"):
self.save=save
else:
print _("Invalid config value for raw_hands.save, defaulting to \"error\"")
print (_("Invalid config value for %s, defaulting to %s") % (raw_hands.save, "\"error\""))
self.save="error"
compression=node.getAttribute("compression")
if save in ("none", "gzip", "bzip2"):
self.compression=compression
else:
print _("Invalid config value for raw_hands.compression, defaulting to \"none\"")
print (_("Invalid config value for %s, defaulting to %s") % (raw_hands.compression, "\"none\""))
self.compression="none"
#end def __init__
@ -652,20 +657,20 @@ class RawTourneys:
if node==None:
self.save="error"
self.compression="none"
print _("missing config section raw_tourneys")
#print _("missing config section raw_tourneys")
else:
save=node.getAttribute("save")
if save in ("none", "error", "all"):
self.save=save
else:
print _("Invalid config value for raw_tourneys.save, defaulting to \"error\"")
print (_("Invalid config value for %s, defaulting to %s") % (raw_tourneys.save, "\"error\""))
self.save="error"
compression=node.getAttribute("compression")
if save in ("none", "gzip", "bzip2"):
self.compression=compression
else:
print _("Invalid config value for raw_tourneys.compression, defaulting to \"none\"")
print (_("Invalid config value for %s, defaulting to %s") % (raw_tourneys.compression, "\"none\""))
self.compression="none"
#end def __init__
@ -715,13 +720,13 @@ class Config:
while added > 0 and n < 2:
n = n + 1
log.info(_("Reading configuration file %s") % file)
print (("\n"+_("Reading configuration file %s")+"\n") % file)
#print (("\n"+_("Reading configuration file %s")+"\n") % file)
try:
doc = xml.dom.minidom.parse(file)
self.doc = doc
self.file_error = None
except:
log.error(_("Error parsing %s. See error log file.") % (file))
log.error((_("Error parsing %s.") % (file)) + _("See error log file."))
traceback.print_exc(file=sys.stderr)
self.file_error = sys.exc_info()[1]
# we could add a parameter to decide whether to return or read a line and exit?
@ -824,7 +829,7 @@ class Config:
for raw_tourneys_node in doc.getElementsByTagName('raw_tourneys'):
self.raw_tourneys = RawTourneys(raw_tourneys_node)
print ""
#print ""
#end def __init__
def add_missing_elements(self, doc, example_file):
@ -837,7 +842,7 @@ class Config:
try:
example_doc = xml.dom.minidom.parse(example_file)
except:
log.error(_("Error parsing example configuration file %s. See error log file.") % (example_file))
log.error((_("Error parsing example configuration file %s.") % (example_file)) + _("See error log file."))
return nodes_added
for cnode in doc.getElementsByTagName("FreePokerToolsConfig"):
@ -861,9 +866,6 @@ class Config:
return nodes_added
def set_hhArchiveBase(self, path):
self.imp.node.setAttribute("hhArchiveBase", path)
def find_default_conf(self):
if os.name == 'posix':
config_path = os.path.join(os.path.expanduser("~"), '.fpdb', 'default.conf')
@ -1261,10 +1263,6 @@ class Config:
try: imp['interval'] = self.imp.interval
except: imp['interval'] = 10
# hhArchiveBase is the temp store for part-processed hand histories - should be redundant eventually
try: imp['hhArchiveBase'] = self.imp.hhArchiveBase
except: imp['hhArchiveBase'] = "~/.fpdb/HandHistories/"
# ResultsDirectory is the local cache for downloaded results
# NOTE: try: except: doesn'tseem to be triggering
# using if instead

View File

@ -73,7 +73,7 @@ except ImportError:
use_numpy = False
DB_VERSION = 150
DB_VERSION = 152
# Variance created as sqlite has a bunch of undefined aggregate functions.
@ -134,6 +134,9 @@ class Database:
, {'tab':'HudCache', 'col':'gametypeId', 'drop':1}
, {'tab':'HudCache', 'col':'playerId', 'drop':0}
, {'tab':'HudCache', 'col':'tourneyTypeId', 'drop':0}
, {'tab':'SessionsCache', 'col':'gametypeId', 'drop':1}
, {'tab':'SessionsCache', 'col':'playerId', 'drop':0}
, {'tab':'SessionsCache', 'col':'tourneyTypeId', 'drop':0}
, {'tab':'Players', 'col':'siteId', 'drop':1}
#, {'tab':'Players', 'col':'name', 'drop':0} unique indexes not dropped
, {'tab':'Tourneys', 'col':'tourneyTypeId', 'drop':1}
@ -157,6 +160,9 @@ class Database:
, {'tab':'HudCache', 'col':'gametypeId', 'drop':1}
, {'tab':'HudCache', 'col':'playerId', 'drop':0}
, {'tab':'HudCache', 'col':'tourneyTypeId', 'drop':0}
, {'tab':'SessionsCache', 'col':'gametypeId', 'drop':1}
, {'tab':'SessionsCache', 'col':'playerId', 'drop':0}
, {'tab':'SessionsCache', 'col':'tourneyTypeId', 'drop':0}
, {'tab':'Players', 'col':'siteId', 'drop':1}
, {'tab':'Tourneys', 'col':'tourneyTypeId', 'drop':1}
, {'tab':'TourneysPlayers', 'col':'playerId', 'drop':0}
@ -182,6 +188,9 @@ class Database:
, {'fktab':'HudCache', 'fkcol':'gametypeId', 'rtab':'Gametypes', 'rcol':'id', 'drop':1}
, {'fktab':'HudCache', 'fkcol':'playerId', 'rtab':'Players', 'rcol':'id', 'drop':0}
, {'fktab':'HudCache', 'fkcol':'tourneyTypeId', 'rtab':'TourneyTypes', 'rcol':'id', 'drop':1}
, {'fktab':'SessionsCache','fkcol':'gametypeId', 'rtab':'Gametypes', 'rcol':'id', 'drop':1}
, {'fktab':'SessionsCache','fkcol':'playerId', 'rtab':'Players', 'rcol':'id', 'drop':0}
, {'fktab':'SessionsCache','fkcol':'tourneyTypeId', 'rtab':'TourneyTypes', 'rcol':'id', 'drop':1}
]
, [ # foreign keys for postgres (index 3)
{'fktab':'Hands', 'fkcol':'gametypeId', 'rtab':'Gametypes', 'rcol':'id', 'drop':1}
@ -193,6 +202,9 @@ class Database:
, {'fktab':'HudCache', 'fkcol':'gametypeId', 'rtab':'Gametypes', 'rcol':'id', 'drop':1}
, {'fktab':'HudCache', 'fkcol':'playerId', 'rtab':'Players', 'rcol':'id', 'drop':0}
, {'fktab':'HudCache', 'fkcol':'tourneyTypeId', 'rtab':'TourneyTypes', 'rcol':'id', 'drop':1}
, {'fktab':'SessionsCache','fkcol':'gametypeId', 'rtab':'Gametypes', 'rcol':'id', 'drop':1}
, {'fktab':'SessionsCache','fkcol':'playerId', 'rtab':'Players', 'rcol':'id', 'drop':0}
, {'fktab':'SessionsCache','fkcol':'tourneyTypeId', 'rtab':'TourneyTypes', 'rcol':'id', 'drop':1}
]
, [ # no foreign keys in sqlite (index 4)
]
@ -261,6 +273,7 @@ class Database:
self.db_path = ''
gen = c.get_general_params()
self.day_start = 0
self._has_lock = False
if 'day_start' in gen:
self.day_start = float(gen['day_start'])
@ -386,7 +399,12 @@ class Database:
if use_pool:
MySQLdb = pool.manage(MySQLdb, pool_size=5)
try:
self.connection = MySQLdb.connect(host=host, user=user, passwd=password, db=database, use_unicode=True)
self.connection = MySQLdb.connect(host=host
,user=user
,passwd=password
,db=database
,charset='utf8'
,use_unicode=True)
self.__connected = True
#TODO: Add port option
except MySQLdb.Error, ex:
@ -449,7 +467,7 @@ class Database:
os.mkdir(self.config.dir_database)
database = os.path.join(self.config.dir_database, database)
self.db_path = database
log.info(_("Connecting to SQLite: %(database)s") % {'database':self.db_path})
log.info(_("Connecting to SQLite: %s") % 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
@ -492,19 +510,18 @@ class Database:
self.cursor.execute("SELECT * FROM Settings")
settings = self.cursor.fetchone()
if settings[0] != DB_VERSION:
log.error(_("outdated or too new database version (%s) - please recreate tables")
% (settings[0]))
log.error((_("Outdated or too new database version (%s).") % (settings[0])) + " " + _("Please recreate tables."))
self.wrongDbVersion = True
except:# _mysql_exceptions.ProgrammingError:
if database != ":memory:":
if create:
print _("Failed to read settings table - recreating tables")
log.info(_("Failed to read settings table - recreating tables"))
print (_("Failed to read settings table.") + " - " + _("Recreating tables."))
log.info(_("Failed to read settings table.") + " - " + _("Recreating tables."))
self.recreate_tables()
self.check_version(database=database, create=False)
else:
print _("Failed to read settings table - please recreate tables")
log.info(_("Failed to read settings table - please recreate tables"))
print (_("Failed to read settings table.") + " - " + _("Please recreate tables."))
log.info(_("Failed to read settings table.") + " - " + _("Please recreate tables."))
self.wrongDbVersion = True
else:
self.wrongDbVersion = True
@ -1253,6 +1270,12 @@ class Database:
c.execute(self.sql.query['createRawHands'])
c.execute(self.sql.query['createRawTourneys'])
# Create sessionscache indexes
log.debug("Creating SessionsCache indexes")
c.execute(self.sql.query['addSessionIdIndex'])
c.execute(self.sql.query['addHandsSessionIdIndex'])
c.execute(self.sql.query['addHandsGameSessionIdIndex'])
# Create unique indexes:
log.debug("Creating unique indexes")
c.execute(self.sql.query['addTourneyIndex'])
@ -1519,6 +1542,7 @@ class Database:
c.execute("INSERT INTO Sites (name,code) VALUES ('Betfair', 'BF')")
c.execute("INSERT INTO Sites (name,code) VALUES ('Absolute', 'AB')")
c.execute("INSERT INTO Sites (name,code) VALUES ('PartyPoker', 'PP')")
c.execute("INSERT INTO Sites (name,code) VALUES ('PacificPoker', 'P8')")
c.execute("INSERT INTO Sites (name,code) VALUES ('Partouche', 'PA')")
c.execute("INSERT INTO Sites (name,code) VALUES ('Carbon', 'CA')")
c.execute("INSERT INTO Sites (name,code) VALUES ('PKR', 'PK')")
@ -1617,10 +1641,86 @@ class Database:
print err
#end def rebuild_hudcache
def rebuild_sessionscache(self, h_start=None, v_start=None):
"""clears sessionscache and rebuilds from the individual handsplayers records"""
#Will get to this soon
pass
def rebuild_sessionscache(self):
"""clears sessionscache and rebuilds from the individual records"""
heros = []
for site in self.config.get_supported_sites():
result = self.get_site_id(site)
if result:
site_id = result[0][0]
hero = self.config.supported_sites[site].screen_name
p_id = self.get_player_id(self.config, site, hero)
if p_id:
heros.append(int(p_id))
rebuildSessionsCache = self.sql.query['rebuildSessionsCache']
rebuildSessionsCacheSum = self.sql.query['rebuildSessionsCacheSum']
if len(heros) == 0:
where = '0'
where_summary = '0'
elif len(heros) > 0:
where = str(heros[0])
where_summary = str(heros[0])
if len(heros) > 1:
for i in heros:
if i != heros[0]:
where = where + ' OR HandsPlayers.playerId = %s' % str(i)
where_summary = where_summary + ' OR TourneysPlayers.playerId = %s' % str(i)
rebuildSessionsCache = rebuildSessionsCache.replace('<where_clause>', where)
rebuildSessionsCacheSum = rebuildSessionsCacheSum.replace('<where_clause>', where_summary)
c = self.get_cursor()
c.execute(self.sql.query['clearSessionsCache'])
self.commit()
sc, gsc = {'bk': []}, {'bk': []}
c.execute(rebuildSessionsCache)
tmp = c.fetchone()
while True:
pids, game, pdata = {}, {}, {}
pdata['pname'] = {}
id = tmp[0]
startTime = tmp[1]
pids['pname'] = tmp[2]
gid = tmp[3]
game['type'] = tmp[4]
pdata['pname']['totalProfit'] = tmp[5]
pdata['pname']['tourneyTypeId'] = tmp[6]
tmp = c.fetchone()
sc = self.prepSessionsCache (id, pids, startTime, sc , heros, tmp == None)
gsc = self.storeSessionsCache(id, pids, startTime, game, gid, pdata, sc, gsc, None, heros, tmp == None)
if tmp == None:
for i, id in sc.iteritems():
if i!='bk':
sid = id['id']
gid = gsc[i]['id']
c.execute("UPDATE Hands SET sessionId = %s, gameSessionId = %s WHERE id = %s", (sid, gid, i))
break
self.commit()
sc, gsc = {'bk': []}, {'bk': []}
c.execute(rebuildSessionsCacheSum)
tmp = c.fetchone()
while True:
pids, game, info = {}, {}, {}
id = tmp[0]
startTime = tmp[1]
pids['pname'] = tmp[2]
game['type'] = 'summary'
info['tourneyTypeId'] = tmp[3]
info['winnings'] = {}
info['winnings']['pname'] = tmp[4]
info['winningsCurrency'] = {}
info['winningsCurrency']['pname'] = tmp[5]
info['buyinCurrency'] = tmp[6]
info['buyin'] = tmp[7]
info['fee'] = tmp[8]
tmp = c.fetchone()
sc = self.prepSessionsCache (id, pids, startTime, sc , heros, tmp == None)
gsc = self.storeSessionsCache(id, pids, startTime, game, None, info, sc, gsc, None, heros, tmp == None)
if tmp == None:
break
def get_hero_hudcache_start(self):
"""fetches earliest stylekey from hudcache for one of hero's player ids"""
@ -1700,6 +1800,34 @@ class Database:
# however the calling prog requires. Main aims:
# - existing static routines from fpdb_simple just modified
def setThreadId(self, threadid):
self.threadId = threadid
def acquireLock(self, wait=True, retry_time=.01):
while not self._has_lock:
cursor = self.get_cursor()
cursor.execute(self.sql.query['selectLock'])
record = cursor.fetchall()
self.commit()
if not len(record):
cursor.execute(self.sql.query['switchLock'], (True, self.threadId))
self.commit()
self._has_lock = True
return True
else:
cursor.execute(self.sql.query['missedLock'], (1, self.threadId))
self.commit()
if not wait:
return False
sleep(retry_time)
def releaseLock(self):
if self._has_lock:
cursor = self.get_cursor()
num = cursor.execute(self.sql.query['switchLock'], (False, self.threadId))
self.commit()
self._has_lock = False
def lock_for_insert(self):
"""Lock tables in MySQL to try to speed inserts up"""
try:
@ -1712,70 +1840,74 @@ class Database:
# NEWIMPORT CODE
###########################
def storeHand(self, p, printdata = False):
def storeHand(self, hdata, hbulk, doinsert = False, printdata = False):
if printdata:
print _("######## Hands ##########")
import pprint
pp = pprint.PrettyPrinter(indent=4)
pp.pprint(p)
pp.pprint(hdata)
print _("###### End Hands ########")
# Tablename can have odd charachers
p['tableName'] = Charset.to_db_utf8(p['tableName'])
hdata['tableName'] = Charset.to_db_utf8(hdata['tableName'])
#stores into table hands:
q = self.sql.query['store_hand']
q = q.replace('%s', self.sql.query['placeholder'])
c = self.get_cursor()
c.execute(q, (
p['tableName'],
p['siteHandNo'],
p['tourneyId'],
p['gametypeId'],
p['sessionId'],
p['startTime'],
hbulk.append( [ hdata['tableName'],
hdata['siteHandNo'],
hdata['tourneyId'],
hdata['gametypeId'],
hdata['sessionId'],
hdata['gameSessionId'],
hdata['startTime'],
datetime.utcnow(), #importtime
p['seats'],
p['maxSeats'],
p['texture'],
p['playersVpi'],
p['boardcard1'],
p['boardcard2'],
p['boardcard3'],
p['boardcard4'],
p['boardcard5'],
p['playersAtStreet1'],
p['playersAtStreet2'],
p['playersAtStreet3'],
p['playersAtStreet4'],
p['playersAtShowdown'],
p['street0Raises'],
p['street1Raises'],
p['street2Raises'],
p['street3Raises'],
p['street4Raises'],
p['street1Pot'],
p['street2Pot'],
p['street3Pot'],
p['street4Pot'],
p['showdownPot']
))
return self.get_last_insert_id(c)
# def storeHand
hdata['seats'],
hdata['maxSeats'],
hdata['texture'],
hdata['playersVpi'],
hdata['boardcard1'],
hdata['boardcard2'],
hdata['boardcard3'],
hdata['boardcard4'],
hdata['boardcard5'],
hdata['playersAtStreet1'],
hdata['playersAtStreet2'],
hdata['playersAtStreet3'],
hdata['playersAtStreet4'],
hdata['playersAtShowdown'],
hdata['street0Raises'],
hdata['street1Raises'],
hdata['street2Raises'],
hdata['street3Raises'],
hdata['street4Raises'],
hdata['street1Pot'],
hdata['street2Pot'],
hdata['street3Pot'],
hdata['street4Pot'],
hdata['showdownPot'],
hdata['id']
])
def storeHandsPlayers(self, hid, pids, pdata, hp_bulk = None, insert = False, printdata = False):
if doinsert:
for h in hbulk:
id = h.pop()
if hdata['sc'] and hdata['gsc']:
h[4] = hdata['sc'][id]['id']
h[5] = hdata['gsc'][id]['id']
q = self.sql.query['store_hand']
q = q.replace('%s', self.sql.query['placeholder'])
c = self.get_cursor()
c.executemany(q, hbulk)
self.commit()
return hbulk
def storeHandsPlayers(self, hid, pids, pdata, hpbulk, doinsert = False, printdata = False):
#print "DEBUG: %s %s %s" %(hid, pids, pdata)
if printdata:
import pprint
pp = pprint.PrettyPrinter(indent=4)
pp.pprint(pdata)
inserts = []
for p in pdata:
inserts.append( (hid,
hpbulk.append( ( hid,
pids[p],
pdata[p]['startCash'],
pdata[p]['seatNo'],
@ -1787,6 +1919,19 @@ class Database:
pdata[p]['card5'],
pdata[p]['card6'],
pdata[p]['card7'],
pdata[p]['card8'],
pdata[p]['card9'],
pdata[p]['card10'],
pdata[p]['card11'],
pdata[p]['card12'],
pdata[p]['card13'],
pdata[p]['card14'],
pdata[p]['card15'],
pdata[p]['card16'],
pdata[p]['card17'],
pdata[p]['card18'],
pdata[p]['card19'],
pdata[p]['card20'],
pdata[p]['winnings'],
pdata[p]['rake'],
pdata[p]['totalProfit'],
@ -1881,16 +2026,14 @@ class Database:
pdata[p]['street4Raises']
) )
if insert:
hp_bulk += inserts
if doinsert:
q = self.sql.query['store_hands_players']
q = q.replace('%s', self.sql.query['placeholder'])
c = self.get_cursor()
c.executemany(q, hp_bulk)
c.executemany(q, hpbulk)
return hpbulk
return inserts
def storeHandsActions(self, hid, pids, adata, ha_bulk = None, insert = False, printdata = False):
def storeHandsActions(self, hid, pids, adata, habulk, doinsert = False, printdata = False):
#print "DEBUG: %s %s %s" %(hid, pids, adata)
# This can be used to generate test data. Currently unused
@ -1899,9 +2042,8 @@ class Database:
# pp = pprint.PrettyPrinter(indent=4)
# pp.pprint(adata)
inserts = []
for a in adata:
inserts.append( (hid,
habulk.append( (hid,
pids[adata[a]['player']],
adata[a]['street'],
adata[a]['actionNo'],
@ -1915,16 +2057,14 @@ class Database:
adata[a]['allIn']
) )
if insert:
ha_bulk += inserts
if doinsert:
q = self.sql.query['store_hands_actions']
q = q.replace('%s', self.sql.query['placeholder'])
c = self.get_cursor()
c.executemany(q, ha_bulk)
c.executemany(q, habulk)
return habulk
return inserts
def storeHudCache(self, gid, pids, starttime, pdata):
def storeHudCache(self, gid, pids, starttime, pdata, hcbulk, doinsert = False):
"""Update cached statistics. If update fails because no record exists, do an insert."""
tz = datetime.utcnow() - datetime.today()
@ -1947,11 +2087,9 @@ class Database:
insert_hudcache = insert_hudcache.replace('%s', self.sql.query['placeholder'])
#print "DEBUG: %s %s %s" %(hid, pids, pdata)
inserts = []
for p in pdata:
#NOTE: Insert new stats at right place because SQL needs strict order
line = []
line.append(1) # HDs
line.append(pdata[p]['street0VPI'])
line.append(pdata[p]['street0Aggr'])
@ -2041,160 +2179,365 @@ class Database:
line.append(pdata[p]['street3Raises'])
line.append(pdata[p]['street4Raises'])
line.append(gid) # gametypeId
line.append(pids[p]) # playerId
line.append(len(pids)) # activeSeats
hc, hcs = {}, []
hc['gametypeId'] = gid
hc['playerId'] = pids[p]
hc['activeSeats'] = len(pids)
pos = {'B':'B', 'S':'S', 0:'D', 1:'C', 2:'M', 3:'M', 4:'M', 5:'E', 6:'E', 7:'E', 8:'E', 9:'E' }
line.append(pos[pdata[p]['position']])
line.append(pdata[p]['tourneyTypeId'])
line.append(styleKey) # styleKey
inserts.append(line)
hc['position'] = pos[pdata[p]['position']]
hc['tourneyTypeId'] = pdata[p]['tourneyTypeId']
hc['styleKey'] = styleKey
hc['line'] = line
hc['game'] = [hc['gametypeId']
,hc['playerId']
,hc['activeSeats']
,hc['position']
,hc['tourneyTypeId']
,hc['styleKey']]
hcs.append(hc)
for h in hcs:
match = False
for b in hcbulk:
if h['game']==b['game']:
b['line'] = [sum(l) for l in zip(b['line'], h['line'])]
match = True
if not match: hcbulk.append(h)
cursor = self.get_cursor()
for row in inserts:
# Try to do the update first:
num = cursor.execute(update_hudcache, row)
#print "DEBUG: values: %s" % row[-6:]
# Test statusmessage to see if update worked, do insert if not
# num is a cursor in sqlite
if ((self.backend == self.PGSQL and cursor.statusmessage != "UPDATE 1")
if doinsert:
inserts = []
exists = []
updates = []
for hc in hcbulk:
row = hc['line'] + hc['game']
if hc['game'] in exists:
updates.append(row)
continue
c = self.get_cursor()
num = c.execute(update_hudcache, row)
# Try to do the update first. Do insert it did not work
if ((self.backend == self.PGSQL and c.statusmessage != "UPDATE 1")
or (self.backend == self.MYSQL_INNODB and num == 0)
or (self.backend == self.SQLITE and num.rowcount == 0)):
#move the last 6 items in WHERE clause of row from the end of the array
# to the beginning for the INSERT statement
#print "DEBUG: using INSERT: %s" % num
row = row[-6:] + row[:-6]
num = cursor.execute(insert_hudcache, row)
inserts.append(hc['game'] + hc['line'])
#row = hc['game'] + hc['line']
#num = c.execute(insert_hudcache, row)
#print "DEBUG: Successfully(?: %s) updated HudCacho using INSERT" % num
else:
exists.append(hc['game'])
#print "DEBUG: Successfully updated HudCacho using UPDATE"
pass
if inserts: c.executemany(insert_hudcache, inserts)
if updates: c.executemany(update_hudcache, updates)
def storeSessionsCache(self, pids, startTime, game, pdata):
return hcbulk
def prepSessionsCache(self, hid, pids, startTime, sc, heros, doinsert = False):
"""Update cached sessions. If no record exists, do an insert"""
THRESHOLD = timedelta(seconds=int(self.sessionTimeout * 60))
select_sessionscache = self.sql.query['select_sessionscache']
select_sessionscache = select_sessionscache.replace('%s', self.sql.query['placeholder'])
select_sessionscache_mid = self.sql.query['select_sessionscache_mid']
select_sessionscache_mid = select_sessionscache_mid.replace('%s', self.sql.query['placeholder'])
select_sessionscache_start = self.sql.query['select_sessionscache_start']
select_sessionscache_start = select_sessionscache_start.replace('%s', self.sql.query['placeholder'])
select_prepSC = self.sql.query['select_prepSC'].replace('%s', self.sql.query['placeholder'])
update_Hands_sid = self.sql.query['update_Hands_sid'].replace('%s', self.sql.query['placeholder'])
update_SC_sid = self.sql.query['update_SC_sid'].replace('%s', self.sql.query['placeholder'])
update_prepSC = self.sql.query['update_prepSC'].replace('%s', self.sql.query['placeholder'])
update_sessionscache_mid = self.sql.query['update_sessionscache_mid']
update_sessionscache_mid = update_sessionscache_mid.replace('%s', self.sql.query['placeholder'])
update_sessionscache_start = self.sql.query['update_sessionscache_start']
update_sessionscache_start = update_sessionscache_start.replace('%s', self.sql.query['placeholder'])
update_sessionscache_end = self.sql.query['update_sessionscache_end']
update_sessionscache_end = update_sessionscache_end.replace('%s', self.sql.query['placeholder'])
#print "DEBUG: %s %s %s" %(hid, pids, pdata)
hand = {}
for p, id in pids.iteritems():
if id in heros:
hand['startTime'] = startTime.replace(tzinfo=None)
hand['ids'] = []
insert_sessionscache = self.sql.query['insert_sessionscache']
insert_sessionscache = insert_sessionscache.replace('%s', self.sql.query['placeholder'])
merge_sessionscache = self.sql.query['merge_sessionscache']
merge_sessionscache = merge_sessionscache.replace('%s', self.sql.query['placeholder'])
delete_sessions = self.sql.query['delete_sessions']
delete_sessions = delete_sessions.replace('%s', self.sql.query['placeholder'])
if hand:
id = []
lower = hand['startTime']-THRESHOLD
upper = hand['startTime']+THRESHOLD
for i in range(len(sc['bk'])):
if ((lower <= sc['bk'][i]['sessionEnd'])
and (upper >= sc['bk'][i]['sessionStart'])):
if ((hand['startTime'] <= sc['bk'][i]['sessionEnd'])
and (hand['startTime'] >= sc['bk'][i]['sessionStart'])):
id.append(i)
elif hand['startTime'] < sc['bk'][i]['sessionStart']:
sc['bk'][i]['sessionStart'] = hand['startTime']
id.append(i)
elif hand['startTime'] > sc['bk'][i]['sessionEnd']:
sc['bk'][i]['sessionEnd'] = hand['startTime']
id.append(i)
if len(id) == 1:
id = id[0]
sc['bk'][id]['ids'].append(hid)
elif len(id) == 2:
if sc['bk'][id[0]]['startTime'] < sc['bk'][id[1]]['startTime']:
sc['bk'][id[0]]['endTime'] = sc['bk'][id[1]]['endTime']
else:
sc['bk'][id[0]]['startTime'] = sc['bk'][id[1]]['startTime']
sc['bk'].pop[id[1]]
id = id[0]
sc['bk'][id]['ids'].append(hid)
elif len(id) == 0:
hand['id'] = None
hand['sessionStart'] = hand['startTime']
hand['sessionEnd'] = hand['startTime']
id = len(sc['bk'])
hand['ids'].append(hid)
sc['bk'].append(hand)
update_hands_sessionid = self.sql.query['update_hands_sessionid']
update_hands_sessionid = update_hands_sessionid.replace('%s', self.sql.query['placeholder'])
if doinsert:
c = self.get_cursor()
c.execute("SELECT max(sessionId) FROM SessionsCache")
id = c.fetchone()[0]
if id: sid = id
else: sid = 0
for i in range(len(sc['bk'])):
lower = sc['bk'][i]['sessionStart'] - THRESHOLD
upper = sc['bk'][i]['sessionEnd'] + THRESHOLD
c.execute(select_prepSC, (lower, upper))
r = self.fetchallDict(c)
num = len(r)
if (num == 1):
start, end, update = r[0]['sessionStart'], r[0]['sessionEnd'], False
if sc['bk'][i]['sessionStart'] < start:
start, update = sc['bk'][i]['sessionStart'], True
if sc['bk'][i]['sessionEnd'] > end:
end, update = sc['bk'][i]['sessionEnd'], True
if update:
c.execute(update_prepSC, [start, end, r[0]['id']])
for h in sc['bk'][i]['ids']:
sc[h] = {'id': r[0]['id'], 'data': [start, end]}
elif (num > 1):
start, end, merge, merge_h, merge_sc = None, None, [], [], []
sid += 1
r.append(sc['bk'][i])
for n in r:
if start:
if start > n['sessionStart']:
start = n['sessionStart']
else: start = n['sessionStart']
if end:
if end < n['sessionEnd']:
end = n['sessionEnd']
else: end = n['sessionEnd']
for n in r:
if n['id']:
if n['id'] in merge: continue
merge.append(n['id'])
merge_h.append([sid, n['id']])
merge_sc.append([start, end, sid, n['id']])
c.executemany(update_Hands_sid, merge_h)
c.executemany(update_SC_sid, merge_sc)
for k, v in sc.iteritems():
if k!='bk' and v['id'] in merge:
sc[k]['id'] = sid
for h in sc['bk'][i]['ids']:
sc[h] = {'id': sid, 'data': [start, end]}
elif (num == 0):
sid += 1
start = sc['bk'][i]['sessionStart']
end = sc['bk'][i]['sessionEnd']
for h in sc['bk'][i]['ids']:
sc[h] = {'id': sid, 'data': [start, end]}
return sc
def storeSessionsCache(self, hid, pids, startTime, game, gid, pdata, sc, gsc, tz, heros, doinsert = False):
"""Update cached sessions. If no record exists, do an insert"""
if not tz:
tz_dt = datetime.utcnow() - datetime.today()
tz = tz_dt.seconds/3600
THRESHOLD = timedelta(seconds=int(self.sessionTimeout * 60))
local = startTime + timedelta(hours=int(tz))
date = "d%02d%02d%02d" % (local.year - 2000, local.month, local.day)
select_SC = self.sql.query['select_SC'].replace('%s', self.sql.query['placeholder'])
update_SC = self.sql.query['update_SC'].replace('%s', self.sql.query['placeholder'])
insert_SC = self.sql.query['insert_SC'].replace('%s', self.sql.query['placeholder'])
delete_SC = self.sql.query['delete_SC'].replace('%s', self.sql.query['placeholder'])
update_Hands_gsid = self.sql.query['update_Hands_gsid'].replace('%s', self.sql.query['placeholder'])
#print "DEBUG: %s %s %s" %(hid, pids, pdata)
hand = {}
for p, id in pids.iteritems():
if id in heros:
hand['hands'] = 0
hand['totalProfit'] = 0
hand['playerId'] = id
hand['gametypeId'] = None
hand['date'] = date
hand['startTime'] = startTime.replace(tzinfo=None)
hand['hid'] = hid
hand['tourneys'] = 0
hand['tourneyTypeId'] = None
hand['ids'] = []
if (game['type']=='summary'):
hand['type'] = 'tour'
hand['tourneys'] = 1
hand['tourneyTypeId'] = pdata['tourneyTypeId']
if pdata['buyinCurrency'] == pdata['winningsCurrency'][p]:
hand['totalProfit'] = pdata['winnings'][p] - (pdata['buyin'] + pdata['fee'])
else: hand['totalProfit'] = pdata['winnings'][p]
elif (game['type']=='ring'):
hand['type'] = game['type']
hand['hands'] = 1
hand['gametypeId'] = gid
hand['totalProfit'] = pdata[p]['totalProfit']
elif (game['type']=='tour'):
hand['type'] = game['type']
hand['hands'] = 1
hand['tourneyTypeId'] = pdata[p]['tourneyTypeId']
if hand:
id = []
lower = hand['startTime']-THRESHOLD
upper = hand['startTime']+THRESHOLD
for i in range(len(gsc['bk'])):
if ((hand['date'] == gsc['bk'][i]['date'])
and (hand['gametypeId'] == gsc['bk'][i]['gametypeId'])
and (hand['playerId'] == gsc['bk'][i]['playerId'])
and (hand['tourneyTypeId'] == gsc['bk'][i]['tourneyTypeId'])):
if ((lower <= gsc['bk'][i]['gameEnd'])
and (upper >= gsc['bk'][i]['gameStart'])):
if ((hand['startTime'] <= gsc['bk'][i]['gameEnd'])
and (hand['startTime'] >= gsc['bk'][i]['gameStart'])):
gsc['bk'][i]['hands'] += hand['hands']
gsc['bk'][i]['tourneys'] += hand['tourneys']
gsc['bk'][i]['totalProfit'] += hand['totalProfit']
elif hand['startTime'] < gsc['bk'][i]['gameStart']:
gsc['bk'][i]['hands'] += hand['hands']
gsc['bk'][i]['tourneys'] += hand['tourneys']
gsc['bk'][i]['totalProfit'] += hand['totalProfit']
gsc['bk'][i]['gameStart'] = hand['startTime']
elif hand['startTime'] > gsc['bk'][i]['gameEnd']:
gsc['bk'][i]['hands'] += hand['hands']
gsc['bk'][i]['tourneys'] += hand['tourneys']
gsc['bk'][i]['totalProfit'] += hand['totalProfit']
gsc['bk'][i]['gameEnd'] = hand['startTime']
id.append(i)
if len(id) == 1:
gsc['bk'][id[0]]['ids'].append(hid)
elif len(id) == 2:
if gsc['bk'][id[0]]['gameStart'] < gsc['bk'][id[1]]['gameStart']:
gsc['bk'][id[0]]['gameEnd'] = gsc['bk'][id[1]]['gameEnd']
else: gsc['bk'][id[0]]['gameStart'] = gsc['bk'][id[1]]['gameStart']
gsc['bk'][id[0]]['hands'] += hand['hands']
gsc['bk'][id[0]]['tourneys'] += hand['tourneys']
gsc['bk'][id[0]]['totalProfit'] += hand['totalProfit']
gsc['bk'].pop[id[1]]
gsc['bk'][id[0]]['ids'].append(hid)
elif len(id) == 0:
hand['gameStart'] = hand['startTime']
hand['gameEnd'] = hand['startTime']
id = len(gsc['bk'])
hand['ids'].append(hid)
gsc['bk'].append(hand)
if doinsert:
c = self.get_cursor()
for i in range(len(gsc['bk'])):
hid = gsc['bk'][i]['hid']
sid, start, end = sc[hid]['id'], sc[hid]['data'][0], sc[hid]['data'][1]
lower = gsc['bk'][i]['gameStart'] - THRESHOLD
upper = gsc['bk'][i]['gameEnd'] + THRESHOLD
game = [gsc['bk'][i]['date']
,gsc['bk'][i]['type']
,gsc['bk'][i]['gametypeId']
,gsc['bk'][i]['tourneyTypeId']
,gsc['bk'][i]['playerId']]
row = [lower, upper] + game
c.execute(select_SC, row)
r = self.fetchallDict(c)
num = len(r)
if (num == 1):
gstart, gend = r[0]['gameStart'], r[0]['gameEnd']
if gsc['bk'][i]['gameStart'] < gstart:
gstart = gsc['bk'][i]['gameStart']
if gsc['bk'][i]['gameEnd'] > gend:
gend = gsc['bk'][i]['gameEnd']
row = [start, end, gstart, gend
,gsc['bk'][i]['hands']
,gsc['bk'][i]['tourneys']
,gsc['bk'][i]['totalProfit']
,r[0]['id']]
c.execute(update_SC, row)
for h in gsc['bk'][i]['ids']: gsc[h] = {'id': r[0]['id']}
elif (num > 1):
gstart, gend, hands, tourneys, totalProfit, delete, merge = None, None, 0, 0, 0, [], []
for n in r: delete.append(n['id'])
delete.sort()
for d in delete: c.execute(delete_SC, d)
r.append(gsc['bk'][i])
for n in r:
if gstart:
if gstart > n['gameStart']:
gstart = n['gameStart']
else: gstart = n['gameStart']
if gend:
if gend < n['gameEnd']:
gend = n['gameEnd']
else: gend = n['gameEnd']
hands += n['hands']
tourneys += n['tourneys']
totalProfit += n['totalProfit']
row = [start, end, gstart, gend, sid] + game + [hands, tourneys, totalProfit]
c.execute(insert_SC, row)
gsid = self.get_last_insert_id(c)
for h in gsc['bk'][i]['ids']: gsc[h] = {'id': gsid}
for m in delete: merge.append([gsid, m])
c.executemany(update_Hands_gsid, merge)
elif (num == 0):
gstart = gsc['bk'][i]['gameStart']
gend = gsc['bk'][i]['gameEnd']
hands = gsc['bk'][i]['hands']
tourneys = gsc['bk'][i]['tourneys']
totalProfit = gsc['bk'][i]['totalProfit']
row = [start, end, gstart, gend, sid] + game + [hands, tourneys, totalProfit]
c.execute(insert_SC, row)
gsid = self.get_last_insert_id(c)
for h in gsc['bk'][i]['ids']: gsc[h] = {'id': gsid}
else:
# Something bad happened
pass
self.commit()
return gsc
def getHeroIds(self, pids, sitename):
#Grab playerIds using hero names in HUD_Config.xml
try:
# derive list of program owner's player ids
self.hero = {} # name of program owner indexed by site id
self.hero_ids = []
hero = {} # name of program owner indexed by site id
hero_ids = []
# make sure at least two values in list
# so that tuple generation creates doesn't use
# () or (1,) style
for site in self.config.get_supported_sites():
result = self.get_site_id(site)
if result:
site_id = result[0][0]
self.hero[site_id] = self.config.supported_sites[site].screen_name
p_id = self.get_player_id(self.config, site, self.hero[site_id])
if p_id:
self.hero_ids.append(int(p_id))
hero = self.config.supported_sites[site].screen_name
for n, v in pids.iteritems():
if n == hero and sitename == site:
hero_ids.append(v)
except:
err = traceback.extract_tb(sys.exc_info()[2])[-1]
print _("Error aquiring hero ids:"), str(sys.exc_value)
print err
#print _("Error aquiring hero ids:"), str(sys.exc_value)
return hero_ids
inserts = []
for p in pdata:
if pids[p] in self.hero_ids:
line = [0]*5
if (game['type']=='ring'): line[0] = 1 # count ring hands
if (game['type']=='tour'): line[1] = 1 # count tour hands
if (game['type']=='ring' and game['currency']=='USD'): line[2] = pdata[p]['totalProfit'] #sum of ring profit in USD
if (game['type']=='ring' and game['currency']=='EUR'): line[3] = pdata[p]['totalProfit'] #sum of ring profit in EUR
line[4] = startTime
inserts.append(line)
cursor = self.get_cursor()
id = None
for row in inserts:
threshold = []
threshold.append(row[-1]-THRESHOLD)
threshold.append(row[-1]+THRESHOLD)
cursor.execute(select_sessionscache, threshold)
session_records = cursor.fetchall()
num = len(session_records)
if (num == 1):
id = session_records[0][0] #grab the sessionId
# Try to do the update first:
#print "DEBUG: found 1 record to update"
update_mid = row + row[-1:]
cursor.execute(select_sessionscache_mid, update_mid[-2:])
mid = len(cursor.fetchall())
if (mid == 0):
update_startend = row[-1:] + row + threshold
cursor.execute(select_sessionscache_start, update_startend[-3:])
start = len(cursor.fetchall())
if (start == 0):
#print "DEBUG:", start, " start record found. Update stats and start time"
cursor.execute(update_sessionscache_end, update_startend)
else:
#print "DEBUG: 1 end record found. Update stats and end time time"
cursor.execute(update_sessionscache_start, update_startend)
else:
#print "DEBUG: update stats mid-session"
cursor.execute(update_sessionscache_mid, update_mid)
elif (num > 1):
session_ids = [session_records[0][0], session_records[1][0]]
session_ids.sort()
# Multiple matches found - merge them into one session and update:
# - Obtain the session start and end times for the new combined session
cursor.execute(merge_sessionscache, session_ids)
merge = cursor.fetchone()
# - Delete the old records
for id in session_ids:
cursor.execute(delete_sessions, id)
# - Insert the new updated record
cursor.execute(insert_sessionscache, merge)
# - Obtain the new sessionId and write over the old ids in Hands
id = self.get_last_insert_id(cursor) #grab the sessionId
update_hands = [id] + session_ids
cursor.execute(update_hands_sessionid, update_hands)
# - Update the newly combined record in SessionsCache with data from this hand
update_mid = row + row[-1:]
cursor.execute(update_sessionscache_mid, update_mid)
elif (num == 0):
# No matches found, insert new session:
insert = row + row[-1:]
insert = insert[-2:] + insert[:-2]
#print "DEBUG: No matches found. Insert record", insert
cursor.execute(insert_sessionscache, insert)
id = self.get_last_insert_id(cursor) #grab the sessionId
else:
# Something bad happened
pass
def fetchallDict(self, cursor):
data = cursor.fetchall()
if not data: return []
desc = cursor.description
results = [0]*len(data)
for i in range(len(data)):
results[i] = {}
for n in range(len(desc)):
name = desc[n][0]
results[i][name] = data[i][n]
return results
def nextHandId(self):
c = self.get_cursor()
c.execute("SELECT max(id) FROM Hands")
id = c.fetchone()[0]
if not id: id = 0
id += 1
return id
def isDuplicate(self, gametypeID, siteHandNo):

View File

@ -123,6 +123,7 @@ class DerivedStats():
self.hands['siteHandNo'] = hand.handid
self.hands['gametypeId'] = None # Leave None, handled later after checking db
self.hands['sessionId'] = None # Leave None, added later if caching sessions
self.hands['gameSessionId'] = None # Leave None, added later if caching sessions
self.hands['startTime'] = hand.startTime # format this!
self.hands['importTime'] = None
self.hands['seats'] = self.countPlayers(hand)
@ -213,10 +214,10 @@ class DerivedStats():
for player in hand.players:
hcs = hand.join_holecards(player[1], asList=True)
hcs = hcs + [u'0x', u'0x', u'0x', u'0x', u'0x']
#for i, card in enumerate(hcs[:7], 1): #Python 2.6 syntax
hcs = hcs + [u'0x']*18
#for i, card in enumerate(hcs[:20, 1): #Python 2.6 syntax
# self.handsplayers[player[1]]['card%s' % i] = Card.encodeCard(card)
for i, card in enumerate(hcs[:7]):
for i, card in enumerate(hcs[:20]):
self.handsplayers[player[1]]['card%s' % (i+1)] = Card.encodeCard(card)
self.handsplayers[player[1]]['startCards'] = Card.calcStartCards(hand, player[1])

View File

@ -99,12 +99,12 @@ class Everest(HandHistoryConverter):
except AttributeError:
tmp = handText[0:100]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
if not m2:
tmp = handText[0:100]
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise handinfo from: '%s'") % tmp)
self.info = {}
@ -231,8 +231,8 @@ class Everest(HandHistoryConverter):
elif action.group('ATYPE') in ('FOLD', 'SIT_OUT'):
hand.addFold(street, player)
else:
print (_("Unimplemented readAction: '%s' '%s'") % (action.group('PSEAT'),action.group('ATYPE')))
logging.debug(_("Unimplemented readAction: '%s' '%s'") % (action.group('PSEAT'),action.group('ATYPE')))
print (_("Unimplemented readAction: '%s' '%s'") % (action.group('PSEAT'), action.group('ATYPE')))
logging.debug(_("Unimplemented readAction: '%s' '%s'") % (action.group('PSEAT'), action.group('ATYPE')))
def readShowdownActions(self, hand):
for shows in self.re_ShowdownAction.finditer(hand.handText):

View File

@ -41,7 +41,12 @@ class Everleaf(HandHistoryConverter):
#re.compile(ur"^(Blinds )?(?P<CURRENCY>\$| €|)(?P<SB>[.0-9]+)/(?:\$| €)?(?P<BB>[.0-9]+) (?P<LIMIT>NL|PL|) ?(?P<GAME>(Hold\'em|Omaha|7 Card Stud))", re.MULTILINE)
re_HandInfo = re.compile(ur".*#(?P<HID>[0-9]+)\n.*\n(Blinds )?(?P<CURRENCY>[$€])?(?P<SB>[.0-9]+)/(?:[$€])?(?P<BB>[.0-9]+) (?P<GAMETYPE>.*) - (?P<DATETIME>\d\d\d\d/\d\d/\d\d - \d\d:\d\d:\d\d)\nTable (?P<TABLE>.+$)", re.MULTILINE)
re_Button = re.compile(ur"^Seat (?P<BUTTON>\d+) is the button$", re.MULTILINE)
re_PlayerInfo = re.compile(ur"^Seat (?P<SEAT>[0-9]+): (?P<PNAME>.*) \(\s+([$€]? (?P<CASH>[.0-9]+) (USD|EURO|Chips)|new player|All-in) \)$", re.MULTILINE)
re_PlayerInfo = re.compile(ur"""^Seat\s(?P<SEAT>[0-9]+):\s(?P<PNAME>.*)\s+
\(
\s+[$]?\s?(?P<CASH>[.0-9]+)
(\s(USD|EURO|Chips)?(new\splayer|All-in)?)?
\s?\)$
""", re.MULTILINE|re.VERBOSE)
re_Board = re.compile(ur"\[ (?P<CARDS>.+) \]")
re_TourneyInfoFromFilename = re.compile(ur".*TID_(?P<TOURNO>[0-9]+)-(?P<TABLE>[0-9]+)\.txt")
@ -91,8 +96,6 @@ class Everleaf(HandHistoryConverter):
'bigBet'
'currency' in ('USD', 'EUR', 'T$', <countrycode>)
or None if we fail to get the info """
#(TODO: which parts are optional/required?)
# Blinds $0.50/$1 PL Omaha - 2008/12/07 - 21:59:48
# Blinds $0.05/$0.10 NL Hold'em - 2009/02/21 - 11:21:57
# $0.25/$0.50 7 Card Stud - 2008/12/05 - 21:43:59
@ -108,7 +111,7 @@ or None if we fail to get the info """
if not m:
tmp = handText[0:100]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
mg = m.groupdict()
@ -164,11 +167,6 @@ or None if we fail to get the info """
# https://www.poker4ever.com/tourney/%TOURNEY_NUMBER%
# Believe Everleaf time is GMT/UTC, no transation necessary
# Stars format (Nov 10 2008): 2008/11/07 12:38:49 CET [2008/11/07 7:38:49 ET]
# or : 2008/11/07 12:38:49 ET
# Not getting it in my HH files yet, so using
# 2008/11/10 3:58:52 ET
#TODO: Need some date functions to convert to different timezones (Date::Manip for perl rocked for this)
hand.startTime = datetime.datetime.strptime(m.group('DATETIME'), "%Y/%m/%d - %H:%M:%S")
return
@ -187,9 +185,6 @@ or None if we fail to get the info """
def markStreets(self, hand):
# PREFLOP = ** Dealing down cards **
# This re fails if, say, river is missing; then we don't get the ** that starts the river.
#m = re.search('(\*\* Dealing down cards \*\*\n)(?P<PREFLOP>.*?\n\*\*)?( Dealing Flop \*\* \[ (?P<FLOP1>\S\S), (?P<FLOP2>\S\S), (?P<FLOP3>\S\S) \])?(?P<FLOP>.*?\*\*)?( Dealing Turn \*\* \[ (?P<TURN1>\S\S) \])?(?P<TURN>.*?\*\*)?( Dealing River \*\* \[ (?P<RIVER1>\S\S) \])?(?P<RIVER>.*)', hand.handText,re.DOTALL)
if hand.gametype['base'] == 'hold':
m = re.search(r"\*\* Dealing down cards \*\*(?P<PREFLOP>.+(?=\*\* Dealing Flop \*\*)|.+)"
r"(\*\* Dealing Flop \*\*(?P<FLOP> \[ \S\S, \S\S, \S\S \].+(?=\*\* Dealing Turn \*\*)|.+))?"
@ -285,7 +280,7 @@ or None if we fail to get the info """
elif action.group('ATYPE') == ' complete to':
hand.addComplete( street, action.group('PNAME'), action.group('BET'))
else:
logging.debug(_("Unimplemented readAction: %s %s") % (action.group('PNAME'),action.group('ATYPE')))
logging.debug(_("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'), action.group('ATYPE')))
def readShowdownActions(self, hand):

View File

@ -25,7 +25,6 @@ import datetime
from Exceptions import FpdbParseError
from HandHistoryConverter import *
import PokerStarsToFpdb
from TourneySummary import *
class FullTiltPokerSummary(TourneySummary):
@ -46,7 +45,7 @@ class FullTiltPokerSummary(TourneySummary):
substitutions = {
'LEGAL_ISO' : "USD|EUR|GBP|CAD|FPP", # legal ISO currency codes
'LS' : "\$|\xe2\x82\xac|", # legal currency symbols - Euro(cp1252, utf-8)
'LS' : u"\$|\xe2\x82\xac|\u20ac|", # legal currency symbols - Euro(cp1252, utf-8)
'TAB' : u"-\u2013'\s\da-zA-Z", # legal characters for tablename
'NUM' : u".,\d", # legal characters in number format
}
@ -90,8 +89,8 @@ class FullTiltPokerSummary(TourneySummary):
m = self.re_TourneyInfo.search(self.summaryText[:2000])
if m == None:
tmp = self.summaryText[0:200]
log.error(_("parseSummary: Unable to recognise Tourney Info: '%s'") % tmp)
log.error(_("parseSummary: Raising FpdbParseError"))
log.error("parseSummary: " + _("Unable to recognise Tourney Info: '%s'") % tmp)
log.error("parseSummary: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise Tourney Info: '%s'") % tmp)
#print "DEBUG: m.groupdict(): %s" % m.groupdict()
@ -116,8 +115,8 @@ class FullTiltPokerSummary(TourneySummary):
m = self.re_Currency.search(self.summaryText)
if m == None:
log.error(_("parseSummary: Unable to locate currency"))
log.error(_("parseSummary: Raising FpdbParseError"))
log.error("parseSummary: " + _("Unable to locate currency"))
log.error("parseSummary: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to locate currency"))
#print "DEBUG: m.groupdict(): %s" % m.groupdict()

View File

@ -37,7 +37,7 @@ class Fulltilt(HandHistoryConverter):
substitutions = {
'LEGAL_ISO' : "USD|EUR|GBP|CAD|FPP", # legal ISO currency codes
'LS' : u"\$|\u20AC|\xe2\x82\xac|", # legal currency symbols - Euro(cp1252, utf-8)
'TAB' : u"-\u2013'\s\da-zA-Z", # legal characters for tablename
'TAB' : u"-\u2013'\s\da-zA-Z#_", # legal characters for tablename
'NUM' : u".,\d", # legal characters in number format
}
@ -61,7 +61,9 @@ class Fulltilt(HandHistoryConverter):
'400.00': ('100.00', '200.00'), '400': ('100.00', '200.00'),
'500.00': ('125.00', '250.00'), '500': ('125.00', '250.00'),
'800.00': ('200.00', '400.00'), '800': ('200.00', '400.00'),
'1000.00': ('250.00', '500.00'),'1000': ('250.00', '500.00')
'1000.00': ('250.00', '500.00'),'1000': ('250.00', '500.00'),
'2000.00': ('500.00', '750.00'),'2000': ('500.00', '1000.00'),
'3000.00': ('750.00', '1500.00'),'3000': ('750.00', '1500.00'),
}
# Static regexes
@ -74,7 +76,7 @@ class Fulltilt(HandHistoryConverter):
(Ante\s\$?(?P<ANTE>[%(NUM)s]+)\s)?-\s
[%(LS)s]?(?P<CAP>[%(NUM)s]+\sCap\s)?
(?P<LIMIT>(No\sLimit|Pot\sLimit|Limit))?\s
(?P<GAME>(Hold\'em|Omaha(\sH/L|\sHi/Lo|\sHi|)|7\sCard\sStud|Stud\sH/L|Razz|Stud\sHi|2-7\sTriple\sDraw|5\sCard\sDraw|Badugi))
(?P<GAME>(Hold\'em|Omaha(\sH/L|\sHi/Lo|\sHi|)|7\sCard\sStud|Stud\sH/L|Razz|Stud\sHi|2-7\sTriple\sDraw|5\sCard\sDraw|Badugi|2-7\sSingle\sDraw))
''' % substitutions, re.VERBOSE)
re_SplitHands = re.compile(r"\n\n\n+")
re_TailSplitHands = re.compile(r"(\n\n+)")
@ -172,7 +174,7 @@ class Fulltilt(HandHistoryConverter):
self.re_BringIn = re.compile(r"^%(PLAYERS)s brings in for [%(LS)s]?(?P<BRINGIN>[%(NUM)s]+)" % self.substitutions, re.MULTILINE)
self.re_PostBoth = re.compile(r"^%(PLAYERS)s posts small \& big blinds \[[%(LS)s]? (?P<SBBB>[%(NUM)s]+)" % 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"^%(PLAYERS)s(?P<ATYPE> bets| checks| raises to| completes it to| calls| folds)( [%(LS)s]?(?P<BET>[%(NUM)s]+))?" % self.substitutions, re.MULTILINE)
self.re_Action = re.compile(r"^%(PLAYERS)s(?P<ATYPE> bets| checks| raises to| completes it to| calls| folds| discards| stands pat)( [%(LS)s]?(?P<BET>[%(NUM)s]+))?(\son|\scards?)?(\s\[(?P<CARDS>.+?)\])?" % 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]+): %(PLAYERS)s (\(button\) |\(small blind\) |\(big blind\) )?(collected|showed \[.*\] and won) \([%(LS)s]?(?P<POT>[%(NUM)s]+)\)(, mucked| with.*)?" % self.substitutions, re.MULTILINE)
self.re_SitsOut = re.compile(r"^%s sits out" % player_re, re.MULTILINE)
@ -204,7 +206,7 @@ class Fulltilt(HandHistoryConverter):
if not m:
tmp = handText[0:100]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError for file '%s'") % self.in_path)
log.error("determineGameType: " + _("Raising FpdbParseError for file '%s'") % self.in_path)
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
mg = m.groupdict()
@ -222,6 +224,7 @@ class Fulltilt(HandHistoryConverter):
'2-7 Triple Draw' : ('draw','27_3draw'),
'5 Card Draw' : ('draw','fivedraw'),
'Badugi' : ('draw','badugi'),
'2-7 Single Draw' : ('draw','27_1draw')
}
currencies = { u'':'EUR', '$':'USD', '':'T$' }
@ -241,11 +244,12 @@ class Fulltilt(HandHistoryConverter):
if info['limitType'] == 'fl' and info['bb'] is not None and info['type'] == 'ring':
try:
info['sb'] = self.Lim_Blinds[mg['BB']][0]
info['bb'] = self.Lim_Blinds[mg['BB']][1]
bb = self.clearMoneyString(mg['BB'])
info['sb'] = self.Lim_Blinds[bb][0]
info['bb'] = self.Lim_Blinds[bb][1]
except KeyError:
log.error(_("Lim_Blinds has no lookup for '%s'") % mg['BB'])
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Lim_Blinds has no lookup for '%s'") % mg['BB'])
if mg['GAME'] is not None:
@ -362,7 +366,7 @@ class Fulltilt(HandHistoryConverter):
if plist == {}:
#No players! The hand is either missing stacks or everyone is sitting out
raise FpdbParseError(_("FTP: readPlayerStacks: No players detected (hand #%s)") % hand.handid)
raise FpdbParseError(_("readPlayerStacks: No players detected (hand #%s)") % hand.handid)
def markStreets(self, hand):
@ -422,14 +426,14 @@ class Fulltilt(HandHistoryConverter):
logging.debug(_("Player bringing in: %s for %s") %(m.group('PNAME'), m.group('BRINGIN')))
hand.addBringIn(m.group('PNAME'), m.group('BRINGIN'))
else:
logging.warning(_("No bringin found, handid =%s") % hand.handid)
logging.debug(_("No bringin found, handid =%s") % hand.handid)
def readButton(self, hand):
try:
hand.buttonpos = int(self.re_Button.search(hand.handText).group('BUTTON'))
except AttributeError, e:
# FTP has no indication that a hand is cancelled.
raise FpdbParseError(_("FTP: readButton: Failed to detect button (hand #%s cancelled?)") % hand.handid)
raise FpdbParseError(_("readButton: Failed to detect button (hand #%s cancelled?)") % hand.handid)
def readHeroCards(self, hand):
# streets PREFLOP, PREDRAW, and THIRD are special cases beacause
@ -482,8 +486,12 @@ class Fulltilt(HandHistoryConverter):
hand.addFold( street, action.group('PNAME'))
elif action.group('ATYPE') == ' checks':
hand.addCheck( street, action.group('PNAME'))
elif action.group('ATYPE') == ' discards':
hand.addDiscard(street, action.group('PNAME'), action.group('BET'), action.group('CARDS'))
elif action.group('ATYPE') == ' stands pat':
hand.addStandsPat( street, action.group('PNAME'), action.group('CARDS'))
else:
print _("FullTilt: DEBUG: unimplemented readAction: '%s' '%s'") %(action.group('PNAME'),action.group('ATYPE'),)
print (_("DEBUG: ") + " " + _("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'), action.group('ATYPE')))
def readShowdownActions(self, hand):
@ -760,7 +768,7 @@ class Fulltilt(HandHistoryConverter):
tourney.addPlayer(rank, a.group('PNAME'), winnings, "USD", 0, 0, 0) #TODO: make it store actual winnings currency
else:
print (_("FullTilt: Player finishing stats unreadable : %s") % a)
print (_("Player finishing stats unreadable : %s") % a)
# Find Hero
n = self.re_TourneyHeroFinishingP.search(playersText)
@ -769,9 +777,9 @@ class Fulltilt(HandHistoryConverter):
tourney.hero = heroName
# Is this really useful ?
if heroName not in tourney.ranks:
print (_("FullTilt: %s not found in tourney.ranks ...") % heroName)
print (_("%s not found in tourney.ranks ...") % heroName)
elif (tourney.ranks[heroName] != Decimal(n.group('HERO_FINISHING_POS'))):
print (_("FullTilt: Bad parsing : finish position incoherent : %s / %s") % (tourney.ranks[heroName], n.group('HERO_FINISHING_POS')))
print (_("Bad parsing : finish position incoherent : %s / %s") % (tourney.ranks[heroName], n.group('HERO_FINISHING_POS')))
return True

View File

@ -107,7 +107,7 @@ class GuiImapFetcher (threading.Thread):
def displayConfig(self):
box=gtk.HBox(homogeneous=True)
for text in (_("Site"), _("Fetch Type"), _("Mailserver"), _("Username"), _("Password"), _("Mail Folder"), _("Use SSL")):
for text in (_("Site"), _("Fetch Type"), _("Mail Server"), _("Username"), _("Password"), _("Mail Folder"), _("Use SSL")):
label=gtk.Label(text)
box.add(label)
self.mainVBox.pack_start(box, expand=False)

View File

@ -223,13 +223,18 @@ class SummaryImporter:
print "Found %s summaries" %(len(summaryTexts))
errors = 0
imported = 0
####Lock Placeholder####
for j, summaryText in enumerate(summaryTexts, start=1):
sc, gsc = {'bk': []}, {'bk': []}
doinsert = len(summaryTexts)==j
try:
conv = obj(db=None, config=self.config, siteName=site, summaryText=summaryText, builtFrom = "IMAP")
conv = obj(db=self.database, config=self.config, siteName=site, summaryText=summaryText, builtFrom = "IMAP")
sc, gsc = conv.updateSessionsCache(sc, gsc, None, doinsert)
except FpdbParseError, e:
errors += 1
print _("Finished importing %s/%s tournament summaries") %(j, len(summaryTexts))
imported = j
####Lock Placeholder####
return (imported - errors, errors)
def clearFileList(self):

View File

@ -2,7 +2,7 @@
<FreePokerToolsConfig xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="FreePokerToolsConfig.xsd">
<import callFpdbHud = "True" interval = "10" fastStoreHudCache="False" hhArchiveBase="~/.fpdb/HandHistories/" saveActions="True" cacheSessions="True" sessionTimeout="30"></import>
<import callFpdbHud = "True" interval = "10" fastStoreHudCache="False" saveActions="True" cacheSessions="True" sessionTimeout="30"></import>
<!-- These values determine what stats are displayed in the HUD
@ -389,6 +389,49 @@ Left-Drag to Move"
</layout>
</site>
<site enabled="True"
site_name="PacificPoker"
table_finder="poker.exe"
screen_name="Hero"
site_path="C:/Games/Poker/PacificPoker"
HH_path="C:/Users/rwielinga/AppData/Roaming/PacificPoker/HandHistory/Hero/"
decoder="everleaf_decode_table"
converter="PacificPokerToFpdb"
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 enabled="True"
site_name="Betfair"
@ -754,6 +797,7 @@ Left-Drag to Move"
<hhc site="Win2day" converter="Win2dayToFpdb"/>
<hhc site="Absolute" converter="AbsoluteToFpdb"/>
<hhc site="PartyPoker" converter="PartyPokerToFpdb"/>
<hhc site="PacificPoker" converter="PacificPokerToFpdb"/>
<hhc site="Betfair" converter="BetfairToFpdb"/>
<hhc site="OnGame" converter="OnGameToFpdb"/>
<hhc site="Carbon" converter="CarbonToFpdb"/>

View File

@ -12,7 +12,7 @@
config_difficulty="expert"
/>
<import callFpdbHud = "True" interval = "10" fastStoreHudCache="False" hhArchiveBase="~/.fpdb/HandHistories/" saveActions="True" cacheSessions="False" sessionTimeout="30"></import>
<import callFpdbHud = "True" interval = "10" fastStoreHudCache="False" saveActions="True" cacheSessions="False" sessionTimeout="30"></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" />

View File

@ -47,7 +47,7 @@ class Hand(object):
# Class Variables
UPS = {'a':'A', 't':'T', 'j':'J', 'q':'Q', 'k':'K', 'S':'s', 'C':'c', 'H':'h', 'D':'d'}
LCS = {'H':'h', 'D':'d', 'C':'c', 'S':'s'}
SYMBOL = {'USD': '$', 'EUR': u'$', 'GBP': '$', 'T$': '', 'play': ''}
SYMBOL = {'USD': '$', 'CAD': '$', 'EUR': u'$', 'GBP': '$', 'T$': '', 'play': ''}
MS = {'horse' : 'HORSE', '8game' : '8-Game', 'hose' : 'HOSE', 'ha': 'HA'}
ACTION = {'ante': 1, 'small blind': 2, 'secondsb': 3, 'big blind': 4, 'both': 5, 'calls': 6, 'raises': 7,
'bets': 8, 'stands pat': 9, 'folds': 10, 'checks': 11, 'discards': 12, 'bringin': 13, 'completes': 14}
@ -57,6 +57,7 @@ class Hand(object):
#log.debug( _("Hand.init(): handText is ") + str(handText) )
self.config = config
self.saveActions = self.config.get_import_parameters().get('saveActions')
self.callHud = self.config.get_import_parameters().get("callFpdbHud")
self.cacheSessions = self.config.get_import_parameters().get("cacheSessions")
#log = Configuration.get_logger("logging.conf", "db", log_dir=self.config.dir_log)
self.sitename = sitename
@ -101,7 +102,7 @@ class Hand(object):
self.seating = []
self.players = []
self.posted = []
self.tourneysPlayersIds = []
self.tourneysPlayersIds = {}
# Collections indexed by street names
self.bets = {}
@ -232,9 +233,8 @@ dealt whether they were seen in a 'dealt to' line
# Players, Gametypes, TourneyTypes are all shared functions that are needed for additional tables
# These functions are intended for prep insert eventually
#####
# Players - base playerid and siteid tuple
self.dbid_pids = db.getSqlPlayerIDs([p[1] for p in self.players], self.siteId)
self.dbid_gt = db.getGameTypeId(self.siteId, self.gametype, printdata = printtest)
#Gametypes
hilo = "h"
if self.gametype['category'] in ['studhilo', 'omahahilo']:
@ -252,58 +252,67 @@ dealt whether they were seen in a 'dealt to' line
if self.tourNo!=None:
self.tourneyTypeId = db.createTourneyType(self)
db.commit()
self.tourneyId = db.createOrUpdateTourney(self, "HHC")
db.commit()
self.tourneysPlayersIds = db.createOrUpdateTourneysPlayers(self, "HHC")
db.commit()
#end def prepInsert
def insert(self, db, hp_data = None, ha_data = None, insert_data=False, printtest = False):
""" Function to insert Hand into database
Should not commit, and do minimal selects. Callers may want to cache commits
db: a connected Database object"""
#db.commit() #commit these transactions'
def assembleHand(self):
self.stats.getStats(self)
self.hands = self.stats.getHands()
self.handsplayers = self.stats.getHandsPlayers()
#####
# End prep functions
#####
hh = self.stats.getHands()
hp_inserts, ha_inserts = [], []
if not db.isDuplicate(self.dbid_gt, hh['siteHandNo']):
# Hands - Summary information of hand indexed by handId - gameinfo
hh['gametypeId'] = self.dbid_gt
# seats TINYINT NOT NULL,
hh['seats'] = len(self.dbid_pids)
hp = self.stats.getHandsPlayers()
if self.cacheSessions:
hh['sessionId'] = db.storeSessionsCache(self.dbid_pids, self.startTime, self.gametype, hp)
self.dbid_hands = db.storeHand(hh, printdata = printtest)
hp_inserts = db.storeHandsPlayers(self.dbid_hands, self.dbid_pids, hp,
insert=insert_data, hp_bulk = hp_data, printdata = printtest)
if self.saveActions:
ha_inserts = db.storeHandsActions(self.dbid_hands, self.dbid_pids, self.stats.getHandsActions(),
insert=insert_data, ha_bulk = ha_data, printdata = printtest)
else:
log.info(_("Hand.insert(): hid #: %s is a duplicate") % hh['siteHandNo'])
def getHandId(self, db, id):
if db.isDuplicate(self.dbid_gt, self.hands['siteHandNo']):
#log.info(_("Hand.insert(): hid #: %s is a duplicate") % hh['siteHandNo'])
self.is_duplicate = True # i.e. don't update hudcache
raise FpdbHandDuplicate(hh['siteHandNo'])
next = id
raise FpdbHandDuplicate(self.hands['siteHandNo'])
else:
self.dbid_hands = id
self.hands['id'] = self.dbid_hands
next = id +1
return next
return hp_inserts, ha_inserts
def insertHands(self, db, hbulk, doinsert = False, printtest = False):
""" Function to insert Hand into database
Should not commit, and do minimal selects. Callers may want to cache commits
db: a connected Database object"""
self.hands['gametypeId'] = self.dbid_gt
self.hands['seats'] = len(self.dbid_pids)
hbulk = db.storeHand(self.hands, hbulk, doinsert, printtest)
return hbulk
def updateHudCache(self, db):
db.storeHudCache(self.dbid_gt, self.dbid_pids, self.startTime, self.stats.getHandsPlayers())
def insertHandsPlayers(self, db, hpbulk, doinsert = False, printtest = False):
""" Function to inserts HandsPlayers into database"""
hpbulk = db.storeHandsPlayers(self.dbid_hands, self.dbid_pids, self.handsplayers, hpbulk, doinsert, printtest)
return hpbulk
def updateSessionsCache(self, db):
db.storeSessionsCache(self.dbid_pids, self.startTime, self.gametype, self.stats.getHandsPlayers())
def insertHandsActions(self, db, habulk, doinsert = False, printtest = False):
""" Function to inserts HandsActions into database"""
handsactions = self.stats.getHandsActions()
habulk = db.storeHandsActions(self.dbid_hands, self.dbid_pids, handsactions, habulk, doinsert, printtest)
return habulk
def updateHudCache(self, db, hcbulk, doinsert = False):
""" Function to update the HudCache"""
if self.callHud:
hcbulk = db.storeHudCache(self.dbid_gt, self.dbid_pids, self.startTime, self.handsplayers, hcbulk, doinsert)
return hcbulk
def updateSessionsCache(self, db, sc, gsc, tz, doinsert = False):
""" Function to update the SessionsCache"""
if self.cacheSessions:
self.heros = db.getHeroIds(self.dbid_pids, self.sitename)
sc = db.prepSessionsCache(self.dbid_hands, self.dbid_pids, self.startTime, sc, self.heros, doinsert)
gsc = db.storeSessionsCache(self.dbid_hands, self.dbid_pids, self.startTime, self.gametype
,self.dbid_gt, self.handsplayers, sc, gsc, tz, self.heros, doinsert)
if doinsert and sc['bk'] and gsc['bk']:
self.hands['sc'] = sc
self.hands['gsc'] = gsc
else:
self.hands['sc'] = None
self.hands['gsc'] = None
return sc, gsc
def select(self, db, handId):
""" Function to create Hand object from database """
@ -666,10 +675,13 @@ Add a raise on [street] by [player] to [amountTo]
self.pot.addMoney(player, amount)
def addStandsPat(self, street, player):
def addStandsPat(self, street, player, cards):
self.checkPlayerExists(player)
act = (player, 'stands pat')
self.actions[street].append(act)
if cards:
cards = cards.split(' ')
self.addHoleCards(street, player, open=[], closed=cards)
def addFold(self, street, player):
@ -1229,7 +1241,14 @@ class DrawHand(Hand):
def join_holecards(self, player, asList=False):
"""With asList = True it returns the set cards for a player including down cards if they aren't know"""
# FIXME: This should actually return
holecards = [u'0x', u'0x', u'0x', u'0x', u'0x']
holecards = [u'0x']*20
for i, street in enumerate(self.holeStreets):
if player in self.holecards[street].keys():
allhole = self.holecards[street][player][1] + self.holecards[street][player][0]
for c in range(len(allhole)):
idx = c + (i*5)
holecards[idx] = allhole[c]
if asList == False:
return " ".join(holecards)

View File

@ -50,9 +50,6 @@ import Hand
from Exceptions import FpdbParseError
import Configuration
import pygtk
import gtk
class HandHistoryConverter():
READ_CHUNK_SIZE = 10000 # bytes to read at a time from file in tail mode
@ -128,9 +125,6 @@ If in follow mode, wait for more data to turn up.
Otherwise, finish at EOF.
"""
while gtk.events_pending():
gtk.main_iteration(False)
starttime = time.time()
if not self.sanityCheck():
log.warning(_("Failed sanity check"))
@ -183,6 +177,11 @@ Otherwise, finish at EOF.
if self.out_fh != sys.stdout:
self.out_fh.close()
def progressNotify(self):
"A callback to the interface while events are pending"
import gtk, pygtk
while gtk.events_pending():
gtk.main_iteration(False)
def tailHands(self):
"""Generator of handTexts from a tailed file:
@ -460,24 +459,8 @@ or None if we fail to get the info """
def sanityCheck(self):
"""Check we aren't going to do some stupid things"""
#TODO: the hhbase stuff needs to be in fpdb_import
sane = False
base_w = False
#~ #Check if hhbase exists and is writable
#~ #Note: Will not try to create the base HH directory
#~ if not (os.access(self.hhbase, os.W_OK) and os.path.isdir(self.hhbase)):
#~ print "HH Sanity Check: Directory hhbase '" + self.hhbase + "' doesn't exist or is not writable"
#~ else:
#~ #Check if hhdir exists and is writable
#~ if not os.path.isdir(self.hhdir):
#~ # In first pass, dir may not exist. Attempt to create dir
#~ print "Creating directory: '%s'" % (self.hhdir)
#~ os.mkdir(self.hhdir)
#~ sane = True
#~ elif os.access(self.hhdir, os.W_OK):
#~ sane = True
#~ else:
#~ print "HH Sanity Check: Directory hhdir '" + self.hhdir + "' or its parent directory are not writable"
# Make sure input and output files are different or we'll overwrite the source file
if True: # basically.. I don't know

View File

@ -42,7 +42,7 @@ class OnGame(HandHistoryConverter):
siteId = 5 # Needs to match id entry in Sites database
mixes = { } # Legal mixed games
sym = {'USD': "\$", 'CAD': "\$", 'T$': "", "EUR": u"\u20ac", "GBP": "\xa3"} # ADD Euro, Sterling, etc HERE
sym = {'USD': "\$", 'CAD': "\$", 'T$': "", "EUR": u"\u20ac", "GBP": "\xa3"}
substitutions = {
'LEGAL_ISO' : "USD|EUR|GBP|CAD|FPP", # legal ISO currency codes
'LS' : u"\$|\xe2\x82\xac|\u20ac" # legal currency symbols - Euro(cp1252, utf-8)
@ -71,9 +71,11 @@ class OnGame(HandHistoryConverter):
#TODO: detect play money
# "Play money" rather than "Real money" and set currency accordingly
re_HandInfo = re.compile(u"""
\*\*\*\*\*\sHistory\sfor\shand\s(?P<HID>[-A-Z\d]+).*
\*\*\*\*\*\sHistory\sfor\shand\s(?P<HID>[-A-Z\d]+)
(\s\(TOURNAMENT:\s"[a-zA-Z ]+",\s(?P<TID>[-A-Z\d]+),\sbuy-in:\s[%(LS)s](?P<BUYIN>\d+))?
.*
Start\shand:\s(?P<DATETIME>.*)
Table:\s(\[SPEED\]\s)?(?P<TABLE>[-\'\w\s\.]+)\s\[\d+\]\s\(
Table:\s(\[SPEED\]\s)?(?P<TABLE>[-\'\w\#\s\.]+)\s\[\d+\]\s\(
(
(?P<LIMIT>NO_LIMIT|Limit|LIMIT|Pot\sLimit|POT_LIMIT)\s
(?P<GAME>TEXAS_HOLDEM|OMAHA_HI|SEVEN_CARD_STUD|SEVEN_CARD_STUD_HI_LO|RAZZ|FIVE_CARD_DRAW)\s
@ -99,6 +101,7 @@ class OnGame(HandHistoryConverter):
#Seat 1: .Lucchess ($4.17 in chips)
#Seat 1: phantomaas ($27.11)
#Seat 5: mleo17 ($9.37)
#Seat 2: Montferat (1500)
re_PlayerInfo = re.compile(u'Seat (?P<SEAT>[0-9]+):\s(?P<PNAME>.*)\s\((%(LS)s)?(?P<CASH>[.0-9]+)\)' % substitutions)
def compilePlayerRegexs(self, hand):
@ -146,6 +149,7 @@ class OnGame(HandHistoryConverter):
["ring", "hold", "nl"],
["ring", "stud", "fl"],
["ring", "draw", "fl"],
["tour", "hold", "nl"],
]
def determineGameType(self, handText):
@ -157,13 +161,16 @@ class OnGame(HandHistoryConverter):
if not m:
tmp = handText[0:100]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
mg = m.groupdict()
#print "DEBUG: mg: %s" % mg
info['type'] = 'ring'
if mg['TID'] != None:
info['type'] = 'tour'
if 'CURRENCY' in mg:
info['currency'] = self.currencies[mg['CURRENCY']]
@ -173,7 +180,7 @@ class OnGame(HandHistoryConverter):
else:
tmp = handText[0:100]
log.error(_("limit not found in self.limits(%s). hand: '%s'") % (str(mg),tmp))
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("limit not found in self.limits(%s). hand: '%s'") % (str(mg),tmp))
if 'GAME' in mg:
(info['base'], info['category']) = self.games[mg['GAME']]
@ -216,6 +223,10 @@ class OnGame(HandHistoryConverter):
# Need to remove non-alphanumerics for MySQL
hand.handid = hand.handid.replace('R','')
hand.handid = hand.handid.replace('-','')
if key == 'TID':
hand.tourNo = info[key]
if key == 'BUYIN':
hand.buyin = info[key]
if key == 'TABLE':
hand.tablename = info[key]

View File

@ -83,6 +83,7 @@ def site_alias(alias):
"""Function for converting various site aliases to the FPDB name"""
tmp = alias
aliases = {
"PacificPoker" : "PacificPoker",
"PokerStars" : "PokerStars",
"Full Tilt Poker": "Full Tilt Poker",
"PartyPoker" : "PartyPoker",

View File

@ -0,0 +1,467 @@
#!/usr/bin/env python
# -*- coding: utf-8 -*-
#
# Copyright 2008-2010, Carl Gherardi
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# 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 General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
########################################################################
import L10n
_ = L10n.get_translation()
# TODO: straighten out discards for draw games
import sys
from HandHistoryConverter import *
from decimal_wrapper import Decimal
# PacificPoker HH Format
class PacificPoker(HandHistoryConverter):
# Class Variables
sitename = "PacificPoker"
filetype = "text"
codepage = ("utf8", "cp1252")
siteId = 13 # Needs to match id entry in Sites database
mixes = { 'HORSE': 'horse', '8-Game': '8game', 'HOSE': 'hose'} # Legal mixed games
sym = {'USD': "\$", 'CAD': "\$", 'T$': "", "EUR": "\xe2\x82\xac", "GBP": "\xa3", "play": ""} # ADD Euro, Sterling, etc HERE
substitutions = {
'LEGAL_ISO' : "USD|EUR|GBP|CAD|FPP", # legal ISO currency codes
'LS' : u"\$|\xe2\x82\xac|\u20ac|" # legal currency symbols - Euro(cp1252, utf-8)
}
# translations from captured groups to fpdb info strings
# :: TODO 0.02 limit does not seem right
Lim_Blinds = { '0.02': ('0.01', '0.02'), '0.04': ('0.01', '0.02'),
'0.10': ('0.02', '0.05'), '0.20': ('0.05', '0.10'),
'0.40': ('0.10', '0.20'), '0.50': ('0.10', '0.25'),
'1.00': ('0.25', '0.50'), '1': ('0.25', '0.50'),
'2.00': ('0.50', '1.00'), '2': ('0.50', '1.00'),
'4.00': ('1.00', '2.00'), '4': ('1.00', '2.00'),
'6.00': ('1.00', '3.00'), '6': ('1.00', '3.00'),
'8.00': ('2.00', '4.00'), '8': ('2.00', '4.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'),
'40.00': ('10.00', '20.00'), '40': ('10.00', '20.00'),
'60.00': ('15.00', '30.00'), '60': ('15.00', '30.00'),
'80.00': ('20.00', '40.00'), '80': ('20.00', '40.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'),
'800.00': ('200.00', '400.00'), '800': ('200.00', '400.00'),
'1000.00': ('250.00', '500.00'),'1000': ('250.00', '500.00')
}
limits = { 'No Limit':'nl', 'Pot Limit':'pl', 'Limit':'fl', 'LIMIT':'fl', 'Fix Limit':'fl' }
games = { # base, category
"Holdem" : ('hold','holdem'),
'Omaha' : ('hold','omahahi'),
'Omaha Hi/Lo' : ('hold','omahahilo'),
'OmahaHL' : ('hold','omahahilo'),
'Razz' : ('stud','razz'),
'RAZZ' : ('stud','razz'),
'7 Card Stud' : ('stud','studhi'),
'7 Card Stud Hi/Lo' : ('stud','studhilo'),
'Badugi' : ('draw','badugi'),
'Triple Draw 2-7 Lowball' : ('draw','27_3draw'),
'Single Draw 2-7 Lowball' : ('draw','27_1draw'),
'5 Card Draw' : ('draw','fivedraw')
}
currencies = { u'':'EUR', '$':'USD', '':'T$' }
# Static regexes
re_GameInfo = re.compile(u"""
\#Game\sNo\s:\s(?P<HID>[0-9]+)\\n
\*\*\*\*\*\sCassava\sHand\sHistory\sfor\sGame\s[0-9]+\s\*\*\*\*\*\\n
(?P<CURRENCY>%(LS)s)?(?P<SB>[.,0-9]+)/(%(LS)s)?(?P<BB>[.,0-9]+)\sBlinds\s
(?P<LIMIT>No\sLimit|Fix\sLimit|Pot\sLimit)\s
(?P<GAME>Holdem|Omaha|OmahaHL)
\s-\s\*\*\*\s
(?P<DATETIME>.*$)
""" % substitutions, re.MULTILINE|re.VERBOSE)
re_PlayerInfo = re.compile(u"""
^Seat\s(?P<SEAT>[0-9]+):\s
(?P<PNAME>.*)\s
\(\s(%(LS)s)?(?P<CASH>[.,0-9]+)\s\)""" % substitutions,
re.MULTILINE|re.VERBOSE)
re_HandInfo = re.compile("""
^Table\s(?P<TABLE>[-\ \#a-zA-Z\d]+)\s
(\(Real\sMoney\))?
(?P<PLAY>\(Practice\sPlay\))?
\\n
Seat\s(?P<BUTTON>[0-9]+)\sis\sthe\sbutton
""", re.MULTILINE|re.VERBOSE)
re_SplitHands = re.compile('\n\n+')
re_TailSplitHands = re.compile('(\n\n\n+)')
re_Button = re.compile('Seat (?P<BUTTON>\d+) is the button', re.MULTILINE)
re_Board = re.compile(r"\[\s(?P<CARDS>.+)\s\]")
re_DateTime = re.compile("""(?P<D>[0-9]{2})\s(?P<M>[0-9]{2})\s(?P<Y>[0-9]{4})[\- ]+(?P<H>[0-9]+):(?P<MIN>[0-9]+):(?P<S>[0-9]+)""", re.MULTILINE)
# These used to be compiled per player, but regression tests say
# we don't have to, and it makes life faster.
short_subst = {'PLYR': r'(?P<PNAME>.+?)', 'CUR': '\$?'}
re_PostSB = re.compile(r"^%(PLYR)s posts small blind \[%(CUR)s(?P<SB>[.,0-9]+)\]" % short_subst, re.MULTILINE)
re_PostBB = re.compile(r"^%(PLYR)s posts big blind \[%(CUR)s(?P<BB>[.,0-9]+)\]" % short_subst, re.MULTILINE)
re_Antes = re.compile(r"^%(PLYR)s posts the ante \[%(CUR)s(?P<ANTE>[.,0-9]+)\]" % short_subst, re.MULTILINE)
re_BringIn = re.compile(r"^%(PLYR)s: brings[- ]in( low|) for %(CUR)s(?P<BRINGIN>[.,0-9]+)" % short_subst, re.MULTILINE)
re_PostBoth = re.compile(r"^%(PLYR)s posts dead blind \[%(CUR)s(?P<SBBB>[.,0-9]+)\s\+\s%(CUR)s[.,0-9]+\]" % short_subst, re.MULTILINE)
re_HeroCards = re.compile(r"^Dealt to %(PLYR)s( \[\s(?P<NEWCARDS>.+?)\s\])" % short_subst, re.MULTILINE)
re_Action = re.compile(r"""
^%(PLYR)s(?P<ATYPE>\sbets|\schecks|\sraises|\scalls|\sfolds|\sdiscards|\sstands\spat)
(\s\[(%(CUR)s)?(?P<BET>[.,0-9]+)\])?
(\s*and\sis\sall.in)?
(\s*and\shas\sreached\sthe\s[%(CUR)s\d\.]+\scap)?
(\s*cards?(\s\[(?P<DISCARDED>.+?)\])?)?\s*$"""
% short_subst, re.MULTILINE|re.VERBOSE)
re_ShowdownAction = re.compile(r"^%s shows \[(?P<CARDS>.*)\]" % short_subst['PLYR'], re.MULTILINE)
re_sitsOut = re.compile("^%s sits out" % short_subst['PLYR'], re.MULTILINE)
re_ShownCards = re.compile("^%s ?(?P<SHOWED>shows|mucks) \[ (?P<CARDS>.*) \]$" % short_subst['PLYR'], re.MULTILINE)
re_CollectPot = re.compile(r"^%(PLYR)s collected \[ %(CUR)s(?P<POT>[.,0-9]+) \]$" % short_subst, re.MULTILINE)
def compilePlayerRegexs(self, hand):
pass
def readSupportedGames(self):
return [["ring", "hold", "nl"],
["ring", "hold", "pl"],
["ring", "hold", "fl"],
["ring", "stud", "fl"],
["ring", "draw", "fl"],
["ring", "draw", "pl"],
["ring", "draw", "nl"],
["tour", "hold", "nl"],
["tour", "hold", "pl"],
["tour", "hold", "fl"],
["tour", "stud", "fl"],
["tour", "draw", "fl"],
["tour", "draw", "pl"],
["tour", "draw", "nl"],
]
def determineGameType(self, handText):
info = {}
m = self.re_GameInfo.search(handText)
if not m:
tmp = handText[0:120]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
mg = m.groupdict()
if 'LIMIT' in mg:
#print "DEBUG: re_GameInfo[LIMIT] \'", mg['LIMIT'], "\'"
info['limitType'] = self.limits[mg['LIMIT']]
if 'GAME' in mg:
#print "DEBUG: re_GameInfo[GAME] \'", mg['GAME'], "\'"
(info['base'], info['category']) = self.games[mg['GAME']]
if 'SB' in mg:
#print "DEBUG: re_GameInfo[SB] \'", mg['SB'], "\'"
info['sb'] = mg['SB']
if 'BB' in mg:
#print "DEBUG: re_GameInfo[BB] \'", mg['BB'], "\'"
info['bb'] = mg['BB']
if 'CURRENCY' in mg:
#print "DEBUG: re_GameInfo[CURRENCY] \'", mg['CURRENCY'], "\'"
info['currency'] = self.currencies[mg['CURRENCY']]
if 'TOURNO' in mg and mg['TOURNO'] is not None:
info['type'] = 'tour'
else:
info['type'] = 'ring'
if info['limitType'] == 'fl' and info['bb'] is not None and info['type'] == 'ring' and info['base'] != 'stud':
try:
info['sb'] = self.Lim_Blinds[mg['BB']][0]
info['bb'] = self.Lim_Blinds[mg['BB']][1]
except KeyError:
log.error(_("Lim_Blinds has no lookup for '%s'") % mg['BB'])
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Lim_Blinds has no lookup for '%s'") % mg['BB'])
return info
def readHandInfo(self, hand):
info = {}
m = self.re_HandInfo.search(hand.handText,re.DOTALL)
m2 = self.re_GameInfo.search(hand.handText)
if m is None or m2 is None:
log.error(_("No match in readHandInfo: '%s'") % hand.handText[0:100])
raise FpdbParseError(_("No match in readHandInfo: '%s'") % hand.handText[0:100])
info.update(m.groupdict())
info.update(m2.groupdict())
log.debug("readHandInfo: %s" % info)
for key in info:
if key == 'DATETIME':
#2008/11/12 10:00:48 CET [2008/11/12 4:00:48 ET] # (both dates are parsed so ET date overrides the other)
#2008/08/17 - 01:14:43 (ET)
#2008/09/07 06:23:14 ET
m1 = self.re_DateTime.finditer(info[key])
datetimestr = "2000/01/01 00:00:00" # default used if time not found
for a in m1:
datetimestr = "%s/%s/%s %s:%s:%s" % (a.group('Y'), a.group('M'),a.group('D'),a.group('H'),a.group('MIN'),a.group('S'))
#tz = a.group('TZ') # just assume ET??
#print " tz = ", tz, " datetime =", datetimestr
hand.startTime = datetime.datetime.strptime(datetimestr, "%Y/%m/%d %H:%M:%S") # also timezone at end, e.g. " ET"
hand.startTime = HandHistoryConverter.changeTimezone(hand.startTime, "ET", "UTC")
if key == 'HID':
hand.handid = info[key]
if key == 'TOURNO':
hand.tourNo = info[key]
if key == 'BUYIN':
if hand.tourNo!=None:
#print "DEBUG: info['BUYIN']: %s" % info['BUYIN']
#print "DEBUG: info['BIAMT']: %s" % info['BIAMT']
#print "DEBUG: info['BIRAKE']: %s" % info['BIRAKE']
#print "DEBUG: info['BOUNTY']: %s" % info['BOUNTY']
if info[key] == 'Freeroll':
hand.buyin = 0
hand.fee = 0
hand.buyinCurrency = "FREE"
else:
if info[key].find("$")!=-1:
hand.buyinCurrency="USD"
elif info[key].find(u"")!=-1:
hand.buyinCurrency="EUR"
elif info[key].find("FPP")!=-1:
hand.buyinCurrency="PSFP"
else:
#FIXME: handle other currencies, FPP, play money
raise FpdbParseError(_("Failed to detect currency.") + " " + _("Hand ID: %s: '%s'") % (hand.handid, info[key]))
info['BIAMT'] = info['BIAMT'].strip(u'$€FPP')
if hand.buyinCurrency!="PSFP":
if info['BOUNTY'] != None:
# There is a bounty, Which means we need to switch BOUNTY and BIRAKE values
tmp = info['BOUNTY']
info['BOUNTY'] = info['BIRAKE']
info['BIRAKE'] = tmp
info['BOUNTY'] = info['BOUNTY'].strip(u'$€') # Strip here where it isn't 'None'
hand.koBounty = int(100*Decimal(info['BOUNTY']))
hand.isKO = True
else:
hand.isKO = False
info['BIRAKE'] = info['BIRAKE'].strip(u'$€')
hand.buyin = int(100*Decimal(info['BIAMT']))
hand.fee = int(100*Decimal(info['BIRAKE']))
else:
hand.buyin = int(Decimal(info['BIAMT']))
hand.fee = 0
if key == 'LEVEL':
hand.level = info[key]
if key == 'TABLE':
if hand.tourNo != None:
hand.tablename = re.split(" ", info[key])[1]
else:
hand.tablename = info[key]
if key == 'BUTTON':
hand.buttonpos = info[key]
if key == 'MAX' and info[key] != None:
hand.maxseats = int(info[key])
if key == 'MIXED':
hand.mixed = self.mixes[info[key]] if info[key] is not None else None
if key == 'PLAY' and info['PLAY'] is not None:
# hand.currency = 'play' # overrides previously set value
hand.gametype['currency'] = 'play'
def readButton(self, hand):
m = self.re_Button.search(hand.handText)
if m:
hand.buttonpos = int(m.group('BUTTON'))
else:
log.info(_('readButton: not found'))
def readPlayerStacks(self, hand):
log.debug("readPlayerStacks")
m = self.re_PlayerInfo.finditer(hand.handText)
for a in m:
#print "DEBUG: Seat[", a.group('SEAT'), "]; PNAME[", a.group('PNAME'), "]; CASH[", a.group('CASH'), "]"
hand.addPlayer(int(a.group('SEAT')), a.group('PNAME'), a.group('CASH'))
def markStreets(self, hand):
# PREFLOP = ** Dealing down cards **
# This re fails if, say, river is missing; then we don't get the ** that starts the river.
if hand.gametype['base'] in ("hold"):
m = re.search(r"\*\* Dealing down cards \*\*(?P<PREFLOP>.+(?=\*\* Dealing flop \*\*)|.+)"
r"(\*\* Dealing flop \*\* (?P<FLOP>\[ \S\S, \S\S, \S\S \].+(?=\*\* Dealing turn \*\*)|.+))?"
r"(\*\* Dealing turn \*\* (?P<TURN>\[ \S\S \].+(?=\*\* Dealing river \*\*)|.+))?"
r"(\*\* Dealing river \*\* (?P<RIVER>\[ \S\S \].+))?"
, hand.handText,re.DOTALL)
if m is None:
log.error("Didn't match markStreets")
raise FpdbParseError(_("No match in markStreets"))
else:
#print "DEBUG: Matched markStreets"
mg = m.groupdict()
# if 'PREFLOP' in mg:
# print "DEBUG: PREFLOP: ", [mg['PREFLOP']]
# if 'FLOP' in mg:
# print "DEBUG: FLOP: ", [mg['FLOP']]
# if 'TURN' in mg:
# print "DEBUG: TURN: ", [mg['TURN']]
# if 'RIVER' in mg:
# print "DEBUG: RIVER: ", [mg['RIVER']]
hand.addStreets(m)
def readCommunityCards(self, hand, street): # street has been matched by markStreets, so exists in this hand
if street in ('FLOP','TURN','RIVER'): # a list of streets which get dealt community cards (i.e. all but PREFLOP)
#print "DEBUG readCommunityCards:", street, hand.streets.group(street)
m = self.re_Board.search(hand.streets[street])
hand.setCommunityCards(street, m.group('CARDS').split(', '))
def readAntes(self, hand):
log.debug(_("reading antes"))
m = self.re_Antes.finditer(hand.handText)
for player in m:
#~ logging.debug("hand.addAnte(%s,%s)" %(player.group('PNAME'), player.group('ANTE')))
hand.addAnte(player.group('PNAME'), player.group('ANTE'))
def readBringIn(self, hand):
m = self.re_BringIn.search(hand.handText,re.DOTALL)
if m:
#~ logging.debug("readBringIn: %s for %s" %(m.group('PNAME'), m.group('BRINGIN')))
hand.addBringIn(m.group('PNAME'), m.group('BRINGIN'))
def readBlinds(self, hand):
liveBlind = True
for a in self.re_PostSB.finditer(hand.handText):
if liveBlind:
hand.addBlind(a.group('PNAME'), 'small blind', a.group('SB'))
liveBlind = False
else:
# Post dead blinds as ante
hand.addBlind(a.group('PNAME'), 'secondsb', a.group('SB'))
for a in self.re_PostBB.finditer(hand.handText):
hand.addBlind(a.group('PNAME'), 'big blind', a.group('BB'))
for a in self.re_PostBoth.finditer(hand.handText):
hand.addBlind(a.group('PNAME'), 'both', a.group('SBBB'))
def readHeroCards(self, hand):
# streets PREFLOP, PREDRAW, and THIRD are special cases beacause
# we need to grab hero's cards
for street in ('PREFLOP', 'DEAL'):
if street in hand.streets.keys():
m = self.re_HeroCards.finditer(hand.streets[street])
for found in m:
# if m == None:
# hand.involved = False
# else:
hand.hero = found.group('PNAME')
newcards = found.group('NEWCARDS').split(', ')
hand.addHoleCards(street, hand.hero, closed=newcards, shown=False, mucked=False, dealt=True)
for street, text in hand.streets.iteritems():
if not text or street in ('PREFLOP', 'DEAL'): continue # already done these
m = self.re_HeroCards.finditer(hand.streets[street])
for found in m:
player = found.group('PNAME')
if found.group('NEWCARDS') is None:
newcards = []
else:
newcards = found.group('NEWCARDS').split(', ')
if found.group('OLDCARDS') is None:
oldcards = []
else:
oldcards = found.group('OLDCARDS').split(', ')
if street == 'THIRD' and len(newcards) == 3: # hero in stud game
hand.hero = player
hand.dealt.add(player) # need this for stud??
hand.addHoleCards(street, player, closed=newcards[0:2], open=[newcards[2]], shown=False, mucked=False, dealt=False)
else:
hand.addHoleCards(street, player, open=newcards, closed=oldcards, shown=False, mucked=False, dealt=False)
def readAction(self, hand, street):
m = self.re_Action.finditer(hand.streets[street])
for action in m:
acts = action.groupdict()
#print "DEBUG: acts: %s" %acts
if action.group('ATYPE') == ' raises':
hand.addRaiseTo( street, action.group('PNAME'), action.group('BET').replace(',','') )
elif action.group('ATYPE') == ' calls':
hand.addCall( street, action.group('PNAME'), action.group('BET').replace(',','') )
elif action.group('ATYPE') == ' bets':
hand.addBet( street, action.group('PNAME'), action.group('BET').replace(',','') )
elif action.group('ATYPE') == ' folds':
hand.addFold( street, action.group('PNAME'))
elif action.group('ATYPE') == ' checks':
hand.addCheck( street, action.group('PNAME'))
elif action.group('ATYPE') == ' discards':
hand.addDiscard(street, action.group('PNAME'), action.group('BET').replace(',',''), action.group('DISCARDED'))
elif action.group('ATYPE') == ' stands pat':
hand.addStandsPat( street, action.group('PNAME'))
else:
print (_("DEBUG: ") + _("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'), action.group('ATYPE')))
def readShowdownActions(self, hand):
# TODO: pick up mucks also??
for shows in self.re_ShowdownAction.finditer(hand.handText):
cards = shows.group('CARDS').split(', ')
hand.addShownCards(cards, shows.group('PNAME'))
def readCollectPot(self,hand):
for m in self.re_CollectPot.finditer(hand.handText):
#print "DEBUG: hand.addCollectPot(player=", m.group('PNAME'), ", pot=", m.group('POT'), ")"
hand.addCollectPot(player=m.group('PNAME'),pot=m.group('POT').replace(',',''))
def readShownCards(self,hand):
for m in self.re_ShownCards.finditer(hand.handText):
if m.group('CARDS') is not None:
cards = m.group('CARDS')
cards = cards.split(', ') # needs to be a list, not a set--stud needs the order
(shown, mucked) = (False, False)
if m.group('SHOWED') == "showed": shown = True
elif m.group('SHOWED') == "mucked": mucked = True
#print "DEBUG: hand.addShownCards(%s, %s, %s, %s)" %(cards, m.group('PNAME'), shown, mucked)
hand.addShownCards(cards=cards, player=m.group('PNAME'), shown=shown, mucked=mucked)
if __name__ == "__main__":
parser = OptionParser()
parser.add_option("-i", "--input", dest="ipath", help=_("parse input hand history"), default="regression-test-files/stars/horse/HH20090226 Natalie V - $0.10-$0.20 - HORSE.txt")
parser.add_option("-o", "--output", dest="opath", help=_("output translation to"), default="-")
parser.add_option("-f", "--follow", dest="follow", help=_("follow (tail -f) the input"), action="store_true", default=False)
#parser.add_option("-q", "--quiet", action="store_const", const=logging.CRITICAL, dest="verbosity", default=logging.INFO)
#parser.add_option("-v", "--verbose", action="store_const", const=logging.INFO, dest="verbosity")
#parser.add_option("--vv", action="store_const", const=logging.DEBUG, dest="verbosity")
(options, args) = parser.parse_args()
e = PacificPoker(in_path = options.ipath, out_path = options.opath, follow = options.follow)

View File

@ -195,7 +195,7 @@ class PartyPoker(HandHistoryConverter):
if m is None:
tmp = handText[0:100]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
mg = m.groupdict()
@ -345,7 +345,7 @@ class PartyPoker(HandHistoryConverter):
elif info[key].find(u"")!=-1:
hand.buyinCurrency="EUR"
else:
raise FpdbParseError(_("Failed to detect currency. Hand ID: %s: '%s'") % (hand.handid, info[key]))
raise FpdbParseError(_("Failed to detect currency.") + " " + _("Hand ID: %s: '%s'") % (hand.handid, info[key]))
info[key] = info[key].strip(u'$€')
hand.buyin = int(100*Decimal(info[key]))
if key == 'LEVEL':
@ -532,9 +532,7 @@ class PartyPoker(HandHistoryConverter):
elif actionType == 'checks':
hand.addCheck( street, playerName )
else:
raise FpdbParseError(
_("Unimplemented readAction: '%s' '%s'") % (playerName,actionType,),
hid = hand.hid, )
raise FpdbParseError(_("Unimplemented readAction: '%s' '%s'") % (playerName,actionType), hid = hand.hid)
def readShowdownActions(self, hand):
# all action in readShownCards

View File

@ -126,7 +126,7 @@ class Pkr(HandHistoryConverter):
if not m:
tmp = handText[0:100]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
mg = m.groupdict()
@ -151,7 +151,7 @@ class Pkr(HandHistoryConverter):
info['bb'] = self.Lim_Blinds[mg['BB']][1]
except KeyError:
log.error(_("Lim_Blinds has no lookup for '%s'") % mg['BB'])
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Lim_Blinds has no lookup for '%s'") % mg['BB'])
return info
@ -348,7 +348,7 @@ class Pkr(HandHistoryConverter):
elif action.group('ATYPE') == ' stands pat':
hand.addStandsPat( street, action.group('PNAME'))
else:
print "DEBUG: unimplemented readAction: '%s' '%s'" %(action.group('PNAME'),action.group('ATYPE'),)
print (_("DEBUG: ") + _("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'), action.group('ATYPE')))
def readShowdownActions(self, hand):

View File

@ -68,7 +68,7 @@ class PokerStarsSummary(TourneySummary):
re_Currency = re.compile(u"""(?P<CURRENCY>[%(LS)s]|FPP)""" % substitutions)
re_Player = re.compile(u"""(?P<RANK>[0-9]+):\s(?P<NAME>.*)\s\(.*\),(\s)?(\$(?P<WINNINGS>[0-9]+\.[0-9]+))?(?P<STILLPLAYING>still\splaying)?((?P<TICKET>Tournament\sTicket)\s\(WSOP\sStep\s(?P<LEVEL>\d)\))?(\s+)?""")
re_Player = re.compile(u"""(?P<RANK>[0-9]+):\s(?P<NAME>.*)\s\(.*\),(\s)?([%(LS)s](?P<WINNINGS>[0-9]+\.[0-9]+))?(?P<STILLPLAYING>still\splaying)?((?P<TICKET>Tournament\sTicket)\s\(WSOP\sStep\s(?P<LEVEL>\d)\))?(\s+)?""" % substitutions)
re_DateTime = re.compile("\[(?P<Y>[0-9]{4})\/(?P<M>[0-9]{2})\/(?P<D>[0-9]{2})[\- ]+(?P<H>[0-9]+):(?P<MIN>[0-9]+):(?P<S>[0-9]+)")
@ -78,8 +78,8 @@ class PokerStarsSummary(TourneySummary):
m = self.re_TourneyInfo.search(self.summaryText)
if m == None:
tmp = self.summaryText[0:200]
log.error(_("parseSummary: Unable to recognise Tourney Info: '%s'") % tmp)
log.error(_("parseSummary: Raising FpdbParseError"))
log.error("parseSummary: " + _("Unable to recognise Tourney Info: '%s'") % tmp)
log.error("parseSummary: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise Tourney Info: '%s'") % tmp)
#print "DEBUG: m.groupdict(): %s" % m.groupdict()
@ -104,8 +104,8 @@ class PokerStarsSummary(TourneySummary):
m = self.re_Currency.search(self.summaryText)
if m == None:
log.error(_("parseSummary: Unable to locate currency"))
log.error(_("parseSummary: Raising FpdbParseError"))
log.error("parseSummary: " + _("Unable to locate currency"))
log.error("parseSummary: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to locate currency"))
#print "DEBUG: m.groupdict(): %s" % m.groupdict()

View File

@ -38,11 +38,11 @@ class PokerStars(HandHistoryConverter):
codepage = ("utf8", "cp1252")
siteId = 2 # Needs to match id entry in Sites database
mixes = { 'HORSE': 'horse', '8-Game': '8game', 'HOSE': 'hose'} # Legal mixed games
mixes = { 'HORSE': 'horse', '8-Game': '8game', 'HOSE': 'hose', 'Mixed Hold\'em': 'mholdem'} # Legal mixed games
sym = {'USD': "\$", 'CAD': "\$", 'T$': "", "EUR": "\xe2\x82\xac", "GBP": "\xa3", "play": ""} # ADD Euro, Sterling, etc HERE
substitutions = {
'LEGAL_ISO' : "USD|EUR|GBP|CAD|FPP", # legal ISO currency codes
'LS' : "\$|\xe2\x82\xac|" # legal currency symbols - Euro(cp1252, utf-8)
'LS' : u"\$|\xe2\x82\xac|\u20ac|" # legal currency symbols - Euro(cp1252, utf-8)
}
# translations from captured groups to fpdb info strings
@ -90,7 +90,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|Mixed PLH/PLO)?\s?\(?
(?P<MIXED>HORSE|8\-Game|HOSE|Mixed\sPLH/PLO|Mixed\sHold\'em)?\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|Single\sDraw\s2\-7\sLowball|5\sCard\sDraw)\s
(?P<LIMIT>No\sLimit|Limit|LIMIT|Pot\sLimit)\)?,?\s
(-\s)?
@ -145,7 +145,8 @@ class PokerStars(HandHistoryConverter):
(\s(%(CUR)s)?(?P<BET>[.\d]+))?(\sto\s%(CUR)s(?P<BETTO>[.\d]+))? # the number discarded goes in <BET>
\s*(and\sis\sall.in)?
(and\shas\sreached\sthe\s[%(CUR)s\d\.]+\scap)?
(\scards?(\s\[(?P<DISCARDED>.+?)\])?)?\s*$"""
(\son|\scards?)?
(\s\[(?P<CARDS>.+?)\])?\s*$"""
% short_subst, re.MULTILINE|re.VERBOSE)
re_ShowdownAction = re.compile(r"^%s: shows \[(?P<CARDS>.*)\]" % short_subst['PLYR'], re.MULTILINE)
re_sitsOut = re.compile("^%s sits out" % short_subst['PLYR'], re.MULTILINE)
@ -183,7 +184,7 @@ class PokerStars(HandHistoryConverter):
if not m:
tmp = handText[0:100]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
mg = m.groupdict()
@ -209,7 +210,7 @@ class PokerStars(HandHistoryConverter):
info['bb'] = self.Lim_Blinds[mg['BB']][1]
except KeyError:
log.error(_("Lim_Blinds has no lookup for '%s'") % mg['BB'])
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Lim_Blinds has no lookup for '%s'") % mg['BB'])
return info
@ -262,7 +263,7 @@ class PokerStars(HandHistoryConverter):
hand.buyinCurrency="PSFP"
else:
#FIXME: handle other currencies, play money
raise FpdbParseError(_("Failed to detect currency. Hand ID: %s: '%s'") % (hand.handid, info[key]))
raise FpdbParseError(_("Failed to detect currency.") + " " + _("Hand ID: %s: '%s'") % (hand.handid, info[key]))
info['BIAMT'] = info['BIAMT'].strip(u'$€FPP')
@ -432,11 +433,11 @@ class PokerStars(HandHistoryConverter):
elif action.group('ATYPE') == ' checks':
hand.addCheck( street, action.group('PNAME'))
elif action.group('ATYPE') == ' discards':
hand.addDiscard(street, action.group('PNAME'), action.group('BET'), action.group('DISCARDED'))
hand.addDiscard(street, action.group('PNAME'), action.group('BET'), action.group('CARDS'))
elif action.group('ATYPE') == ' stands pat':
hand.addStandsPat( street, action.group('PNAME'))
hand.addStandsPat( street, action.group('PNAME'), action.group('CARDS'))
else:
print (_("DEBUG: ") + _("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'),action.group('ATYPE')))
print (_("DEBUG: ") + _("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'), action.group('ATYPE')))
def readShowdownActions(self, hand):

View File

@ -243,7 +243,7 @@ class RushNotes(Aux_Window):
c.execute(("SELECT handId, position, startCards, street0Aggr, tableName " +
"FROM Hands, HandsPlayers " +
"WHERE HandsPlayers.handId = Hands.id " +
"AND street0VPI = 1 " +
"AND street0VPI " +
"AND startCards > 0 " +
"AND playerId = %d " +
"ORDER BY startCards DESC " +

View File

@ -108,6 +108,15 @@ class Sql:
self.query['createSettingsTable'] = """CREATE TABLE Settings
(version INTEGER NOT NULL) """
################################
# Create InsertLock
################################
if db_server == 'mysql':
self.query['createLockTable'] = """CREATE TABLE InsertLock (
id BIGINT UNSIGNED AUTO_INCREMENT NOT NULL, PRIMARY KEY (id),
locked BOOLEAN NOT NULL DEFAULT FALSE)
ENGINE=INNODB"""
################################
# Create RawHands (this table is all but identical with RawTourneys)
################################
@ -279,7 +288,7 @@ class Sql:
if db_server == 'mysql':
self.query['createPlayersTable'] = """CREATE TABLE Players (
id INT UNSIGNED AUTO_INCREMENT NOT NULL, PRIMARY KEY (id),
name VARCHAR(32) CHARACTER SET utf8 NOT NULL,
name VARCHAR(32) NOT NULL,
siteId SMALLINT UNSIGNED NOT NULL, FOREIGN KEY (siteId) REFERENCES Sites(id),
comment text,
commentTs DATETIME)
@ -347,6 +356,7 @@ class Sql:
tourneyId INT UNSIGNED,
gametypeId SMALLINT UNSIGNED NOT NULL, FOREIGN KEY (gametypeId) REFERENCES Gametypes(id),
sessionId INT UNSIGNED,
gameSessionId INT UNSIGNED,
startTime DATETIME NOT NULL,
importTime DATETIME NOT NULL,
seats TINYINT NOT NULL,
@ -385,6 +395,7 @@ class Sql:
tourneyId INT,
gametypeId INT NOT NULL, FOREIGN KEY (gametypeId) REFERENCES Gametypes(id),
sessionId INT,
gameSessionId INT,
startTime timestamp without time zone NOT NULL,
importTime timestamp without time zone NOT NULL,
seats SMALLINT NOT NULL,
@ -422,6 +433,7 @@ class Sql:
tourneyId INT,
gametypeId INT NOT NULL,
sessionId INT,
gameSessionId INT,
startTime REAL NOT NULL,
importTime REAL NOT NULL,
seats INT NOT NULL,
@ -621,6 +633,19 @@ class Sql:
card5 smallint,
card6 smallint,
card7 smallint,
card8 smallint, /* cards 8-20 for draw hands */
card9 smallint,
card10 smallint,
card11 smallint,
card12 smallint,
card13 smallint,
card14 smallint,
card15 smallint,
card16 smallint,
card17 smallint,
card18 smallint,
card19 smallint,
card20 smallint,
startCards smallint,
ante INT,
@ -748,6 +773,19 @@ class Sql:
card5 smallint,
card6 smallint,
card7 smallint,
card8 smallint, /* cards 8-20 for draw hands */
card9 smallint,
card10 smallint,
card11 smallint,
card12 smallint,
card13 smallint,
card14 smallint,
card15 smallint,
card16 smallint,
card17 smallint,
card18 smallint,
card19 smallint,
card20 smallint,
startCards smallint,
ante INT,
@ -874,6 +912,19 @@ class Sql:
card5 INT,
card6 INT,
card7 INT,
card8 INT, /* cards 8-20 for draw hands */
card9 INT,
card10 INT,
card11 INT,
card12 INT,
card13 INT,
card14 INT,
card15 INT,
card16 INT,
card17 INT,
card18 INT,
card19 INT,
card20 INT,
startCards INT,
ante INT,
@ -1430,33 +1481,62 @@ class Sql:
id BIGINT UNSIGNED AUTO_INCREMENT NOT NULL, PRIMARY KEY (id),
sessionStart DATETIME NOT NULL,
sessionEnd DATETIME NOT NULL,
ringHDs INT NOT NULL,
tourHDs INT NOT NULL,
ringProfitUSD INT NOT NULL,
ringProfitEUR INT NOT NULL)
gameStart DATETIME NOT NULL,
gameEnd DATETIME NOT NULL,
sessionId BIGINT,
date CHAR(7) NOT NULL, /* 1st char is style (A/T/H/S), other 6 are the key */
type char(7) NOT NULL,
gametypeId SMALLINT UNSIGNED, FOREIGN KEY (gametypeId) REFERENCES Gametypes(id),
tourneyTypeId SMALLINT UNSIGNED, FOREIGN KEY (tourneyTypeId) REFERENCES TourneyTypes(id),
playerId INT UNSIGNED NOT NULL, FOREIGN KEY (playerId) REFERENCES Players(id),
hands INT NOT NULL,
tourneys INT NOT NULL,
totalProfit INT)
ENGINE=INNODB
"""
ENGINE=INNODB"""
elif db_server == 'postgresql':
self.query['createSessionsCacheTable'] = """CREATE TABLE SessionsCache (
id BIGSERIAL, PRIMARY KEY (id),
sessionStart REAL NOT NULL,
sessionEnd REAL NOT NULL,
ringHDs INT NOT NULL,
tourHDs INT NOT NULL,
ringProfitUSD INT NOT NULL,
ringProfitEUR INT NOT NULL)
gameStart REAL NOT NULL,
gameEnd REAL NOT NULL,
sessionId INT,
date CHAR(7) NOT NULL, /* 1st char is style (A/T/H/S), other 6 are the key */
type char(7),
gametypeId INT, FOREIGN KEY (gametypeId) REFERENCES Gametypes(id),
tourneyTypeId INT, FOREIGN KEY (tourneyTypeId) REFERENCES TourneyTypes(id),
playerId INT, FOREIGN KEY (playerId) REFERENCES Players(id),
hands INT,
tourneys INT,
totalProfit INT)
"""
elif db_server == 'sqlite':
self.query['createSessionsCacheTable'] = """CREATE TABLE SessionsCache (
id INTEGER PRIMARY KEY,
sessionStart REAL NOT NULL,
sessionEnd REAL NOT NULL,
ringHDs INT NOT NULL,
tourHDs INT NOT NULL,
ringProfitUSD INT NOT NULL,
ringProfitEUR INT NOT NULL)
sessionStart timestamp NOT NULL,
sessionEnd timestamp NOT NULL,
gameStart timestamp NOT NULL,
gameEnd timestamp NOT NULL,
sessionId INT,
date TEXT NOT NULL, /* 1st char is style (A/T/H/S), other 6 are the key */
type TEXT,
gametypeId INT,
tourneyTypeId INT,
playerId INT,
hands INT,
tourneys INT,
totalProfit INT)
"""
self.query['addSessionIdIndex'] = """CREATE INDEX index_SessionId ON SessionsCache (sessionId)"""
self.query['addHandsSessionIdIndex'] = """CREATE INDEX index_handsSessionId ON Hands (sessionId)"""
self.query['addHandsGameSessionIdIndex'] = """CREATE INDEX index_handsGameSessionId ON Hands (gameSessionId)"""
if db_server == 'mysql':
self.query['addTourneyIndex'] = """ALTER TABLE Tourneys ADD UNIQUE INDEX siteTourneyNo(siteTourneyNo, tourneyTypeId)"""
elif db_server == 'postgresql':
@ -1479,7 +1559,7 @@ class Sql:
self.query['addPlayersIndex'] = """CREATE UNIQUE INDEX name ON Players (name, siteId)"""
if db_server == 'mysql':
self.query['addTPlayersIndex'] = """ALTER TABLE TourneysPlayers ADD UNIQUE INDEX tourneyId(tourneyId, playerId)"""
self.query['addTPlayersIndex'] = """ALTER TABLE TourneysPlayers ADD UNIQUE INDEX _tourneyId(tourneyId, playerId)"""
elif db_server == 'postgresql':
self.query['addTPlayersIndex'] = """CREATE UNIQUE INDEX tourneyId ON TourneysPlayers (tourneyId, playerId)"""
elif db_server == 'sqlite':
@ -3401,7 +3481,7 @@ class Sql:
<limit_test>
<game_test>
AND hp.tourneysPlayersId IS NULL
GROUP BY h.startTime, hp.handId, hp.sawShowdown, hp.totalProfit
GROUP BY h.startTime, hp.handId, hp.sawShowdown, ( hp.totalProfit / ( gt.bigBlind * 2 ) ) * 100
ORDER BY h.startTime"""
self.query['getRingProfitAllHandsPlayerIdSiteInDollars'] = """
@ -4142,7 +4222,7 @@ class Sql:
"""
self.query['insert_hudcache'] = """
INSERT INTO HudCache (
insert into HudCache (
gametypeId,
playerId,
activeSeats,
@ -4237,7 +4317,7 @@ class Sql:
street2Raises,
street3Raises,
street4Raises)
VALUES (%s, %s, %s, %s, %s,
values (%s, %s, %s, %s, %s,
%s, %s, %s, %s, %s,
%s, %s, %s, %s, %s,
%s, %s, %s, %s, %s,
@ -4364,95 +4444,135 @@ class Sql:
# Queries to rebuild/modify sessionscache
####################################
self.query['select_sessionscache'] = """
self.query['clearSessionsCache'] = """DELETE FROM SessionsCache"""
self.query['rebuildSessionsCache'] = """
SELECT Hands.id as id,
Hands.startTime as startTime,
HandsPlayers.playerId as playerId,
Hands.gametypeId as gametypeId,
Gametypes.type as game,
HandsPlayers.totalProfit as totalProfit,
Tourneys.tourneyTypeId as tourneyTypeId
FROM Gametypes, HandsPlayers, Hands
LEFT JOIN Tourneys ON Hands.tourneyId = Tourneys.tourneyTypeId
WHERE HandsPlayers.handId = Hands.id
AND Hands.gametypeId = Gametypes.id
AND (case when HandsPlayers.playerId = <where_clause> then 1 else 0 end) = 1
ORDER BY Hands.startTime ASC"""
self.query['rebuildSessionsCacheSum'] = """
SELECT Tourneys.id as id,
Tourneys.startTime as startTime,
TourneysPlayers.playerId,
TourneyTypes.id as tourneyTypeId,
TourneysPlayers.winnings as winnings,
TourneysPlayers.winningsCurrency as winningsCurrency,
TourneyTypes.currency as buyinCurrency,
TourneyTypes.buyIn as buyIn,
TourneyTypes.fee as fee,
case when TourneyTypes.rebuy then TourneyTypes.rebuyCost else 0 end as rebuyCost,
case when TourneyTypes.rebuy then TourneyTypes.rebuyFee else 0 end as rebuyFee,
case when TourneyTypes.addOn then TourneyTypes.addOnCost else 0 end as addOnCost,
case when TourneyTypes.addOn then TourneyTypes.addOnFee else 0 end as addOnFee,
case when TourneyTypes.knockout then TourneyTypes.koBounty else 0 end as koBounty
FROM Tourneys, TourneyTypes, TourneysPlayers
WHERE Tourneys.tourneyTypeId = TourneyTypes.id
AND Tourneys.id = TourneysPlayers.tourneyId
AND (case when TourneysPlayers.playerId = <where_clause> then 1 else 0 end) = 1
ORDER BY Tourneys.startTime ASC"""
self.query['select_prepSC'] = """
SELECT sessionId as id,
sessionStart,
sessionEnd,
count(sessionId) as count
FROM SessionsCache
WHERE sessionEnd>=%s
AND sessionStart<=%s
GROUP BY sessionId, sessionStart, sessionEnd"""
self.query['update_prepSC'] = """
UPDATE SessionsCache SET
sessionStart=%s,
sessionEnd=%s
WHERE sessionId=%s"""
self.query['update_SC'] = """
UPDATE SessionsCache SET
sessionStart=%s,
sessionEnd=%s,
gameStart=%s,
gameEnd=%s,
hands=hands+%s,
tourneys=tourneys+%s,
totalProfit=totalProfit+%s
WHERE id=%s"""
self.query['select_SC'] = """
SELECT id,
sessionStart,
sessionEnd,
ringHDs,
tourHDs,
ringProfitUSD,
ringProfitEUR
gameStart,
gameEnd,
sessionId,
date,
type,
gametypeId,
tourneyTypeId,
playerId,
hands,
tourneys,
totalProfit
FROM SessionsCache
WHERE sessionEnd>=%s
AND sessionStart<=%s"""
WHERE gameEnd>=%s
AND gameStart<=%s
AND date=%s
AND type=%s
AND (case when gametypeId is NULL then 1 else
(case when gametypeId=%s then 1 else 0 end) end)=1
AND (case when tourneyTypeId is NULL then 1 else
(case when tourneyTypeId=%s then 1 else 0 end) end)=1
AND playerId=%s"""
self.query['select_sessionscache_mid'] = """
SELECT sessionStart,
sessionEnd,
ringHDs,
tourHDs,
ringProfitUSD,
ringProfitEUR
FROM SessionsCache
WHERE sessionEnd>=%s
AND sessionStart<=%s"""
self.query['select_sessionscache_start'] = """
SELECT sessionStart,
sessionEnd,
ringHDs,
tourHDs,
ringProfitUSD,
ringProfitEUR
FROM SessionsCache
WHERE sessionStart>%s
AND sessionEnd>=%s
AND sessionStart<=%s"""
self.query['update_sessionscache_mid'] = """
UPDATE SessionsCache SET
ringHDs=ringHDs+%s,
tourHDs=tourHDs+%s,
ringProfitUSD=ringProfitUSD+%s,
ringProfitEUR=ringProfitEUR+%s
WHERE sessionStart<=%s
AND sessionEnd>=%s"""
self.query['update_sessionscache_start'] = """
UPDATE SessionsCache SET
sessionStart=%s,
ringHDs=ringHDs+%s,
tourHDs=tourHDs+%s,
ringProfitUSD=ringProfitUSD+%s,
ringProfitEUR=ringProfitEUR+%s
WHERE sessionStart>%s
AND sessionEnd>=%s
AND sessionStart<=%s"""
self.query['update_sessionscache_end'] = """
UPDATE SessionsCache SET
sessionEnd=%s,
ringHDs=ringHDs+%s,
tourHDs=tourHDs+%s,
ringProfitUSD=ringProfitUSD+%s,
ringProfitEUR=ringProfitEUR+%s
WHERE sessionEnd<%s
AND sessionEnd>=%s
AND sessionStart<=%s"""
self.query['insert_sessionscache'] = """
INSERT INTO SessionsCache (
self.query['insert_SC'] = """
insert into SessionsCache (
sessionStart,
sessionEnd,
ringHDs,
tourHDs,
ringProfitUSD,
ringProfitEUR)
VALUES (%s, %s, %s, %s, %s, %s)"""
gameStart,
gameEnd,
sessionId,
date,
type,
gametypeId,
tourneyTypeId,
playerId,
hands,
tourneys,
totalProfit)
values (%s, %s, %s, %s, %s, %s, %s,
%s, %s, %s, %s, %s, %s)"""
self.query['merge_sessionscache'] = """
SELECT min(sessionStart), max(sessionEnd), sum(ringHDs), sum(tourHDs), sum(ringProfitUSD), sum(ringProfitEUR)
FROM SessionsCache
WHERE (case when id=%s or id=%s then 1 else 0 end)=1"""
self.query['update_Hands_gsid'] = """
UPDATE Hands SET
gameSessionId=%s
WHERE gameSessionId=%s"""
self.query['delete_sessions'] = """
DELETE FROM SessionsCache
WHERE id=%s"""
self.query['update_hands_sessionid'] = """
self.query['update_Hands_sid'] = """
UPDATE Hands SET
sessionId=%s
WHERE (case when sessionId=%s or sessionId=%s then 1 else 0 end)=1"""
WHERE sessionId=%s"""
self.query['update_SC_sid'] = """
UPDATE SessionsCache SET
sessionStart=%s,
sessionEnd=%s,
sessionId=%s
WHERE sessionId=%s"""
self.query['delete_SC'] = """
DELETE FROM SessionsCache
WHERE id=%s"""
####################################
# Database management queries
@ -4468,6 +4588,25 @@ class Sql:
elif db_server == 'sqlite':
self.query['analyze'] = "analyze"
if db_server == 'mysql':
self.query['selectLock'] = """
SELECT locked
FROM InsertLock
WHERE locked=True
LOCK IN SHARE MODE"""
if db_server == 'mysql':
self.query['switchLock'] = """
UPDATE InsertLock SET
locked=%s
WHERE id=%s"""
if db_server == 'mysql':
self.query['missedLock'] = """
UPDATE InsertLock SET
missed=missed+%s
WHERE id=%s"""
if db_server == 'mysql':
self.query['lockForInsert'] = """
lock tables Hands write, HandsPlayers write, HandsActions write, Players write
@ -4652,6 +4791,7 @@ class Sql:
tourneyId,
gametypeid,
sessionId,
gameSessionId,
startTime,
importtime,
seats,
@ -4682,7 +4822,7 @@ class Sql:
values
(%s, %s, %s, %s, %s, %s, %s, %s, %s, %s, %s,
%s, %s, %s, %s, %s, %s, %s, %s, %s, %s, %s,
%s, %s, %s, %s, %s, %s, %s, %s, %s)"""
%s, %s, %s, %s, %s, %s, %s, %s, %s, %s)"""
self.query['store_hands_players'] = """insert into HandsPlayers (
@ -4698,6 +4838,19 @@ class Sql:
card5,
card6,
card7,
card8,
card9,
card10,
card11,
card12,
card13,
card14,
card15,
card16,
card17,
card18,
card19,
card20,
winnings,
rake,
totalProfit,
@ -4812,7 +4965,10 @@ class Sql:
%s, %s, %s, %s, %s,
%s, %s, %s, %s, %s,
%s, %s, %s, %s, %s,
%s, %s, %s, %s
%s, %s, %s, %s, %s,
%s, %s, %s, %s, %s,
%s, %s, %s, %s, %s,
%s, %s
)"""
self.query['store_hands_actions'] = """insert into HandsActions (

View File

@ -78,8 +78,8 @@ class Sitename(TourneySummary):
m = self.re_TourneyInfo.search(self.summaryText)
if m == None:
tmp = self.summaryText[0:200]
log.error(_("parseSummary: Unable to recognise Tourney Info: '%s'") % tmp)
log.error(_("parseSummary: Raising FpdbParseError"))
log.error("parseSummary: " + _("Unable to recognise Tourney Info: '%s'") % tmp)
log.error("parseSummary: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise Tourney Info: '%s'") % tmp)
print "DEBUG: m.groupdict(): %s" % m.groupdict()

View File

@ -21,8 +21,6 @@
import sys
import os
import codecs
import pprint
import PokerStarsToFpdb
from Hand import *
import Configuration
import Database
@ -31,6 +29,10 @@ import fpdb_import
import Options
import datetime
import pytz
import pprint
pp = pprint.PrettyPrinter(indent=4)
DEBUG = False
class FpdbError:
@ -147,6 +149,10 @@ def compare_hands_file(filename, importer, errors):
for hand in handlist:
ghash = hand.stats.getHands()
# Delete unused data from hash
del ghash['gsc']
del ghash['sc']
del ghash['id']
for datum in ghash:
#print "DEBUG: hand: '%s'" % datum
try:
@ -155,7 +161,7 @@ def compare_hands_file(filename, importer, errors):
pass
else:
# Stats don't match.
if datum == "gametypeId" or datum == 'sessionId' or datum == 'tourneyId':
if datum == "gametypeId" or datum == 'sessionId' or datum == 'tourneyId' or datum == 'gameSessionId':
# Not an error. gametypeIds are dependent on the order added to the db.
#print "DEBUG: Skipping mismatched gamtypeId"
pass
@ -172,6 +178,8 @@ def compare(leaf, importer, errors, site):
# Test if this is a hand history file
if filename.endswith('.txt'):
# test if there is a .hp version of the file
if DEBUG: print "Site: %s" % site
if DEBUG: print "Filename: %s" % filename
importer.addBulkImportImportFileOrDir(filename, site=site)
(stored, dups, partial, errs, ttime) = importer.runImport()
@ -213,7 +221,7 @@ def usage():
print "Run tests for a sinlge site:"
print "\t./TestHandsPlayers -s <Sitename>"
print "Run tests for a sinlge file in a site:"
print "\t./TestHandsPlayers -s <Sitename> -f <filname>"
print "\t./TestHandsPlayers -s <Sitename> -f <filename>"
sys.exit(0)
def main(argv=None):
@ -255,6 +263,7 @@ def main(argv=None):
importer.setCallHud(False)
importer.setFakeCacheHHC(True)
PacificPokerErrors= FpdbError('PacificPoker')
PokerStarsErrors = FpdbError('PokerStars')
FTPErrors = FpdbError('Full Tilt Poker')
PartyPokerErrors = FpdbError('Party Poker')
@ -271,7 +280,7 @@ def main(argv=None):
WinamaxErrors = FpdbError('Winamax')
ErrorsList = [
PokerStarsErrors, FTPErrors, PartyPokerErrors,
PacificPokerErrors, PokerStarsErrors, FTPErrors, PartyPokerErrors,
BetfairErrors, OnGameErrors, AbsoluteErrors,
EverleafErrors, CarbonErrors, PKRErrors,
iPokerErrors, WinamaxErrors, UltimateBetErrors,
@ -279,6 +288,7 @@ def main(argv=None):
]
sites = {
'PacificPoker' : False,
'PokerStars' : False,
'Full Tilt Poker' : False,
'PartyPoker' : False,
@ -301,6 +311,11 @@ def main(argv=None):
else:
sites[options.sitename] = True
if sites['PacificPoker'] == True and not single_file_test:
walk_testfiles("regression-test-files/cash/PacificPoker/", compare, importer, PacificPokerErrors, "PacificPoker")
elif sites['PacificPoker'] == True and single_file_test:
walk_testfiles(options.filename, compare, importer, PacificPokerErrors, "PacificPoker")
if sites['PokerStars'] == True and not single_file_test:
walk_testfiles("regression-test-files/cash/Stars/", compare, importer, PokerStarsErrors, "PokerStars")
walk_testfiles("regression-test-files/tour/Stars/", compare, importer, PokerStarsErrors, "PokerStars")
@ -323,6 +338,7 @@ def main(argv=None):
walk_testfiles(options.filename, compare, importer, BetfairErrors, "Betfair")
if sites['OnGame'] == True and not single_file_test:
walk_testfiles("regression-test-files/cash/OnGame/", compare, importer, OnGameErrors, "OnGame")
walk_testfiles("regression-test-files/tour/ongame/", compare, importer, OnGameErrors, "OnGame")
elif sites['OnGame'] == True and single_file_test:
walk_testfiles(options.filename, compare, importer, OnGameErrors, "OnGame")
if sites['Absolute'] == True and not single_file_test:
@ -336,6 +352,7 @@ def main(argv=None):
walk_testfiles(options.filename, compare, importer, UltimateBetErrors, "Absolute")
if sites['Everleaf'] == True and not single_file_test:
walk_testfiles("regression-test-files/cash/Everleaf/", compare, importer, EverleafErrors, "Everleaf")
walk_testfiles("regression-test-files/tour/Everleaf/", compare, importer, EverleafErrors, "Everleaf")
elif sites['Everleaf'] == True and single_file_test:
walk_testfiles(options.filename, compare, importer, EverleafErrors, "Everleaf")
if sites['Carbon'] == True and not single_file_test:

View File

@ -288,6 +288,24 @@ winnings (int) the money the player ended the tourney with (can be 0, or -1 i
print "checkPlayerExists", player, "fail"
raise FpdbParseError
def updateSessionsCache(self, sc, gsc, tz, doinsert):
self.heros = self.db.getHeroIds(self.dbid_pids, self.siteName)
sc = self.db.prepSessionsCache(self.tourNo, self.dbid_pids, self.startTime, sc , self.heros, doinsert)
gsc = self.db.storeSessionsCache(self.tourNo, self.dbid_pids, self.startTime, {'type': 'summary'}
,None, self.assembleInfo(), sc, gsc, tz, self.heros, doinsert)
return sc, gsc
def assembleInfo(self):
info = {}
info['tourneyTypeId'] = self.tourneyTypeId
info['winnings'] = self.winnings
info['winningsCurrency'] = self.winningsCurrency
info['buyinCurrency'] = self.buyinCurrency
info['buyin'] = self.buyin
info['fee'] = self.fee
return info
def writeSummary(self, fh=sys.__stdout__):
print >>fh, "Override me"

View File

@ -31,14 +31,20 @@ class Win2day(HandHistoryConverter):
sitename = "Win2day"
filetype = "text"
codepage = "cp1252"
codepage = "utf-8"
siteID = 4
# Static regexes
#<HISTORY ID="102271403" SESSION="session31237702.xml" TABLE="Innsbruck 3" GAME="GAME_THM" GAMETYPE="GAMETYPE_REAL" GAMEKIND="GAMEKIND_CASH" TABLECURRENCY="EUR" LIMIT="NL" STAKES="0.25/0.50" DATE="1246909773" WIN="0.00" LOSS="0.50">
#'^<HISTORY ID="(?P<HID>[0-9]+)" SESSION="session[0-9]+\.xml" TABLE="(?P<TABLE>[- a-zA-Z0-9]+)" GAME="(?P<GAME>[_A-Z]+)" GAMETYPE="[_a-zA-Z]+" GAMEKIND="[_a-zA-Z]+" TABLECURRENCY="(?P<CURRENCY>[A-Z]+)" LIMIT="(?P<LIMIT>NL|PL)" STAKES="(?P<SB>[.0-9]+)/(?P<BB>[.0-9]+)" DATE="(?P<DATETIME>[0-9]+)" WIN="[.0-9]+" LOSS="[.0-9]+">$'
re_GameInfo = re.compile('^<HISTORY ID="(?P<HID>[0-9]+)" SESSION="session[0-9]+\.xml" TABLE="(?P<TABLE>[- a-zA-Z0-9]+)" GAME="(?P<GAME>[_A-Z]+)" GAMETYPE="[_a-zA-Z]+" GAMEKIND="[_a-zA-Z]+" TABLECURRENCY="(?P<CURRENCY>[A-Z]+)" LIMIT="(?P<LIMIT>NL|PL)" STAKES="(?P<SB>[.0-9]+)/(?P<BB>[.0-9]+)" DATE="(?P<DATETIME>[0-9]+)" WIN="[.0-9]+" LOSS="[.0-9]+">', re.MULTILINE)
re_GameInfo = re.compile("""<HISTORY\sID="(?P<HID>[0-9]+)"\sSESSION="session[0-9]+\.xml"\s
TABLE="(?P<TABLE>[-\sa-zA-Z0-9\xc0-\xfc/.]+)"\s
GAME="(?P<GAME>[_A-Z]+)"\sGAMETYPE="[_a-zA-Z]+"\sGAMEKIND="[_a-zA-Z]+"\s
TABLECURRENCY="(?P<CURRENCY>[A-Z]+)"\s
LIMIT="(?P<LIMIT>NL|PL)"\s
STAKES="(?P<SB>[.0-9]+)/(?P<BB>[.0-9]+)"\s
DATE="(?P<DATETIME>[0-9]+)"\s
(TABLETOURNEYID=""\s)?
WIN="[.0-9]+"\sLOSS="[.0-9]+"
""", re.MULTILINE| re.VERBOSE)
re_SplitHands = re.compile('</HISTORY>')
re_HandInfo = re.compile("^Table \'(?P<TABLE>[- a-zA-Z]+)\'(?P<TABLEATTRIBUTES>.+?$)?", re.MULTILINE)
re_Button = re.compile('<ACTION TYPE="HAND_DEAL" PLAYER="(?P<BUTTON>[^"]+)">\n<CARD LINK="[0-9b]+"></CARD>\n<CARD LINK="[0-9b]+"></CARD></ACTION>\n<ACTION TYPE="ACTION_', re.MULTILINE)
@ -91,12 +97,13 @@ class Win2day(HandHistoryConverter):
m = self.re_GameInfo.search(handText)
if not m:
tmp = handText[0:100]
tmp = handText[0:1000]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
mg = m.groupdict()
#print "DEBUG: mg: %s" % mg
# translations from captured groups to our info strings
#limits = { 'NL':'nl', 'PL':'pl', 'Limit':'fl' }
@ -338,7 +345,7 @@ class Win2day(HandHistoryConverter):
elif action.group('ATYPE') == 'ACTION_STAND':
hand.addStandsPat( street, action.group('PNAME'))
else:
print (_("DEBUG: ") + _("unimplemented readAction: '%s' '%s'") % (action.group('PNAME'), action.group('ATYPE')))
print (_("DEBUG: ") + _("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'), action.group('ATYPE')))
def readShowdownActions(self, hand):

View File

@ -80,7 +80,7 @@ class Table(Table_Window):
try:
if self.window == None:
log.error(_("Window %s not found. Skipping." % self.search_string))
log.error(_("Window %s not found. Skipping.") % self.search_string)
return None
except AttributeError:
log.error(_("self.window doesn't exist? why?"))

View File

@ -45,7 +45,7 @@ class WinamaxSummary(TourneySummary):
substitutions = {
'LEGAL_ISO' : "USD|EUR|GBP|CAD|FPP", # legal ISO currency codes
'LS' : u"\$|\xe2\x82\xac|\u20AC|" # legal currency symbols
'LS' : u"\$|\xe2\x82\xac|\u20ac|" # legal currency symbols
}
re_GameType = re.compile("""<h1>((?P<LIMIT>No Limit|Pot Limit) (?P<GAME>Hold\'em))</h1>""")

View File

@ -52,10 +52,10 @@ class Winamax(HandHistoryConverter):
siteId = 14 # Needs to match id entry in Sites database
mixes = { } # Legal mixed games
sym = {'USD': "\$", 'CAD': "\$", 'T$': "", "EUR": "\xe2\x82\xac", "GBP": "\xa3"} # ADD Euro, Sterling, etc HERE
sym = {'USD': "\$", 'CAD': "\$", 'T$': "", "EUR": u"\xe2\x82\xac|\u20ac", "GBP": "\xa3"} # ADD Euro, Sterling, etc HERE
substitutions = {
'LEGAL_ISO' : "USD|EUR|GBP|CAD|FPP", # legal ISO currency codes
'LS' : "\$|\xe2\x82\xac|" # legal currency symbols - Euro(cp1252, utf-8)
'LS' : u"\$|\xe2\x82\xac|\u20ac|" # legal currency symbols - Euro(cp1252, utf-8)
}
limits = { 'no limit':'nl', 'pot limit' : 'pl','LIMIT':'fl'}
@ -170,7 +170,7 @@ class Winamax(HandHistoryConverter):
if not m:
tmp = handText[0:100]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
mg = m.groupdict()
@ -188,7 +188,7 @@ class Winamax(HandHistoryConverter):
else:
tmp = handText[0:100]
log.error(_("limit not found in self.limits(%s). hand: '%s'") % (str(mg),tmp))
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("limit not found in self.limits(%s). hand: '%s'") % (str(mg),tmp))
if 'GAME' in mg:
(info['base'], info['category']) = self.games[mg['GAME']]
@ -260,7 +260,7 @@ class Winamax(HandHistoryConverter):
hand.buyinCurrency="PSFP"
else:
#FIXME: handle other currencies (are there other currencies?)
raise FpdbParseError(_("Failed to detect currency. Hand ID: %s: '%s'") % (hand.handid, info[key]))
raise FpdbParseError(_("Failed to detect currency.") + " " + _("Hand ID: %s: '%s'") % (hand.handid, info[key]))
info['BIAMT'] = info['BIAMT'].strip(u'$€FPP')
@ -403,7 +403,7 @@ class Winamax(HandHistoryConverter):
elif action.group('ATYPE') == ' stands pat':
hand.addStandsPat( street, action.group('PNAME'))
else:
log.fatal(_("DEBUG: ") + _("unimplemented readAction: '%s' '%s'") % (action.group('PNAME'),action.group('ATYPE')))
log.fatal(_("DEBUG: ") + _("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'), action.group('ATYPE')))
# print "Processed %s"%acts
# print "committed=",hand.pot.committed

View File

@ -201,7 +201,6 @@ class fpdb:
# although not perfect, it seems to be the least instrusive.
baseNormStyle = eventBox.get_style().base[gtk.STATE_INSENSITIVE]
if baseNormStyle:
print baseNormStyle
eventBox.modify_bg(gtk.STATE_ACTIVE, gtk.gdk.color_parse(str(baseNormStyle)))
if nb.get_n_pages() > 0:
@ -267,10 +266,15 @@ class fpdb:
'Eric Blade', '_mt', 'sqlcoder', 'Bostik', _('and others')])
dia.set_program_name("Free Poker Database (FPDB)")
db_version = ""
#if self.db is not None:
# db_version = self.db.get_version()
nums = [(_('Operating System'), os.name),
if (os.name=="posix"):
os_text=str(os.uname())
elif (os.name=="nt"):
import platform
os_text=("Windows" + " " + str(platform.win32_ver()))
else:
os_text="Unknown"
nums = [(_('Operating System'), os_text),
('Python', sys.version[0:3]),
('GTK+', '.'.join([str(x) for x in gtk.gtk_version])),
('PyGTK', '.'.join([str(x) for x in gtk.pygtk_version])),
@ -282,7 +286,7 @@ class fpdb:
]
versions = gtk.TextBuffer()
w = 20 # width used for module names and version numbers
versions.set_text('\n'.join([x[0].rjust(w) + ' ' + x[1].ljust(w) for x in nums]))
versions.set_text('\n'.join([x[0].rjust(w) + ': ' + x[1].ljust(w) for x in nums]))
view = gtk.TextView(versions)
view.set_editable(False)
view.set_justification(gtk.JUSTIFY_CENTER)
@ -1328,26 +1332,6 @@ You can find the full license texts in agpl-3.0.txt, gpl-2.0.txt, gpl-3.0.txt an
return response
def validate_config(self):
# can this be removed now?
if self.config.get_import_parameters().get('saveStarsHH'):
hhbase = self.config.get_import_parameters().get("hhArchiveBase")
hhbase = os.path.expanduser(hhbase)
#hhdir = os.path.join(hhbase,site)
hhdir = hhbase
if not os.path.isdir(hhdir):
diapath = gtk.MessageDialog(parent=None, flags=0, type=gtk.MESSAGE_WARNING, buttons=(gtk.BUTTONS_YES_NO), message_format="Setup hh dir")
diastring = _("WARNING: Unable to find output hand history directory %s\n\n Press YES to create this directory, or NO to select a new one.") % hhdir
diapath.format_secondary_text(diastring)
response = diapath.run()
diapath.destroy()
if response == gtk.RESPONSE_YES:
try:
os.makedirs(hhdir)
except:
self.warning_box(_("WARNING: Unable to create hand output directory. Importing is not likely to work until this is fixed."))
elif response == gtk.RESPONSE_NO:
self.select_hhArchiveBase()
# check if sites in config file are in DB
for site in self.config.get_supported_sites(True): # get site names from config file
try:

View File

@ -170,7 +170,7 @@ class Importer:
def addImportFile(self, filename, site = "default", filter = "passthrough"):
#TODO: test it is a valid file -> put that in config!!
#print "addimportfile: filename is a", filename.__class__
# filename now comes in as unicode
# filename not guaranteed to be unicode
if filename in self.filelist or not os.path.exists(filename):
return
self.filelist[filename] = [site] + [filter]
@ -196,11 +196,10 @@ class Importer:
if os.path.isdir(inputPath):
for subdir in os.walk(inputPath):
for file in subdir[2]:
self.addImportFile(unicode(os.path.join(subdir[0], file),'utf-8'),
site=site, filter=filter)
self.addImportFile(os.path.join(subdir[0], file), site=site, filter=filter)
else:
self.addImportFile(inputPath, site=site, filter=filter)
self.addImportFile(unicode(inputPath,'utf-8'), site=site, filter=filter)
#Add a directory of files to filelist
#Only one import directory per site supported.
#dirlist is a hash of lists:
@ -242,7 +241,7 @@ class Importer:
#print "dropInd =", self.settings['dropIndexes'], " dropHudCache =", self.settings['dropHudCache']
if self.settings['threads'] <= 0:
(totstored, totdups, totpartial, toterrors) = self.importFiles(self.database, None)
(totstored, totdups, totpartial, toterrors) = self.importFiles(None)
else:
# create queue (will probably change to deque at some point):
self.writeq = Queue.Queue( self.settings['writeQSize'] )
@ -254,7 +253,7 @@ class Importer:
t.setDaemon(True)
t.start()
# read hands and write to q:
(totstored, totdups, totpartial, toterrors) = self.importFiles(self.database, self.writeq)
(totstored, totdups, totpartial, toterrors) = self.importFiles(self.writeq)
if self.writeq.empty():
print _("writers finished already")
@ -286,7 +285,7 @@ class Importer:
return (totstored, totdups, totpartial, toterrors, endtime-starttime)
# end def runImport
def importFiles(self, db, q):
def importFiles(self, q):
""""Read filenames in self.filelist and pass to import_file_dict().
Uses a separate database connection if created as a thread (caller
passes None or no param as db)."""
@ -304,7 +303,7 @@ class Importer:
ProgressDialog.progress_update()
(stored, duplicates, partial, errors, ttime) = self.import_file_dict(db, file
(stored, duplicates, partial, errors, ttime) = self.import_file_dict(file
,self.filelist[file][0], self.filelist[file][1], q)
totstored += stored
totdups += duplicates
@ -395,7 +394,7 @@ class Importer:
self.caller.addText("\n"+os.path.basename(file))
except KeyError: # TODO: What error happens here?
pass
(stored, duplicates, partial, errors, ttime) = self.import_file_dict(self.database, file, self.filelist[file][0], self.filelist[file][1], None)
(stored, duplicates, partial, errors, ttime) = self.import_file_dict(file, self.filelist[file][0], self.filelist[file][1], None)
try:
if not os.path.isdir(file): # Note: This assumes that whatever calls us has an "addText" func
self.caller.addText(" %d stored, %d duplicates, %d partial, %d errors (time = %f)" % (stored, duplicates, partial, errors, ttime))
@ -426,81 +425,75 @@ class Importer:
#rulog.close()
# This is now an internal function that should not be called directly.
def import_file_dict(self, db, file, site, filter, q=None):
#print "import_file_dict"
def import_file_dict(self, file, site, filter, q=None):
if os.path.isdir(file):
self.addToDirList[file] = [site] + [filter]
return (0,0,0,0,0)
conv = None
(stored, duplicates, partial, errors, ttime) = (0, 0, 0, 0, time())
# sc: is there any need to decode this? maybe easier to skip it than guess at the encoding?
#file = file.decode("utf-8") #(Configuration.LOCALE_ENCODING)
# Load filter, process file, pass returned filename to import_fpdb_file
if self.settings['threads'] > 0 and self.writeq is not None:
log.info((_("Converting %s") % file) + " (" + str(q.qsize()) + ")")
else:
log.info(_("Converting %s") % file)
hhbase = self.config.get_import_parameters().get("hhArchiveBase")
hhbase = os.path.expanduser(hhbase)
hhdir = os.path.join(hhbase,site)
try:
out_path = os.path.join(hhdir, file.split(os.path.sep)[-2]+"-"+os.path.basename(file))
except:
out_path = os.path.join(hhdir, "x"+strftime("%d-%m-%y")+os.path.basename(file))
else: log.info(_("Converting %s") % file)
filter_name = filter.replace("ToFpdb", "")
mod = __import__(filter)
obj = getattr(mod, filter_name, None)
if callable(obj):
idx = 0
if file in self.pos_in_file:
idx = self.pos_in_file[file]
else:
self.pos_in_file[file] = 0
hhc = obj( self.config, in_path = file, out_path = out_path, index = idx
, starsArchive = self.settings['starsArchive'], ftpArchive = self.settings['ftpArchive'],
sitename = site )
if file in self.pos_in_file: idx = self.pos_in_file[file]
else: self.pos_in_file[file], idx = 0, 0
hhc = obj( self.config, in_path = file, index = idx
,starsArchive = self.settings['starsArchive']
,ftpArchive = self.settings['ftpArchive']
,sitename = site )
if hhc.getStatus():
if self.caller: hhc.progressNotify()
handlist = hhc.getProcessedHands()
self.pos_in_file[file] = hhc.getLastCharacterRead()
to_hud = []
hp_bulk = []
ha_bulk = []
i = 0
(hbulk, hpbulk, habulk, hcbulk, phands, ihands, to_hud) = ([], [], [], [], [], [], [])
sc, gsc = {'bk': []}, {'bk': []}
####Lock Placeholder####
for hand in handlist:
i += 1
if hand is not None:
hand.prepInsert(self.database, printtest = self.settings['testData'])
self.database.commit()
phands.append(hand)
####Lock Placeholder####
for hand in phands:
hand.assembleHand()
####Lock Placeholder####
id = self.database.nextHandId()
for i in range(len(phands)):
doinsert = len(phands)==i+1
hand = phands[i]
try:
hp_inserts, ha_inserts = hand.insert(self.database, hp_data = hp_bulk,
ha_data = ha_bulk, insert_data = len(handlist)==i,
printtest = self.settings['testData'])
hp_bulk += hp_inserts
ha_bulk += ha_inserts
id = hand.getHandId(self.database, id)
sc, gsc = hand.updateSessionsCache(self.database, sc, gsc, None, doinsert)
hbulk = hand.insertHands(self.database, hbulk, doinsert, self.settings['testData'])
hcbulk = hand.updateHudCache(self.database, hcbulk, doinsert)
ihands.append(hand)
to_hud.append(id)
except Exceptions.FpdbHandDuplicate:
duplicates += 1
else:
if self.callHud and hand.dbid_hands != 0:
to_hud.append(hand.dbid_hands)
else: # TODO: Treat empty as an error, or just ignore?
log.error(_("Hand processed but empty"))
self.database.commit()
####Lock Placeholder####
# Call hudcache update if not in bulk import mode
# FIXME: Need to test for bulk import that isn't rebuilding the cache
if self.callHud:
for hand in handlist:
if hand is not None and not hand.is_duplicate:
hand.updateHudCache(self.database)
for i in range(len(ihands)):
doinsert = len(ihands)==i+1
hand = ihands[i]
hpbulk = hand.insertHandsPlayers(self.database, hpbulk, doinsert, self.settings['testData'])
habulk = hand.insertHandsActions(self.database, habulk, doinsert, self.settings['testData'])
self.database.commit()
#pipe the Hands.id out to the HUD
if self.caller:
if self.callHud:
for hid in to_hud:
try:
print _("fpdb_import: sending hand to hud"), hand.dbid_hands, "pipe =", self.caller.pipe_to_hud

View File

@ -120,7 +120,7 @@ or None if we fail to get the info """
except AttributeError:
tmp = handText[0:100]
log.error(_("Unable to recognise gametype from: '%s'") % tmp)
log.error(_("determineGameType: Raising FpdbParseError"))
log.error("determineGameType: " + _("Raising FpdbParseError"))
raise FpdbParseError(_("Unable to recognise gametype from: '%s'") % tmp)
self.info = {}
@ -258,7 +258,7 @@ or None if we fail to get the info """
#print "DEBUG: addBringIn(%s, %s)" %(action.group('PNAME'), action.group('BET'))
hand.addBringIn(action.group('PNAME'), action.group('BET'))
else:
logging.error(_("Unimplemented readAction: %s") % (ag))
logging.error(_("DEBUG: ") + _("Unimplemented readAction: '%s' '%s'") % (action.group('PNAME'), action.group('ATYPE')))
def readShowdownActions(self, hand):
for shows in self.re_ShowdownAction.finditer(hand.handText):

Binary file not shown.

Binary file not shown.

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

4226
pyfpdb/locale/fpdb-it_IT.po Normal file

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -9,21 +9,24 @@ msgmerge --update locale/fpdb-de_DE.po locale/fpdb-en_GB.pot
msgmerge --update locale/fpdb-es_ES.po locale/fpdb-en_GB.pot
msgmerge --update locale/fpdb-fr_FR.po locale/fpdb-en_GB.pot
msgmerge --update locale/fpdb-hu_HU.po locale/fpdb-en_GB.pot
msgmerge --update locale/fpdb-it_IT.po locale/fpdb-en_GB.pot
msgmerge --update locale/fpdb-pl_PL.po locale/fpdb-en_GB.pot
msgmerge --update locale/fpdb-ru_RU.po locale/fpdb-en_GB.pot
msgfmt -c locale/fpdb-de_DE.po
msgfmt -c locale/fpdb-es_ES.po
msgfmt -c locale/fpdb-fr_FR.po
msgfmt -c locale/fpdb-hu_HU.po
msgfmt -c locale/fpdb-pl_PL.po
msgfmt -c locale/fpdb-ru_RU.po
msgfmt -c --check-accelerators locale/fpdb-de_DE.po
msgfmt -c --check-accelerators locale/fpdb-es_ES.po
msgfmt -c --check-accelerators locale/fpdb-fr_FR.po
msgfmt -c --check-accelerators locale/fpdb-hu_HU.po
msgfmt -c --check-accelerators locale/fpdb-it_IT.po
msgfmt -c --check-accelerators locale/fpdb-pl_PL.po
msgfmt -c --check-accelerators locale/fpdb-ru_RU.po
echo "compiling mo files"
python /usr/share/doc/python-2.*/examples/Tools/i18n/msgfmt.py --output-file=locale/de/LC_MESSAGES/fpdb.mo locale/fpdb-de_DE.po
python /usr/share/doc/python-2.*/examples/Tools/i18n/msgfmt.py --output-file=locale/es/LC_MESSAGES/fpdb.mo locale/fpdb-es_ES.po
python /usr/share/doc/python-2.*/examples/Tools/i18n/msgfmt.py --output-file=locale/fr/LC_MESSAGES/fpdb.mo locale/fpdb-fr_FR.po
python /usr/share/doc/python-2.*/examples/Tools/i18n/msgfmt.py --output-file=locale/hu/LC_MESSAGES/fpdb.mo locale/fpdb-hu_HU.po
python /usr/share/doc/python-2.*/examples/Tools/i18n/msgfmt.py --output-file=locale/it/LC_MESSAGES/fpdb.mo locale/fpdb-it_IT.po
python /usr/share/doc/python-2.*/examples/Tools/i18n/msgfmt.py --output-file=locale/pl/LC_MESSAGES/fpdb.mo locale/fpdb-pl_PL.po
python /usr/share/doc/python-2.*/examples/Tools/i18n/msgfmt.py --output-file=locale/ru/LC_MESSAGES/fpdb.mo locale/fpdb-ru_RU.po

Binary file not shown.

Binary file not shown.

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 34,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 32,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'PLAYER1': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'PLAYER2': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 1.0,
'wonWhenSeenStreet4': 0.0},
u'PLAYER3': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'PLAYER4': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'PLAYER5': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -629,12 +707,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'PLAYER6': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -734,12 +825,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'PLAYER7': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 13,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 46,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player1': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player3': { 'card1': 26,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 41,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 1.0,
'wonWhenSeenStreet4': 0.0},
u'Player4': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player5': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player7': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -629,12 +707,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player8': { 'card1': 24,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 50,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -734,12 +825,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player9': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 0,
'boardcard4': 5,
'boardcard5': 29,
'gameSessionId': 1,
'gametypeId': 1,
'importTime': None,
'maxSeats': 10,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Villain': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': True,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -1,10 +1,23 @@
{ u'Player1': { 'card1': 29,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 16,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player2': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player3': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player4': { 'card1': 33,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 7,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 1.0,
'wonWhenSeenStreet4': 0.0},
u'Player5': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player6': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -629,12 +707,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player7': { 'card1': 43,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 22,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -734,12 +825,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player8': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -0,0 +1,47 @@
Full Tilt Poker Game #29178537030: Table Broadridge (6 max) - $0.10/$0.20 Ante $0.05 - No Limit 2-7 Single Draw - 01:27:48 ET - 2011/03/20
Seat 1: mrsjoanmac ($20.28)
Seat 2: Thanks4Coming ($22.22)
Seat 3: Hero ($9.95)
Seat 4: N804SY ($17.75), is sitting out
Seat 5: Wayren ($24.81)
Seat 6: Sonny090 ($47.65)
Thanks4Coming antes $0.05
mrsjoanmac antes $0.05
Wayren antes $0.05
Sonny090 antes $0.05
Hero antes $0.05
Wayren posts the small blind of $0.10
Sonny090 posts the big blind of $0.20
The button is in seat #4
*** HOLE CARDS ***
Dealt to Hero [4s Ah Ts 8h 5c]
mrsjoanmac folds
Thanks4Coming folds
Hero has 15 seconds left to act
Hero raises to $0.60
Wayren calls $0.50
Sonny090 calls $0.40
*** DRAW *** (Pot: $2.05)
Wayren discards 1 card
Sonny090 discards 1 card
Hero discards 2 cards [Ah Ts]
Wayren is dealt 1 card
Sonny090 is dealt 1 card
Dealt to Hero [4s 8h 5c] [Qc 5s]
Wayren checks
Sonny090 bets $0.80
Hero folds
Wayren calls $0.80
*** SHOW DOWN ***
Sonny090 shows [Td 9d 8c 7h 3h] T,9,8,7,3
Wayren shows [9s 8s 6c 4h 3d] 9,8,6,4,3
Wayren wins the pot ($3.47) with 9,8,6,4,3
mrsjoanmac is sitting out
*** SUMMARY ***
Total pot $3.65 | Rake $0.18
Seat 1: mrsjoanmac folded before the Draw
Seat 2: Thanks4Coming folded before the Draw
Seat 3: Hero folded after the Draw
Seat 4: N804SY (button) is sitting out
Seat 5: Wayren (small blind) showed [9s 8s 6c 4h 3d] and won ($3.47) with 9,8,6,4,3
Seat 6: Sonny090 (big blind) showed [Td 9d 8c 7h 3h] and lost with T,9,8,7,3

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 0,
'card2': 0,
'card3': 0,
'card4': 0,
'card5': 0,
{ u'Hero': { 'card1': 9,
'card2': 17,
'card3': 13,
'card4': 48,
'card5': 37,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card20': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -110,6 +123,19 @@
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 32,
'card17': 31,
'card18': 29,
'card19': 15,
'card20': 14,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 1.0,
'wonWhenSeenStreet4': 0.0},
u'Player2': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -320,6 +359,19 @@
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 21,
'card17': 7,
'card18': 6,
'card19': 30,
'card20': 40,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player4': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player5': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 0,
'boardcard4': 0,
'boardcard5': 0,
'gameSessionId': 1,
'gametypeId': 12,
'importTime': None,
'maxSeats': 6,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 0,
'card2': 0,
'card3': 0,
'card4': 0,
'card5': 0,
{ u'Hero': { 'card1': 1,
'card2': 24,
'card3': 42,
'card4': 35,
'card5': 27,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card20': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player1': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player4': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player5': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 6,
'card17': 32,
'card18': 33,
'card19': 17,
'card20': 15,
'card2': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player6': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 49,
'card17': 19,
'card18': 30,
'card19': 28,
'card20': 14,
'card2': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -0,0 +1,65 @@
FullTiltPoker Game #27088270000: Table harrington25 (6 max) - $1,500/$3,000 - Limit 2-7 Triple Draw - 11:00:00 ET - 2011/01/08
Seat 1: Player1 ($103,461)
Seat 2: Player2 ($120,106)
Seat 4: Hero ($57,750)
Seat 6: Player6 ($46,497.50)
Player1 posts the small blind of $750
Player2 posts the big blind of $1,500
The button is in seat #6
*** HOLE CARDS ***
Dealt to Hero [5s 3h 4c Qs 8d]
Hero raises to $3,000
Player6 raises to $4,500
Player1 folds
Player2 has 15 seconds left to act
Player2 raises to $6,000
Hero calls $3,000
Player6 calls $1,500
*** FIRST DRAW ***
Player2 discards 1 card
Hero discards 1 card [Qs]
Player6 discards 2 cards
Player2 is dealt 1 card
Dealt to Hero [5s 3h 4c 8d] [2h]
Player6 is dealt 2 cards
Player2 checks
Hero bets $1,500
Player6 raises to $3,000
Player2 calls $3,000
Hero raises to $4,500
Player6 raises to $6,000
Player2 calls $3,000
Hero calls $1,500
*** SECOND DRAW ***
Player2 discards 1 card
Hero stands pat on [5s 3h 4c 8d 2h]
Player6 has 15 seconds left to act
Player6 has requested TIME
Player6 stands pat
Player2 is dealt 1 card
Player2 checks
Hero checks
Player6 checks
*** THIRD DRAW ***
Player2 discards 1 card
Hero stands pat on [5s 3h 4c 8d 2h]
Player6 stands pat
Player2 is dealt 1 card
Player2 bets $3,000
Hero calls $3,000
Player6 folds
*** SHOW DOWN ***
Player2 shows [8s 6d 4s 3d 2c] 8,6,4,3,2
Hero shows [8d 5s 4c 3h 2h] 8,5,4,3,2
Hero wins the pot ($42,748) with 8,5,4,3,2
*** SUMMARY ***
Duration 106s
Total pot $42,750 | Rake $2
Seat 1: Player1 (small blind) folded before the draw
Seat 2: Player2 (big blind) showed [8s 6d 4s 3d 2c] and lost with 8,6,4,3,2
Seat 4: Hero showed [8d 5s 4c 3h 2h] and won ($42,748) with 8,5,4,3,2
Seat 6: Player6 (button) folded after the 3rd Draw

View File

@ -3,6 +3,7 @@
'boardcard3': 0,
'boardcard4': 0,
'boardcard5': 0,
'gameSessionId': 1,
'gametypeId': 1,
'importTime': None,
'maxSeats': 6,

View File

@ -1,10 +1,23 @@
{ u'Player3': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': True,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player4': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': True,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player5': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player6': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 0,
'boardcard4': 0,
'boardcard5': 0,
'gameSessionId': 1,
'gametypeId': 1,
'importTime': None,
'maxSeats': 6,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 0,
'card2': 0,
'card3': 0,
'card4': 0,
'card5': 0,
{ u'Hero': { 'card1': 48,
'card2': 17,
'card3': 44,
'card4': 14,
'card5': 7,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card20': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -110,6 +123,19 @@
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 6,
'card17': 19,
'card18': 45,
'card19': 11,
'card20': 50,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -215,6 +241,19 @@
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 13,
'card17': 52,
'card18': 23,
'card19': 49,
'card20': 2,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -320,6 +359,19 @@
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 10,
'card17': 36,
'card18': 40,
'card19': 1,
'card20': 12,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player4': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 0,
'boardcard4': 0,
'boardcard5': 0,
'gameSessionId': 1,
'gametypeId': 117,
'importTime': None,
'maxSeats': 6,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 0,
'card2': 0,
'card3': 0,
'card4': 0,
'card5': 0,
{ u'Hero': { 'card1': 7,
'card2': 6,
'card3': 32,
'card4': 50,
'card5': 10,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card20': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -110,6 +123,19 @@
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 38,
'card17': 37,
'card18': 30,
'card19': 29,
'card20': 28,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -215,6 +241,19 @@
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 49,
'card17': 36,
'card18': 21,
'card19': 47,
'card20': 43,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player3': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player4': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player6': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 0,
'boardcard4': 0,
'boardcard5': 0,
'gameSessionId': 1,
'gametypeId': 1,
'importTime': None,
'maxSeats': 6,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 0,
'card2': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
{ u'Hero': { 'card1': 24,
'card2': 10,
'card3': 38,
'card4': 11,
'card5': 41,
'card6': 24,
'card7': 11,
'card8': 32,
'card9': 26,
'card10': 28,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card20': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player2': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -215,6 +241,19 @@
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 34,
'card17': 47,
'card18': 21,
'card19': 39,
'card20': 40,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 1.0,
'wonWhenSeenStreet4': 0.0},
u'Player6': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 0,
'boardcard4': 0,
'boardcard5': 0,
'gameSessionId': 1,
'gametypeId': 2,
'importTime': None,
'maxSeats': 7,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 0,
'card2': 0,
'card3': 0,
'card4': 0,
{ u'Hero': { 'card1': 13,
'card2': 50,
'card3': 41,
'card4': 36,
'card5': 0,
'card6': 0,
'card7': 0,
'card6': 13,
'card7': 41,
'card8': 10,
'card9': 33,
'card10': 0,
'card11': 13,
'card12': 41,
'card13': 33,
'card14': 46,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card20': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player2': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player3': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -313,13 +352,27 @@
'wonWhenSeenStreet2': 0.0,
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player4': { 'card1': 0,
u'Player4': {
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 24,
'card17': 42,
'card18': 2,
'card19': 27,
'card20': 0,
'card1': 0,
'card2': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -418,13 +471,27 @@
'wonWhenSeenStreet2': 1.0,
'wonWhenSeenStreet3': 1.0,
'wonWhenSeenStreet4': 0.0},
u'Player5': { 'card1': 0,
u'Player5': {
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 43,
'card17': 3,
'card18': 26,
'card19': 49,
'card20': 0,
'card1': 0,
'card2': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +591,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player6': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -629,12 +709,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player7': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 29,
'card17': 15,
'card18': 40,
'card19': 18,
'card20': 0,
'card2': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 52,
'boardcard4': 17,
'boardcard5': 29,
'gameSessionId': 1,
'gametypeId': 99,
'importTime': None,
'maxSeats': 9,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 47,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 9,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player1': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player2': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player3': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 1.0,
'wonWhenSeenStreet4': 0.0},
u'Player6': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player7': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -629,12 +707,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player8': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 41,
'boardcard4': 42,
'boardcard5': 13,
'gameSessionId': 1,
'gametypeId': 21,
'importTime': None,
'maxSeats': 6,

View File

@ -1,10 +1,23 @@
{ u'AllenCunningham': { 'card1': 19,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 27,
'card20': 0,
'card3': 51,
'card4': 26,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 1.0,
'wonWhenSeenStreet4': 0.0},
u'Erick Lindgren': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Shoe Lab': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'TexasLimitDonk': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'zbubop': { 'card1': 28,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 8,
'card20': 0,
'card3': 52,
'card4': 50,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 0,
'boardcard4': 0,
'boardcard5': 0,
'gameSessionId': 1,
'gametypeId': 7,
'importTime': None,
'maxSeats': 6,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 1,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 34,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': True,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player1': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player2': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player3': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player4': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': True,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player6': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 0,
'boardcard4': 0,
'boardcard5': 0,
'gameSessionId': 1,
'gametypeId': 6,
'importTime': None,
'maxSeats': 9,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 50,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 16,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'MANUTD': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'T0r3x': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'proud2Bwhack': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'ronaldd1969': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'shleekom': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -629,12 +707,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'stark00': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -734,12 +825,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'vision': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -839,12 +943,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'yrthligar': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 8,
'boardcard4': 51,
'boardcard5': 5,
'gameSessionId': 1,
'gametypeId': 8,
'importTime': None,
'maxSeats': 6,

View File

@ -1,10 +1,23 @@
{ u'B_Isreal22': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'DrZartinger': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Hero': { 'card1': 15,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 10,
'card20': 0,
'card3': 42,
'card4': 25,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'ShaDiv': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Timoha777': { 'card1': 24,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 23,
'card20': 0,
'card3': 16,
'card4': 50,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 1.0,
'wonWhenSeenStreet4': 0.0},
u'rockinalex': { 'card1': 49,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 31,
'card20': 0,
'card3': 19,
'card4': 39,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -1,10 +1,23 @@
{ u'FILL A RACK': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 26,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Hero': { 'card1': 43,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 1,
'card20': 0,
'card3': 9,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'arjun1111': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 52,
'card4': 2,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'chasrigg': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 10,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'goulartarm': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 50,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'kwuiyhw': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 34,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -629,12 +707,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'thebear666': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 45,
'card4': 11,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': True,
'foldToOtherRaisedStreet0': False,

View File

@ -0,0 +1,55 @@
Full Tilt Poker Game #29408130000: Table XGod_Of_WarX - $2/$4 Ante $0.40 - Limit Stud H/L - 01:12:00 ET - 2011/03/28
Seat 1: Player1 ($17.70)
Seat 2: Hero ($82.30)
Seat 3: Player3 ($81.70)
Seat 5: Player5 ($95.45)
Seat 6: Player6 ($43.60), is sitting out
Seat 7: Player7 ($435.15)
Seat 8: Player8 ($20.60)
Player5 antes $0.40
Player7 antes $0.40
Player1 antes $0.40
Hero antes $0.40
Player8 antes $0.40
Player3 antes $0.40
*** 3RD STREET ***
Dealt to Player1 [3c]
Dealt to Hero [5d Ah] [Ad]
Dealt to Player3 [7h]
Dealt to Player5 [4c]
Dealt to Player7 [8h]
Dealt to Player8 [5s]
Player1 is low with [3c]
Player1 brings in for $0.50
Hero completes it to $2
Player3 folds
Player5 calls $2
Player7 folds
Player7 is sitting out
Player8 folds
Player1 folds
*** 4TH STREET ***
Dealt to Hero [5d Ah Ad] [6h]
Dealt to Player5 [4c] [7c]
Hero bets $2
Player5 calls $2
*** 5TH STREET ***
Dealt to Hero [5d Ah Ad 6h] [5c]
Dealt to Player5 [4c 7c] [Tc]
Hero bets $4
Player5 folds
Uncalled bet of $4 returned to Hero
Hero mucks
Hero wins the pot ($10.90)
*** SUMMARY ***
Total pot $10.90 | Rake $0
Seat 1: Player1 folded on 3rd St.
Seat 2: Hero collected ($10.90), mucked
Seat 3: Player3 folded on 3rd St.
Seat 5: Player5 folded on 5th St.
Seat 6: Player6 is sitting out
Seat 7: Player7 folded on 3rd St.
Seat 8: Player8 folded on 3rd St.

View File

@ -3,6 +3,7 @@
'boardcard3': 0,
'boardcard4': 0,
'boardcard5': 0,
'gameSessionId': 1,
'gametypeId': 5,
'importTime': None,
'maxSeats': 8,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 18,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 25,
'card20': 0,
'card3': 42,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player2': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 40,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player3': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 4,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player4': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 32,
'card4': 33,
'card5': 16,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player5': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 51,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player7': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 5,
'card4': 8,
'card5': 30,
'card6': 14,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -629,12 +707,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player8': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 45,
'card4': 26,
'card5': 7,
'card6': 28,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 0,
'boardcard4': 0,
'boardcard5': 0,
'gameSessionId': 1,
'gametypeId': 1,
'importTime': None,
'maxSeats': 8,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 36,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 14,
'card20': 0,
'card3': 44,
'card4': 8,
'card5': 34,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player2': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 23,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player3': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 26,
'card4': 10,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player4': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 41,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player5': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 6,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player6': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -629,12 +707,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player7': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 52,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -734,12 +825,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player8': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 37,
'card4': 46,
'card5': 18,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 25,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 51,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 1.0,
'wonWhenSeenStreet4': 0.0},
u'player1': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'player2': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'player4': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'player5': { 'card1': 24,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 11,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -3,6 +3,7 @@
'boardcard3': 50,
'boardcard4': 49,
'boardcard5': 48,
'gameSessionId': 1,
'gametypeId': 1,
'importTime': None,
'maxSeats': 10,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 19,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 22,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -104,12 +117,25 @@
'wonWhenSeenStreet3': 1.0,
'wonWhenSeenStreet4': 0.0},
u'Player10': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -209,12 +235,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player2': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -314,12 +353,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player5': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -419,12 +471,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player7': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -524,12 +589,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player8': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

View File

@ -1,10 +1,23 @@
{ u'Hero': { 'card1': 26,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 7,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -100,12 +113,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player1': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -201,12 +227,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player2': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -302,12 +341,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player3': { 'card1': 1,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 15,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -403,12 +455,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'Player4': { 'card1': 16,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 34,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,
@ -504,12 +569,25 @@
'wonWhenSeenStreet3': 0.0,
'wonWhenSeenStreet4': 0.0},
u'allout96': { 'card1': 0,
'card10': 0,
'card11': 0,
'card12': 0,
'card13': 0,
'card14': 0,
'card15': 0,
'card16': 0,
'card17': 0,
'card18': 0,
'card19': 0,
'card2': 0,
'card20': 0,
'card3': 0,
'card4': 0,
'card5': 0,
'card6': 0,
'card7': 0,
'card8': 0,
'card9': 0,
'foldBbToStealChance': False,
'foldSbToStealChance': False,
'foldToOtherRaisedStreet0': False,

Some files were not shown because too many files have changed in this diff Show More