Python使用MySQL连接器

时间:2015-07-18 00:21:39

标签: mysql python-2.7 mysql-connector-python

我是Python和MySQL的新手。我正在编写代码,查询60个不同的表,每个表包含五分钟内每秒的记录。代码每五分钟执行一次。一些查询可以达到1/2 MB的数据,但大多数都在50 KB范围内。我使用MySQL Connector / Python在运行Windows 7,64位的工作站上运行。我正在使用PowerShell窗口测试我的代码,但代码最终将作为计划任务运行。工作站有足够的RAM(8 GB)。其他进程正在运行,但根据任务管理器,只使用了一半的内存。一般来说,一切都按预期执行,但有时处理挂起。我在代码中插入了print语句(我也使用了调试器跟踪)来确定挂起的位置。它发生在对fetchall的调用上。以下是代码的密切关系部分。所有CAPS都是(伪)常量。

mncdb = mysql.connector.connect(
    option_files=ENV_MCG_MYSQL_OPTION_FILE,
    option_groups=ENV_MCG_MYSQL_OPTION_GROUP,
    host=ut_get_workstation_hostname(),
    database=ENV_MNC_DATABASE_NAME
    )
for generic_table_id in DBR_TABLE_INDEX:
    site_table_id = DBR_SITE_TABLE_NAMES[site_id][generic_table_id]
    db_cursor = mncdb.cursor() 
    db_command = (
                  "SELECT *"
                  +" FROM "
                  +site_table_id
                  +" WHERE "
                  +DBR_DATETIME_FIELD
                  +" >= '"
                  +query_start_time+"'"
                  +" AND "
                  +DBR_DATETIME_FIELD
                  +" < '"
                  +query_end_time+"'"
                 )
    try:
        db_cursor.execute(db_command)
        print "selected data for table "+site_table_id
        try:
            table_info = db_cursor.fetchall()
            print "extracted data for table "+site_table_id
        except:
            print "DB exception "+formatExceptionInfo()
            print "FETCH failed to return any rows..."
            table_info = []
            raise
    except:
        print "uncaught DB error "+formatExceptionInfo()
        raise

。 。 。 其他使用数据的处理 。 。 。         db_cursor.close()     mncdb.close() 。 。 。 没有例外。在单独的PowerShell窗口中,我可以访问代码处理的数据。对于我的测试,在执行代码之前加载数据库中的所有数据。在测试代​​码时,没有进程正在更新数据库。挂起可能在第一次执行代码时或在执行几个小时后发生。

我的问题是什么导致代码挂在fetchall语句上?

2 个答案:

答案 0 :(得分:0)

您可以通过设置提取大小来缓解此问题:

mncdb = mysql.connector.connect(option_files=ENV_MCG_MYSQL_OPTION_FILE, option_groups=ENV_MCG_MYSQL_OPTION_GROUP,host=ut_get_workstation_hostname(,database=ENV_MNC_DATABASE_NAME, cursorclass = MySQLdb.cursors.SSCursor)

但是在执行此操作之前,您还应该在构建语句时使用mysql excuse for prepared statements而不是字符串连接。

答案 1 :(得分:0)

挂起可能涉及MySQL表本身,而不是Python代码。它们包含许多记录吗?他们的桌子很宽吗?它们是否在datetime_field上编入索引?

考虑各种策略:

  1. 专门选择所需的列而不是星号,调用所有列。

  2. 在where子句中使用的DBR_DATETIME_FIELD的索引(即隐式连接)。

  3. 进一步使用打印的计时器print(datetime.datetime.now())进行诊断,以查看哪些是瓶颈表。在这样做时,请务必导入datetime模块。