当前位置: 首页 > 知识库问答 >
问题:

Python中重定向文件流的推荐方法?

阎承嗣
2023-03-14

我正在为一个断断续续变化的sqlite数据库编写一个备份脚本。现在是这样的:

from bz2 import BZ2File
from datetime import datetime
from os.path import dirname, abspath, join
from hashlib import sha512
def backup_target_database(target):
    backup_dir = dirname(abspath(target))
    hash_file = join(backup_dir, 'last_hash')
    new_hash = sha512(open(target, 'rb').read()).digest()
    if new_hash != open(hash_file, 'rb').read():
        fmt = '%Y%m%d-%H%M.sqlite3.bz2'
        snapshot_file = join(backup_dir, datetime.now().strftime(fmt))
        BZ2File(snapshot_file, 'wb').write(open(target, 'rb').read())
        open(hash_file, 'wb').write(new_hash)

目前数据库的重量仅为20MB,因此在运行并将整个文件读入内存时(在检测到更改时执行两次)不会太费力,但我不想等到这成为一个问题。

使用Bashscript术语进行这种流管道的正确方法是什么?

共有1个答案

姬成荫
2023-03-14

首先,您的代码中存在重复(读取目标文件两次)。

您可以将shutil.copyfileobj和hashlib.update用于节省内存的例程。

from bz2 import BZ2File
from datetime import datetime
from hashlib import sha512
from os.path import dirname, abspath, join
from shutil import copyfileobj

def backup_target_database(target_path):
    backup_dir = dirname(abspath(target_path))
    hash_path = join(backup_dir, 'last_hash')
    old_hash = open(hash_path, 'rb').read()
    hasher = sha512()
    with open(target_path, 'rb') as target:
        while True:
            data = target.read(1024)
            if not data:
                break
            hasher.update(data)
        new_hash = hasher.digest()
    if new_hash != old_hash:
        fmt = '%Y%m%d-%H%M.sqlite3.bz2'
        snapshot_path = join(backup_dir, datetime.now().strftime(fmt))
        with open(target_path, 'rb') as target:
            with BZ2File(snapshot_path, 'wb', compresslevel=9) as snapshot:
                copyfileobj(target, snapshot)

(注意:我没有测试此代码。如果您有问题,请通知我)

 类似资料:
  • 问题内容: 如何在Python中将stdout重定向到任意文件? 当从ssh会话中启动运行了很长时间的Python脚本(例如,Web应用程序)并进行背景调整,并且ssh会话关闭时,该应用程序将在尝试写入stdout时引发并失败。我需要找到一种方法来使应用程序和模块输出到文件而不是stdout,以防止由于而导致失败。当前,我使用将输出重定向到文件,并且可以完成工作,但是我想知道是否有一种出于好奇而无

  • 本文向大家介绍Python 读写文件和file对象的方法(推荐),包括了Python 读写文件和file对象的方法(推荐)的使用技巧和注意事项,需要的朋友参考一下 1.open 使用open打开文件后一定要记得调用文件对象的close()方法。比如可以用try/finally语句来确保最后能关闭文件。 file_object = open('thefile.txt') try:      all_

  • 我将我们的web应用程序移动到docker compose部署(Django、DRF、AngularJS)。 Docker现在看起来很稳定,一切都很顺利。 我想: 与您确认,我正在遵循有关应用程序配置文件的最佳做法 知道“卷文件”是否实际上是绑定装载,这是不推荐的 我已经设法使用环境变量和docker-comment秘密读取从Django文件,它的工作原理。缺点是环境变量仅限于简单的字符串,在发送

  • 本文向大家介绍xcode中获取js文件的路径方法(推荐),包括了xcode中获取js文件的路径方法(推荐)的使用技巧和注意事项,需要的朋友参考一下 NSString *filePath = [[NSBundle mainBundle] pathForResource:@"click" ofType:@"js"]; 理论上这样是应该能获取click.js的路径的,但是返回的确是null。 解决方法是

  • 本文向大家介绍Java读写文件方法总结(推荐),包括了Java读写文件方法总结(推荐)的使用技巧和注意事项,需要的朋友参考一下 Java的读写文件方法在工作中相信有很多的用处的,本人在之前包括现在都在使用Java的读写文件方法来处理数据方面的输入输出,确实很方便。奈何我的记性实在是叫人着急,很多时候既然都会想不起来怎么写了,不过我的Java代码量也实在是少的可怜,所以应该多多练习。这里做一个总结,

  • 经典登录模式 本模式适合经典vpn认证模式。用户直接使用私有账户登录vpn获取内网资源,之后经过OA的登录过程进入OA系统。 一些客户不希望用户多输入一遍vpn账号,想要简化流程,于是就产生了本流程的一个变种:在vpn服务器上开启外部认证模式,使用同一账户先登录VPN,之后使用此账户登录OA系统。这样,用户认为是输入了一遍账号密码,实际上依旧是分开进行登录的。 初始化vpn配置 [必需] 添加登录