使用psycopg2向PostgreSQL数据库写入一个git修订哈希(SHA-1)



将诸如f844cdc09651448d6c3e765fadac448253a16928之类的git修订散列(SHA-1)存储到带有psycopg2的PostgreSQL数据库(>v.11)中最有效的方法是什么?

详细信息和代码

我有一个SHA-1哈希,它是Python中的十六进制字符串,我想将其存储在PostgreSQL数据库中:

import psycopg2
from subprocess import Popen, PIPE
psycopg2.__version__ # prints '2.9.1 (dt dec pq3 ext lo64)'
cmd_list = [ "git", "rev-parse", "HEAD", ]
process = Popen(cmd_list, stdout=PIPE, stderr=PIPE)
stdout, stderr = process.communicate()
git_sha1 = stdout.decode('ascii').strip()
conn = psycopg.connect(**DB_PARAMETERS)
curs = conn.cursor()
sql = """UPDATE table SET git_sha1 = %(git_sha1)s WHERE id=1;"""
curs.execute(
sql,
vars = {
"git_sha1": git_sha1
}
)
conn.commit()
conn.close()

目前,我在数据库中有一个git_sha1字段作为VARCHAR(40),但由于数字修订哈希是十六进制字符串,因此最好将字符限制为[0-9a-f]。但我觉得手动只为该字段设置域不舒服。。。我觉得它应该以一种更好、更有力的方式来实现这一点。

那么,在PostgreSQL数据库中编写此类数据是否存在这样一种更好、更优雅的方法呢?

版本控制:

  • Python 3.6.9(默认值,2021年1月26日15:33:00)
  • git版本2.33.1
  • psql(PostgreSQL)12.4(Ubuntu 12.4-1.pgdg18.04+1)
  • Ubuntu 18.04(5.4.0-87通用x86_64 GNU/Linux)

Git ID是SHA-1校验和。它们被表示为40个字符的十六进制字符串,但实际上是20个字节的数字。将它们存储为二进制数据:bytea。这将使存储量减半。

插入时decode为十六进制字符串,提取时encode返回为十六进制。

create temporary table foo ( git_id bytea );
insert into foo (git_id) values 
(
decode('f844cdc09651448d6c3e765fadac448253a16928', 'hex')
);
select encode(git_id, 'hex') from foo;

在psycop2中,或者您可以将其转换为bytes,psycop将做正确的事情。

curs.execute(
sql,
vars = {
"git_sha1": bytes.fromhex(git_sha1)
}
)

请参阅psycop文档中的二进制自适应。

最新更新