From ce23f8892a17c2330c89bc21c5253aa5482d8aff Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mattias=20Andr=C3=A9e?= Date: Sat, 3 Nov 2012 09:52:24 +0100 Subject: [PATCH] m fix + metadata collection creation with ponysay-tool --- completion/ponysay-tool | 4 +++ manuals/ponysay.texinfo | 25 ++++++++++--- ponysay-tool.py | 78 ++++++++++++++++++++++++++++++++++++++++- ponysay.py | 8 ++--- setup.py | 15 ++++---- 5 files changed, 115 insertions(+), 15 deletions(-) diff --git a/completion/ponysay-tool b/completion/ponysay-tool index 9b2e72bb..73379fc8 100644 --- a/completion/ponysay-tool +++ b/completion/ponysay-tool @@ -15,4 +15,8 @@ (argumented (option --edit-apply) (complete --edit-apply) (bind --edit) (desc 'Replace all metadata with stash metadata')) + (argumented (option --dimensions) (complete --dimensions) (arg PONYDIR) (files -d *) (desc 'Generate pony dimension file for a directory')) + + (argumented (option --metadata) (complete --metadata) (arg PONYDIR) (files -d *) (desc 'Generate pony metadata collection file for a directory')) + ) diff --git a/manuals/ponysay.texinfo b/manuals/ponysay.texinfo index 47f4dcb6..f5478bae 100644 --- a/manuals/ponysay.texinfo +++ b/manuals/ponysay.texinfo @@ -1105,10 +1105,11 @@ its purpose is to provide tools to ponysay relevant actions that is not printing (like the commands @command{ponysay} and @command{ponythink}). @menu -* Fill KMS cache:: Pre-generate kmsponies to your cache. -* Metadata pasting:: Copy, remove, stash and apply stashed pony metadata. -* Editing metadata:: Editing the metadata in a pony file. -* Dimension files:: Generate pony dimension files. +* Fill KMS cache:: Pre-generate kmsponies to your cache. +* Metadata pasting:: Copy, remove, stash and apply stashed pony metadata. +* Editing metadata:: Editing the metadata in a pony file. +* Metadata collections:: Generate pony metadata collection files. +* Dimension files:: Generate pony dimension files. @end menu @@ -1269,6 +1270,22 @@ Exit the editor, do not forget to save if you have made changes. @end table +@node Metadata collections +@csection Metadata collections +@cindex metadata collection files +@cindex pony metadata collections +@opindex @option{--metadata} +@opindex @option{--restrict} +@opindex @option{-r} + +Pony metadata collection files are used by @command{ponysay} to by just reading +one file per directory determine all pony files metadata and determine which +ponies will pass the @option{--restrict} option when ponies are randomly selected. + +A metadata colletion file's content a list, of pony files with and their corresponding +metadata as a map from tag name to tag value set, serialised with Python's cPickle module. + + @node Dimension files @section Dimension files @cindex dimension files diff --git a/ponysay-tool.py b/ponysay-tool.py index b7e3f444..e0f6b75c 100755 --- a/ponysay-tool.py +++ b/ponysay-tool.py @@ -78,6 +78,9 @@ class PonysayTool(): elif (opts['--dimensions'] is not None) and (len(opts['--dimensions']) == 1): self.generateDimensions(opts['--dimensions'][0]) + elif (opts['--metadata'] is not None) and (len(opts['--metadata']) == 1): + self.generateMetadata(opts['--metadata'][0]) + elif (opts['--edit'] is not None) and (len(opts['--edit']) == 1): pony = opts['--edit'][0] if not os.path.isfile(pony): @@ -286,6 +289,78 @@ class PonysayTool(): file.flush() + ''' + Generate pony metadata collection file for a directory + + @param ponydir The directory + ''' + def generateMetadata(self, ponydir): + if not ponydir.endswith('/'): + ponydir += '/' + def makeset(value): + rc = set() + bracket = 0 + esc = False + buf = '' + for c in value: + if esc: + if bracket == 0: + if c not in (',', '\\', '('. ')'): + buf += '\\' + buf += c + esc = False + elif c == '(': + bracket += 1 + elif c == ')': + if bracket == 0: + raise Exception('Bracket mismatch') + bracket -= 1 + elif c == '\\': + esc = True + elif bracket == 0: + if c == ',': + buf = buf.strip() + if len(buf) > 0: + rc.add(buf) + buf = '' + else: + buf += c + if bracket > 0: + raise Exception('Bracket mismatch') + buf = buf.strip() + if len(buf) > 0: + rc.add(buf) + return rc + everything = [] + for ponyfile in os.listdir(ponydir): + if ponyfile.endswith('.pony') and (ponyfile != '.pony'): + with open(ponydir + ponyfile, 'rb') as file: + data = file.read().decode('utf8', 'replace') + data = [line.replace('\n', '') for line in data.split('\n')] + if data[0] != '$$$': + meta = [] + else: + sep = 1 + while data[sep] != '$$$': + sep += 1 + meta = data[1 : sep] + data = [] + for line in meta: + if ':' in line: + key = line[:line.find(':')].strip() + value = line[line.find(':') + 1:] + test = key + for c in 'ABCDEFGHIJKLMN OPQRSTUVWXYZ': + test = test.replace(c, '') + if (len(test) == 0) and (len(key) > 0): + data.append((key, makeset(value))) + everything.append(ponyfile[:-5], data) + import cPickle + with open(ponydir + 'metadata', 'wb') as file: + cPickle.dump(everything, file, -1) + file.flush() + + ''' Edit a pony file's metadata @@ -825,7 +900,7 @@ if __name__ == '__main__': '%s %s' % (usage_program, '(--edit | --edit-rm) \033[33mPONY-FILE\033[39m'), '%s %s' % (usage_program, '--edit-stash \033[33mPONY-FILE\033[39m > \033[33mSTASH-FILE\033[39m'), '%s %s' % (usage_program, '--edit-apply \033[33mPONY-FILE\033[39m < \033[33mSTASH-FILE\033[39m'), - '%s %s' % (usage_program, '--dimensions \033[33mPONY-DIR\033[39m'), + '%s %s' % (usage_program, '(--dimensions | --metadata) \033[33mPONY-DIR\033[39m'), ]) usage = usage.replace('\033[', '\0') @@ -845,6 +920,7 @@ if __name__ == '__main__': opts.add_argumentless(['-v', '--version'], help = 'Print the version of the program.') opts.add_argumentless(['--kms'], help = 'Generate all kmsponies for the current TTY palette') opts.add_argumented( ['--dimensions'], arg = 'PONY-DIR', help = 'Generate pony dimension file for a directory') + opts.add_argumented( ['--metadata'], arg = 'PONY-DIR', help = 'Generate pony metadata collection file for a directory') opts.add_argumented( ['--edit'], arg = 'PONY-FILE', help = 'Edit a pony file\'s metadata') opts.add_argumented( ['--edit-rm'], arg = 'PONY-FILE', help = 'Remove metadata from a pony file') opts.add_argumented( ['--edit-apply'], arg = 'PONY-FILE', help = 'Apply metadata from stdin to a pony file') diff --git a/ponysay.py b/ponysay.py index 4b4fe827..ad551432 100755 --- a/ponysay.py +++ b/ponysay.py @@ -581,22 +581,22 @@ class Ponysay(): def __init__(self, cellkey, cellvalue): (self.cellkey, self.callvalue) = (key, value) def __call__(self, has): - return False if key not in has else (has[key] != value) + return False if key not in has else (value not in has[key]) class STest: def __init__(self, cellkey, cellvalue): (self.cellkey, self.callvalue) = (key, value) def __call__(self, has): - return False if key not in has else (has[key] ?= value) + return False if key not in has else (value in has[key]) class ITest: def __init__(self, cellkey, cellvalue): (self.cellkey, self.callvalue) = (key, value) def __call__(self, has): - return True if key not in has else (has[key] != value) + return True if key not in has else (value not in has[key]) class NTest: def __init__(self, cellkey, cellvalue): (self.cellkey, self.callvalue) = (key, value) def __call__(self, has): - return True if key not in has else (has[key] == value) + return True if key not in has else (value in has[key]) if strict and invert: return SITest(key, value) if strict: return STest(key, value) if invert: return ITest(key, value) diff --git a/setup.py b/setup.py index 54ba6a30..70b7cd3f 100755 --- a/setup.py +++ b/setup.py @@ -389,12 +389,15 @@ class Setup(): env = conf['custom-env-python'] if env is None: - (out, err) = Popen(['env', 'python', '--version'], stdout=PIPE, stderr=PIPE).communicate() - out = out.decode('utf8', 'replace') + err.decode('utf8', 'replace') - out = out.replace('\n', '') - env = out.split(' ')[1].split('.')[0] - if int(env) < 3: env = 'python3' - else: env = 'python' + try: + (out, err) = Popen(['env', 'python', '--version'], stdout=PIPE, stderr=PIPE).communicate() + out = out.decode('utf8', 'replace') + err.decode('utf8', 'replace') + out = out.replace('\n', '') + env = out.split(' ')[1].split('.')[0] + if int(env) < 3: env = 'python3' + else: env = 'python' + except: + env = 'python3' mane = False for command in commands: if conf[command] is not None: