1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
|
#!/usr/bin/python
"""This tool reads a yaml file as generated by importpkg.py on stdin and
updates the database with the contents."""
import sys
from debian.debian_support import version_compare
import sqlalchemy
import yaml
from dedup.utils import enable_sqlite_foreign_keys
def readyaml(conn, stream):
gen = yaml.safe_load_all(stream)
metadata = next(gen)
package = metadata["package"]
row = conn.execute(sqlalchemy.text("SELECT id, version FROM package WHERE name = :name;"),
name=package).fetchone()
if row:
pid, version = row
if version_compare(version, metadata["version"]) > 0:
return
else:
pid = None
cur = conn.execute("SELECT name, id FROM function;")
funcmapping = dict(cur.fetchall())
if pid is not None:
conn.execute(sqlalchemy.text("DELETE FROM content WHERE pid = :pid;"),
pid=pid)
conn.execute(sqlalchemy.text("DELETE FROM dependency WHERE pid = :pid;"),
pid=pid)
conn.execute(sqlalchemy.text("UPDATE package SET version = :version, architecture = :architecture, source = :source WHERE id = :pid;"),
version=metadata["version"],
architecture=metadata["architecture"],
source=metadata["source"], pid=pid)
else:
pid = conn.execute(sqlalchemy.text("INSERT INTO package (name, version, architecture, source) VALUES (:name, :version, :architecture, :source);"),
name=package, version=metadata["version"],
architecture=metadata["architecture"],
source=metadata["source"]).lastrowid
if metadata["depends"]:
conn.execute(sqlalchemy.text("INSERT INTO dependency (pid, required) VALUES (:pid, :required);"),
[dict(pid=pid, required=dep)
for dep in metadata["depends"]])
for entry in gen:
if entry == "commit":
return
cur = conn.execute(sqlalchemy.text("INSERT INTO content (pid, filename, size) VALUES (:pid, :filename, :size);"),
pid=pid, filename=entry["name"], size=entry["size"])
cid = cur.lastrowid
if entry["hashes"]:
conn.execute(sqlalchemy.text("INSERT INTO hash (cid, fid, hash) VALUES (:cid, :fid, :hash);"),
[dict(cid=cid, fid=funcmapping[func], hash=hexhash)
for func, hexhash in entry["hashes"].items()])
raise ValueError("missing commit block")
def main():
db = sqlalchemy.create_engine("sqlite:///test.sqlite3")
enable_sqlite_foreign_keys(db)
with db.begin() as conn:
readyaml(conn, sys.stdin)
if __name__ == "__main__":
main()
|