首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >创建db.connection自定义类包装器,继续获取"django.db.utils.InterfaceError:游标已关闭“

创建db.connection自定义类包装器,继续获取"django.db.utils.InterfaceError:游标已关闭“
EN

Stack Overflow用户
提问于 2019-03-31 18:06:45
回答 1查看 915关注 0票数 0

我试图为"django.db.connection“制作自定义的类包装器,但我一直得到"django.db.utils.InterfaceError: django.db.utils.InterfaceError已关闭”。

如果没有自定义类包装器(从./manage.py shell复制),则工作代码如下所示:

代码语言:javascript
复制
>>> from django.db import (connection as con)
>>> with con.cursor() as q:
...     q.execute('select * from master.years a where a.years = %s', [str(2019)])
...     f = [f.name for f in q.description]
...     for b in q:
...             print(dict(zip(f,b)))

我的包装器webapp/mine/db.py

代码语言:javascript
复制
class query_00:
    def __init__(self, db_con, db_sql, db_stmt = []):
        self.db_con = db_con
        self.db_sql = db_sql
        self.fields = []

        with db_con.cursor() as self.query:
            self.query.execute(db_sql, db_stmt)
            self.fields = [f.name for f in self.query.description]

        # for entry in self.query:
            # yield dict(zip(self.fields, entry))

        # self.query = db_con.cursor()

    # must return self, because
    # AttributeError: 'NoneType' object has no attribute 'result'
    def __enter__(self):
        return self
        # self.query.execute(self.db_sql, self.db_stmt)
        # self.fields = [f.name for f in self.query.description]
        # pass

    def __exit__(self, exc_type, exc_value, traceback):
        # is this necessary?
        # self.db_con.close()
        pass

    def result(self):
        for entry in self.query.fetchall():
            yield dict(zip(self.fields, entry))

        # not working
        # for entry in self.query:
            # yield dict(zip(self.fields, entry))

        # not working
        # yield dict(zip(self.fields, entry))

        # pass

然后我在./manage.py shell上尝试输入

代码语言:javascript
复制
from django.db import (connection as con)
from mine.db import query_00
代码语言:javascript
复制
# expected usage, attempt 1
q = query_00(con, 'SELECT * FROM master.years a where a.year = %s', [str(2019),])
for b in q.result():
    print(b)
代码语言:javascript
复制
# expected usage, attempt 2
with query_00(con, 'SELECT * FROM master.years a where a.year = %s', [str(2019),]) as q:
    for b in q.result():
        print(b)

python-3,django-2,postgresql-9

(对不起我的英语)

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2019-04-01 08:12:42

因此,在阅读了文档之后,我意识到连接在init方法中是关闭的。

代码语言:javascript
复制
class query_00:
    def __init__(self, db_con, db_sql, db_stmt = []):
        self.db_con = db_con
        self.db_sql = db_sql
        self.fields = []

        with db_con.cursor() as self.query:
            self.query.execute(db_sql, db_stmt)
            self.fields = [f.name for f in self.query.description]
        # the connection only happend inside "with:" block
        # the connection, was already closed here (after with:)

因此,我只需将游标()保持在变量上

代码语言:javascript
复制
class query_01:
    def __init__(self, db_sql, db_stmt):
        self.db_sql = db_sql
        self.db_stmt = db_stmt
        self.query = connection.cursor()
...

query.execute()放在另一种方法上

代码语言:javascript
复制
...
    def execute(self):
        self.query.execute(self.db_sql, self.db_stmt)
        self.fields = [f.name for f in self.query.description]
...

关于结果()

代码语言:javascript
复制
...
    def result(self):
        self.execute()
        for entry in self.query:
            yield self.keyvalue(entry)
...

那我的班在工作

代码语言:javascript
复制
with query_00('SELECT * FROM master.years a where a.year = %s', [str(2019),]) as q:
    for b in q.result():
        print(b)
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/55443881

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档