#!/usr/bin/python
|
# -*- coding: GBK -*-
|
#
|
##@package
|
#
|
# @todo: ¼Èë·µÀû # Êý¾Ý¿â×Ö¶Î ÇþµÀspid Õ˺Åaccid ÏÉÓñgold ¶Ò»»ËùÔÚ·þserverid
|
#
|
# @author: Alee
|
# @date 2019-1-22 ÏÂÎç03:23:30
|
# @version 1.0
|
#
|
# @note:
|
#
|
#---------------------------------------------------------------------
|
|
import pymongo
|
from pymongo.son_manipulator import SONManipulator
|
import base64
|
from functools import wraps
|
from time import (sleep)
|
|
from lib import CommFunc
|
|
|
class ObjectIdRemover(SONManipulator):
|
def transform_outgoing(self, son, collection):
|
if '_id' in son:
|
del son['_id']
|
return son
|
|
class EncodeStringManipulator(SONManipulator):
|
def __init__(self, encoding):
|
self.encoding = encoding
|
def transform_incoming(self, son, collection):
|
|
def transform_value(value):
|
if isinstance(value, dict):
|
return transform_dict(value)
|
elif isinstance(value, list):
|
return [transform_value(v) for v in value]
|
elif isinstance(value, basestring):
|
result, value = CommFunc.EncodingToUnicode(self.encoding, value)
|
return value
|
return value
|
|
def transform_dict(object):
|
for (key, value) in object.items():
|
object[key] = transform_value(value)
|
return object
|
|
def transform_list(container):
|
for item in container:
|
transform_dict(item)
|
return container
|
|
if isinstance(son, dict):
|
return transform_dict(son)
|
elif isinstance(son, list):
|
return transform_list(son)
|
return son
|
|
def transform_outgoing(self, son, collection):
|
|
def transform_value(value):
|
if isinstance(value, dict):
|
return transform_dict(value)
|
elif isinstance(value, list):
|
return [transform_value(v) for v in value]
|
elif isinstance(value, basestring):
|
result, value =CommFunc.UnicodeToEncoding(self.encoding, value)
|
return value
|
return value
|
|
def transform_dict(object):
|
for (key, value) in object.items():
|
object[key] = transform_value(value)
|
return object
|
|
def transform_list(container):
|
for item in container:
|
transform_dict(item)
|
return container
|
|
if isinstance(son, dict):
|
return transform_dict(son)
|
elif isinstance(son, list):
|
return transform_list(son)
|
return son
|
|
class Base64StringManipulator(SONManipulator):
|
|
def transform_incoming(self, son, collection):
|
|
def transform_value(value):
|
if isinstance(value, dict):
|
return transform_dict(value)
|
elif isinstance(value, list):
|
return [transform_value(v) for v in value]
|
elif isinstance(value, basestring):
|
return base64.b64encode(value)
|
return value
|
|
def transform_dict(object):
|
for (key, value) in object.items():
|
object[key] = transform_value(value)
|
return object
|
|
def transform_list(container):
|
for item in container:
|
transform_dict(item)
|
return container
|
|
if isinstance(son, dict):
|
return transform_dict(son)
|
elif isinstance(son, list):
|
return transform_list(son)
|
return son
|
|
def transform_outgoing(self, son, collection):
|
|
def transform_value(value):
|
if isinstance(value, dict):
|
return transform_dict(value)
|
elif isinstance(value, list):
|
return [transform_value(v) for v in value]
|
elif isinstance(value, basestring):
|
return base64.b64decode(value)
|
return value
|
|
def transform_dict(object):
|
for (key, value) in object.items():
|
object[key] = transform_value(value)
|
return object
|
|
def transform_list(container):
|
for item in container:
|
transform_dict(item)
|
return container
|
|
if isinstance(son, dict):
|
return transform_dict(son)
|
elif isinstance(son, list):
|
return transform_list(son)
|
return son
|
|
#ÓÃÓÚÐÞÊÎDBControllerµÄÊý¾Ý¿â²Ù×÷º¯Êý
|
#¶ÏÏß×Ô¶¯ÖØÊÔ
|
def reconnect_decorator(func):
|
@wraps(func)
|
def wrapper(*args, **kwds):
|
MAX_RECONNECT = 10
|
RECONNECT_INTERVAL = 0.1
|
failCnt = 0
|
while True:
|
try:
|
#È¥µôself
|
return func(*args, **kwds)
|
except pymongo.errors.AutoReconnect, e:
|
failCnt += 1
|
sleep(RECONNECT_INTERVAL)
|
if failCnt > MAX_RECONNECT:
|
raise e
|
|
return wrapper
|
|
class DBController:
|
def __init__(self, host, port, dbName, user, pwd, encoding):
|
self.host = host
|
self.port = port
|
self.dbName = dbName
|
self.user = user
|
self.pwd = pwd
|
|
self.connected = False
|
self.con = None
|
self.db = None
|
self.lastError = None
|
self.translator = None
|
#===========================================================================================
|
# if encoding == 'base64':
|
# self.translator = Base64StringManipulator()
|
# else:
|
# self.translator = EncodeStringManipulator(encoding)
|
#===========================================================================================
|
self.initialize()
|
|
def initialize(self):
|
if not self.connected:
|
if not self.doConnect(self.host, self.port):
|
return False
|
authResult = self.doAuthentication(self.dbName, self.user, self.pwd)
|
if self.db:
|
self.db.add_son_manipulator(ObjectIdRemover())
|
return authResult
|
return True
|
|
def doConnect(self, ip, port):
|
try:
|
self.con = pymongo.Connection(ip, port)
|
except TypeError, typeError:
|
raise
|
except pymongo.errors.ConnectionFailure, failure:
|
self.lastError = failure
|
return False
|
except Exception, e:
|
self.lastError = e
|
return False
|
except:
|
self.lastError = 'Unknown exception occur!'
|
return False
|
self.connected = True
|
return True
|
|
def doAuthentication(self, dbName, user, pwd):
|
if not self.connected or not self.con:
|
self.lastError = 'Not connected yet!'
|
return False
|
self.db = self.con[dbName]
|
authDB = self.con['admin']
|
try:
|
return authDB.authenticate(user, pwd)
|
# return self.db.authenticate(user, pwd)
|
except TypeError, typeError:
|
self.lastError = typeError
|
return False
|
except Exception, e:
|
self.lastError = e
|
return False
|
except:
|
self.lastError = 'Unknown exception occur!'
|
return False
|
|
def find_one(self, colName, spec, filter = None):
|
result, recList = self.find(colName, spec, filter, 1)
|
if not result:
|
return False, None
|
for rec in recList:
|
return True, rec
|
return True, None
|
|
@reconnect_decorator
|
def find(self, colName, spec = None, filter = None, maxCnt = 0, sortBy = None):
|
if not self.connected:
|
if not self.initialize():
|
return False, []
|
|
result = False
|
resultDictList = []
|
col = self.db[colName]
|
if self.translator:
|
spec = self.translator.transform_incoming(spec, None)
|
try:
|
resultCollection = col.find(spec, filter, limit = maxCnt, sort = sortBy)
|
if self.translator:
|
resultDictList = self.translator.transform_outgoing(list(resultCollection), None)
|
else:
|
resultDictList = list(resultCollection)
|
return True, resultDictList
|
except TypeError, typeError:
|
self.lastError = typeError
|
return result, resultDictList
|
except pymongo.errors.OperationFailure, err:
|
self.lastError = err
|
return result, resultDictList
|
except Exception, e:
|
self.lastError = e
|
return result, resultDictList
|
except:
|
self.lastError = 'Unknown exception occur!'
|
return result, resultDictList
|
|
@reconnect_decorator
|
def insert(self, colName, doc_or_docs, isSafe = True):
|
if not self.connected:
|
if not self.initialize():
|
return False
|
|
col = self.db[colName]
|
if self.translator:
|
doc_or_docs = self.translator.transform_incoming(doc_or_docs, None)
|
try:
|
col.insert(doc_or_docs, safe = isSafe)
|
except pymongo.errors.OperationFailure, err:
|
self.lastError = err
|
return False
|
except Exception, e:
|
self.lastError = e
|
return False
|
except:
|
self.lastError = 'Unknown exception occur!'
|
return False
|
return True
|
|
@reconnect_decorator
|
def update(self, colName, spec, doc, isUpsert = False, isSafe = True, isMulti = False):
|
if not self.connected:
|
if not self.initialize():
|
return False
|
|
col = self.db[colName]
|
#ÐèÒªÏȶÔdoc½øÐд¦Àí£¬µ«Óɲ»ÄÜ¿ªÆôcollection.updateµÄmanipulate,ÒòΪÄÇ»áÓ¦ÓÃËùÓд¦Àí
|
if self.translator:
|
spec = self.translator.transform_incoming(spec, None)
|
doc = self.translator.transform_incoming(doc, None)
|
try:
|
col.update(spec, doc, upsert = isUpsert, safe = isSafe, multi = isMulti)
|
except TypeError, typeError:
|
self.lastError = typeError
|
return False
|
except pymongo.errors.OperationFailure, err:
|
self.lastError = err
|
return False
|
except Exception, e:
|
self.lastError = e
|
return False
|
except:
|
self.lastError = 'Unknown exception occur!'
|
return False
|
return True
|
|
@reconnect_decorator
|
def save(self, colName, doc, isSafe = True):
|
if not self.connected:
|
if not self.initialize():
|
return False
|
|
col = self.db[colName]
|
if self.translator:
|
doc = self.translator.transform_incoming(doc, None)
|
try:
|
col.save(doc, safe = isSafe)
|
except TypeError, typeError:
|
self.lastError = typeError
|
return False
|
except pymongo.errors.OperationFailure, err:
|
self.lastError = err
|
return False
|
except Exception, e:
|
self.lastError = e
|
return False
|
except:
|
self.lastError = 'Unknown exception occur!'
|
return False
|
return True
|
|
@reconnect_decorator
|
def remove(self, colName, spec = None, isSafe = True):
|
if not self.connected:
|
if not self.initialize():
|
return False
|
|
col = self.db[colName]
|
if self.translator:
|
spec = self.translator.transform_incoming(spec, None)
|
try:
|
col.remove(spec, safe = isSafe)
|
except pymongo.errors.OperationFailure, err:
|
self.lastError = err
|
return False
|
except Exception, e:
|
self.lastError = e
|
return False
|
except:
|
self.lastError = 'Unknown exception occur!'
|
return False
|
return True
|
|
@reconnect_decorator
|
def drop(self, colName):
|
if not self.connected:
|
if not self.initialize():
|
return False
|
|
col = self.db[colName]
|
try:
|
col.drop()
|
except TypeError, typeError:
|
self.lastError = typeError
|
return False
|
except Exception, e:
|
self.lastError = e
|
return False
|
except:
|
self.lastError = 'Unknown exception occur!'
|
return False
|
return True
|
|
@reconnect_decorator
|
def count(self, colName):
|
if not self.connected:
|
if not self.initialize():
|
return False, 0
|
|
col = self.db[colName]
|
try:
|
cnt = col.count()
|
except pymongo.errors.OperationFailure, err:
|
self.lastError = err
|
return False, 0
|
except Exception, e:
|
self.lastError = e
|
return False, 0
|
except:
|
self.lastError = 'Unknown exception occur!'
|
return False, 0
|
return True, cnt
|
|
|
|
|
def test_DBController():
|
fileIO = open("Bill.txt")
|
# spid accid gold
|
testColName = 'tagDoubleBill'
|
dbController = DBController('localhost', 27017, "DoubleBillDB", 'sa', 'sa', None)
|
|
print "¿ªÊ¼Â¼ÈëÊý¾Ý"
|
cnt = 0
|
spidDict= {}
|
#ÇþµÀSpID Õ˺ÅAccID ÏÉÓñGold ¶Ò»»ËùÔÚ·þServerID
|
for line in fileIO.readlines():
|
try:
|
spID, accID, gold = line.strip().split()
|
except:
|
print "Error:", line
|
continue
|
result, recs = dbController.find(testColName, {"SpID":spID, "AccID":accID})
|
if recs:
|
print "ÖØ¸´²åÈë", spID, accID, gold
|
continue
|
|
doc = {"SpID":spID, "AccID":accID, "Gold":gold, "ServerID":""}
|
result = dbController.insert(testColName, doc)
|
if not result:
|
print "²åÈëʧ°Ü", spID, accID, gold
|
continue
|
|
|
spidDict[spID] = 0
|
cnt += 1
|
|
print "¼ÈëÇþµÀ·µÀû½áÊø£¬×ܹ²%sÌõ, º¬Æ½Ì¨%s"%(cnt, spidDict.keys())
|
|
|
#¿ªÊ¼Â¼ÈëÊý¾Ý
|
#¼ÈëÇþµÀ·µÀû½áÊø£¬×ܹ²681Ìõ, º¬Æ½Ì¨['kupai', 'uc', 'gionee', 'xiaomi', 'vivo', 'lenovo', 'meizu', 'yyb', 'oppo', 'qh360']
|
|
|
def test():
|
|
test_DBController()
|
print 'test ok!'
|
|
if __name__ == '__main__':
|
test()
|
import os
|
os.system("pause")
|