从内存中的http打开sqlite数据库

4

我有一段代码:

from io import BytesIO as Memory

import requests

def download_file_to_obj(url, file_obj):
    with requests.get(url, stream=True) as r:
        r.raise_for_status()
        for chunk in r.iter_content(chunk_size=None):
            if chunk:
                file_obj.write(chunk)


def main(source_url):
    db_in_mem = Memory()
    print('Downloading..')
    download_file_to_obj(source_url, db_in_mem)
    print('Complete!')
    with sqlite3.connect(database=db_in_mem.read()) as con:
        cursor = con.cursor()
        cursor.execute('SELECT * FROM my_table limit 10;')
        data = cursor.fetchall()
        print(data)
    del(db_in_mem)

my_table 在源数据库中存在。 错误信息:

sqlite3.OperationalError: 没有这样的表:my_table

如何从http加载SQLite数据库到内存中?


1
问题在于sqlite3希望其数据库是一个真正的文件,或者是特殊的:memory:内存数据库。即使备份API也只知道如何在它们之间进行复制,但据我所知,没有一种方法能够使用Python文件对象或内存映像。如果您想走这条路,您将不得不找到一个内存文件系统。您可以查看pyfakefs。由您决定是否值得,或者是否使用真正的文件更简单... - Serge Ballesta
谢谢。我认为“建立一个花园”不值得,使用真正的临时文件更容易。正如Python之禅所述:简单胜于复杂。 - Protect children of Donbas2014
3
类似 https://stackoverflow.com/questions/68054099/query-an-existing-downloaded-sqlite-database-in-python-in-memory-without-having - snakecharmerb
@snakecharmerb 看起来是这样,但实际上不是,因为没有执行 SQL 查询的方法。只需进行转储即可。 - Protect children of Donbas2014
2个回答

3
强制SQLite数据库存在于内存中最常见的方法是使用特殊文件名:memory:打开数据库。换句话说,不是传递实际磁盘文件的名称,而是传递字符串:memory:。例如:
database = sqlite3.connect(":memory:")

当这个操作完成后,不会打开任何磁盘文件,而是在内存中创建一个新的数据库。只要数据库连接关闭,该数据库就会消失。每个 :memory: 数据库都各自独立,互不干扰。因此,如果使用文件名 ":memory:" 打开两个数据库连接,则将创建两个独立的内存数据库。

请注意,为了使特殊名称 :memory: 生效并创建纯粹的内存数据库,文件名中不能有其他文本。因此,可以通过在路径名前面添加路径名来在文件中创建基于磁盘的数据库,例如:./:memory:

更多信息请参见:https://www.sqlite.org/inmemorydb.html


0

你可以在 这个解决方案的基础上建立,并将数据插入到一个内存中的 SQLite 数据库中,使用db = sqlite3.connect(":memory:")语句来创建。你应该能够从这个数据库中执行查询操作。


2
尽量不要过于依赖其他答案,因为它可能随时被删除,这会使得这个答案变得无用。 - Chris van Chip

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接