0

tornado/torndb を使用して Web アプリを開発しようとしていますが、データベースのやり取りで問題が発生しています。Web アプリに共通のデータベース機能を提供するために、torndb をラップする「データベース」クラスを作成しました。私が書いたデータベースクラスからメソッドを呼び出すと、データベースへの接続に問題があるようです:

「ERROR:root:localhost で MySQL に接続中にエラーが発生しました」

私のコンストラクターは接続を開くので、接続が開かれた後にこのメッセージが表示される理由について少し混乱しています。これは、私が理解していないスコーピングや GC の問題だと思います。目標は、Database オブジェクトを 1 回作成し、その単一の接続をサーバーの存続期間中維持することです。db は保存されます。

次のコード スニペット期待どおりに動作するため、スコープまたは GC の問題が発生する可能性があります。

#!/usr/bin/python

import torndb

class Database:

def __init__(self):

    try:
        self.__dbh = torndb.Connection(
                'localhost',
                'mydb',
                user = 'myuser',
                password = 'mypass')
    except Exception as e:
        print e


def user_add(self, user, email, passwd):

    insert = "INSERT INTO users (username, email, passwd) VALUES " + \
            "(%s, %s, %s)" % (user, email, passwd)

    rowid = 0
    try:
        rowid = self.__dbh.execute(insert)
    except Exception as e:
        print e

    if rowid is 0:
        return (False, 'User exists');

    return (True, None)


if __name__ == "__main__":
print 'Testing'
raw_input('Hit enter to connect to the DB')

d = Database();


users = []

raw_input('Hit enter to create some users')
for i in range(5):
    users.append(str(i))
    d.user_add(users[i], users[i], users[i])

<-中略->

問題は、Database クラスを定義するモジュールのメイン以外の場所から Database オブジェクトを作成しようとしたときです。たとえば、次のようになります。

import tornado.ioloop
import tornado.httpserver
import tornado.web

from register import Register
from logon import Logon
from db import Database

class Application(tornado.web.Application):

def __init__(self):

    resources = [
            (r"/logon", Logon),
            (r"/register", Register)
            ]

    self.db = Database()
    tornado.web.Application.__init__(self, resources)
    try:
        self.db.user_add('testuser', 'testemail', 'password')
    except Exception as e:
        print e



if __name__ == "__main__":

app = Application()

# Start the server.
server = tornado.httpserver.HTTPServer(app)
server.listen(8080)
tornado.ioloop.IOLoop.instance().start()

上記を実行すると、(self.__dbh.execute() の呼び出しによる) が出力されます。

ERROR:root:localhost の MySQL への接続中にエラーが発生しました

その他の情報:

質問:

  • クラスを定義するモジュールのメインでデータベース オブジェクトを作成する場合と、他の場所でデータベース オブジェクトを作成する場合に違いがあるのはなぜですか?
4

1 に答える 1

1

この問題は、クエリに渡された文字列引数がエスケープされていないことが原因でした。次の変更により機能します。

def user_add(self, user, email, passwd):

    insert = "INSERT INTO users (username, email, passwd) VALUES " + \
            "(\'%s\', \'%s\', \'%s\')" % (user, email, passwd)

    rowid = 0
    try:
        rowid = self.__dbh.execute(insert)
    except Exception as e:
        print e

    if rowid is 0:
        return (False, 'User exists');

    return (True, None)
于 2013-03-04T23:40:14.097 に答える