record file status between restarts

This commit is contained in:
lilydjwg 2012-12-13 22:47:56 +08:00
parent 28c2683178
commit 727c61703b
3 changed files with 32 additions and 3 deletions

View file

@ -5,7 +5,7 @@ Edit a copy of `archrepo.ini` and then run `./archreposrv <config>`.
DEPENDENCIES DEPENDENCIES
==== ====
* Python, &gt;= 3.3 * Python, &gt;= 3.3, with gdbm support
* tornado, > 2.4.1 * tornado, > 2.4.1
* pyinotify, tested 0.9.4 * pyinotify, tested 0.9.4
* winterpy * winterpy

View file

@ -8,6 +8,9 @@ name: archlinuxcn
# files in this directory, remember to update the configuration of inotify. # files in this directory, remember to update the configuration of inotify.
path: /home/lilydjwg/tmpfs/test path: /home/lilydjwg/tmpfs/test
# A database to store package filenames. Default to ${path}/repofiles.db
#files-db: /home/lilydjwg/tmpfs/test/repofiles.db
# Specify where to find these commands # Specify where to find these commands
#command-add: repo-add #command-add: repo-add
#command-remove: repo-remove #command-remove: repo-remove

View file

@ -7,6 +7,7 @@ import configparser
from functools import partial from functools import partial
import queue import queue
import logging import logging
import dbm.gnu
import pyinotify import pyinotify
from tornado.ioloop import IOLoop from tornado.ioloop import IOLoop
@ -16,6 +17,8 @@ import archpkg
from myutils import enable_pretty_logging from myutils import enable_pretty_logging
enable_pretty_logging(logging.DEBUG) enable_pretty_logging(logging.DEBUG)
# FIXME: 如果一个软件包消失了,那么如果它在仓库数据库里,它就应当从数据库删除。否则不应该
class ActionInfo: class ActionInfo:
def __init__(self, path, action): def __init__(self, path, action):
self.pkginfo = archpkg.parsePkgName(path) self.pkginfo = archpkg.parsePkgName(path)
@ -116,11 +119,13 @@ class RepoMan:
class EventHandler(pyinotify.ProcessEvent): class EventHandler(pyinotify.ProcessEvent):
def my_init(self, config, wm, ioloop=None): def my_init(self, config, wm, ioloop=None):
self.moved_away = {} self.moved_away = {}
self.files = files = set()
self.repomans = {} self.repomans = {}
self._ioloop = ioloop or IOLoop.instance() self._ioloop = ioloop or IOLoop.instance()
base = config.get('path') base = config.get('path')
dbname = config.get('files-db', os.path.join(base, 'repofiles.db'))
self._db = dbm.gnu.open(dbname, 'cs')
dirs = [os.path.join(base, x) for x in ('any', 'i686', 'x86_64')] dirs = [os.path.join(base, x) for x in ('any', 'i686', 'x86_64')]
for d in dirs: for d in dirs:
@ -128,6 +133,15 @@ class EventHandler(pyinotify.ProcessEvent):
wm.add_watch(d, pyinotify.ALL_EVENTS) wm.add_watch(d, pyinotify.ALL_EVENTS)
self.repomans[d] = RepoMan(config, d, self._ioloop) self.repomans[d] = RepoMan(config, d, self._ioloop)
self._initial_update(files)
def _initial_update(self, files):
oldfiles = {f.decode('utf-8') for f in self._db.keys()}
for f in files - oldfiles:
self.dispatch(f, 'add')
for f in oldfiles - files:
self.dispatch(f, 'remove')
def process_IN_CLOSE_WRITE(self, event): def process_IN_CLOSE_WRITE(self, event):
logging.debug('Writing done: %s', event.pathname) logging.debug('Writing done: %s', event.pathname)
self.dispatch(event.pathname, 'add') self.dispatch(event.pathname, 'add')
@ -188,7 +202,7 @@ class EventHandler(pyinotify.ProcessEvent):
newpath = os.path.join(newd, file) newpath = os.path.join(newd, file)
if action == 'add': if action == 'add':
os.symlink(os.path.join('..', arch, file), newpath) os.symlink(os.path.join('..', arch, file), newpath)
self.repomans[newd].add_action(ActionInfo(newpath, action)) self._real_dispatch(newd, ActionInfo(newpath, action))
else: else:
try: try:
os.unlink(newpath) os.unlink(newpath)
@ -197,6 +211,18 @@ class EventHandler(pyinotify.ProcessEvent):
# someone deleted the file for us # someone deleted the file for us
pass pass
self._real_dispatch(d, act)
def _real_dispatch(self, d, act):
key = act.path.encode('utf-8')
if act.action == 'add':
self._db[key] = b'\x01'
else:
try:
del self._db[key]
except KeyError:
logging.warn('files db inconsistent: key %s not there', key)
self.repomans[d].add_action(act) self.repomans[d].add_action(act)
# def process_default(self, event): # def process_default(self, event):