hgbook
annotate en/cmdref.py @ 371:0801d625fabe
translated up to section 1.8
updated also the status of the project
updated also the status of the project
author | Javier Rojas <jerojasro@devnull.li> |
---|---|
date | Sun Oct 26 17:39:41 2008 -0500 (2008-10-26) |
parents | |
children |
rev | line source |
---|---|
bos@133 | 1 #!/usr/bin/env python |
bos@133 | 2 |
bos@133 | 3 import getopt |
bos@133 | 4 import itertools |
bos@133 | 5 import os |
bos@133 | 6 import re |
bos@133 | 7 import sys |
bos@133 | 8 |
bos@133 | 9 def usage(exitcode): |
bos@133 | 10 print >> sys.stderr, ('usage: %s [-H|--hidden] hg_repo' % |
bos@133 | 11 os.path.basename(sys.argv[0])) |
bos@133 | 12 sys.exit(exitcode) |
bos@133 | 13 |
bos@133 | 14 try: |
bos@133 | 15 opts, args = getopt.getopt(sys.argv[1:], 'AHh?', ['all', 'help', 'hidden']) |
bos@133 | 16 opt_all = False |
bos@133 | 17 opt_hidden = False |
bos@133 | 18 for o, a in opts: |
bos@133 | 19 if o in ('-h', '-?', '--help'): |
bos@133 | 20 usage(0) |
bos@133 | 21 if o in ('-A', '--all'): |
bos@133 | 22 opt_all = True |
bos@133 | 23 if o in ('-H', '--hidden'): |
bos@133 | 24 opt_hidden = True |
bos@133 | 25 except getopt.GetoptError, err: |
bos@133 | 26 print >> sys.stderr, 'error:', err |
bos@133 | 27 usage(1) |
bos@133 | 28 |
bos@133 | 29 try: |
bos@133 | 30 hg_repo, ltx_file = args |
bos@133 | 31 except ValueError: |
bos@133 | 32 usage(1) |
bos@133 | 33 |
bos@133 | 34 if not os.path.isfile(os.path.join(hg_repo, 'mercurial', 'commands.py')): |
bos@133 | 35 print >> sys.stderr, ('error: %r does not contain mercurial code' % |
bos@133 | 36 hg_repo) |
bos@133 | 37 sys.exit(1) |
bos@133 | 38 |
bos@133 | 39 sys.path.insert(0, hg_repo) |
bos@133 | 40 |
bos@133 | 41 from mercurial import commands |
bos@133 | 42 |
bos@133 | 43 def get_commands(): |
bos@133 | 44 seen = {} |
bos@133 | 45 for name, info in sorted(commands.table.iteritems()): |
bos@133 | 46 aliases = name.split('|', 1) |
bos@133 | 47 name = aliases.pop(0).lstrip('^') |
bos@133 | 48 function, options, synopsis = info |
bos@133 | 49 seen[name] = {} |
bos@133 | 50 for shortopt, longopt, arg, desc in options: |
bos@133 | 51 seen[name][longopt] = shortopt |
bos@133 | 52 return seen |
bos@133 | 53 |
bos@133 | 54 def cmd_filter((name, aliases, options)): |
bos@133 | 55 if opt_all: |
bos@133 | 56 return True |
bos@133 | 57 if opt_hidden: |
bos@133 | 58 return name.startswith('debug') |
bos@133 | 59 return not name.startswith('debug') |
bos@133 | 60 |
bos@133 | 61 def scan(ltx_file): |
bos@133 | 62 cmdref_re = re.compile(r'^\\cmdref{(?P<cmd>\w+)}') |
bos@133 | 63 optref_re = re.compile(r'^\\l?optref{(?P<cmd>\w+)}' |
bos@133 | 64 r'(?:{(?P<short>[^}])})?' |
bos@133 | 65 r'{(?P<long>[^}]+)}') |
bos@133 | 66 |
bos@133 | 67 seen = {} |
bos@133 | 68 locs = {} |
bos@133 | 69 for lnum, line in enumerate(open(ltx_file)): |
bos@133 | 70 m = cmdref_re.match(line) |
bos@133 | 71 if m: |
bos@133 | 72 d = m.groupdict() |
bos@133 | 73 cmd = d['cmd'] |
bos@133 | 74 seen[cmd] = {} |
bos@133 | 75 locs[cmd] = lnum + 1 |
bos@133 | 76 continue |
bos@133 | 77 m = optref_re.match(line) |
bos@133 | 78 if m: |
bos@133 | 79 d = m.groupdict() |
bos@133 | 80 seen[d['cmd']][d['long']] = d['short'] |
bos@133 | 81 continue |
bos@133 | 82 return seen, locs |
bos@133 | 83 |
bos@133 | 84 documented, locs = scan(ltx_file) |
bos@133 | 85 known = get_commands() |
bos@133 | 86 |
bos@133 | 87 doc_set = set(documented) |
bos@133 | 88 known_set = set(known) |
bos@133 | 89 |
bos@133 | 90 errors = 0 |
bos@133 | 91 |
bos@133 | 92 for nonexistent in sorted(doc_set.difference(known_set)): |
bos@133 | 93 print >> sys.stderr, ('%s:%d: %r command does not exist' % |
bos@133 | 94 (ltx_file, locs[nonexistent], nonexistent)) |
bos@133 | 95 errors += 1 |
bos@133 | 96 |
bos@133 | 97 def optcmp(a, b): |
bos@133 | 98 la, sa = a |
bos@133 | 99 lb, sb = b |
bos@133 | 100 sc = cmp(sa, sb) |
bos@133 | 101 if sc: |
bos@133 | 102 return sc |
bos@133 | 103 return cmp(la, lb) |
bos@133 | 104 |
bos@133 | 105 for cmd in doc_set.intersection(known_set): |
bos@133 | 106 doc_opts = documented[cmd] |
bos@133 | 107 known_opts = known[cmd] |
bos@133 | 108 |
bos@133 | 109 do_set = set(doc_opts) |
bos@133 | 110 ko_set = set(known_opts) |
bos@133 | 111 |
bos@133 | 112 for nonexistent in sorted(do_set.difference(ko_set)): |
bos@133 | 113 print >> sys.stderr, ('%s:%d: %r option to %r command does not exist' % |
bos@133 | 114 (ltx_file, locs[cmd], nonexistent, cmd)) |
bos@133 | 115 errors += 1 |
bos@133 | 116 |
bos@133 | 117 def mycmp(la, lb): |
bos@133 | 118 sa = known_opts[la] |
bos@133 | 119 sb = known_opts[lb] |
bos@133 | 120 return optcmp((la, sa), (lb, sb)) |
bos@133 | 121 |
bos@133 | 122 for undocumented in sorted(ko_set.difference(do_set), cmp=mycmp): |
bos@133 | 123 print >> sys.stderr, ('%s:%d: %r option to %r command not documented' % |
bos@133 | 124 (ltx_file, locs[cmd], undocumented, cmd)) |
bos@133 | 125 shortopt = known_opts[undocumented] |
bos@133 | 126 if shortopt: |
bos@133 | 127 print '\optref{%s}{%s}{%s}' % (cmd, shortopt, undocumented) |
bos@133 | 128 else: |
bos@133 | 129 print '\loptref{%s}{%s}' % (cmd, undocumented) |
bos@133 | 130 errors += 1 |
bos@133 | 131 sys.stdout.flush() |
bos@133 | 132 |
bos@133 | 133 if errors: |
bos@133 | 134 sys.exit(1) |
bos@133 | 135 |
bos@133 | 136 sorted_locs = sorted(locs.iteritems(), key=lambda x:x[1]) |
bos@133 | 137 |
bos@133 | 138 def next_loc(cmd): |
bos@133 | 139 for i, (name, loc) in enumerate(sorted_locs): |
bos@133 | 140 if name >= cmd: |
bos@133 | 141 return sorted_locs[i-1][1] + 1 |
bos@133 | 142 return loc |
bos@133 | 143 |
bos@133 | 144 for undocumented in sorted(known_set.difference(doc_set)): |
bos@133 | 145 print >> sys.stderr, ('%s:%d: %r command not documented' % |
bos@133 | 146 (ltx_file, next_loc(undocumented), undocumented)) |
bos@133 | 147 print '\cmdref{%s}' % undocumented |
bos@133 | 148 for longopt, shortopt in sorted(known[undocumented].items(), cmp=optcmp): |
bos@133 | 149 if shortopt: |
bos@133 | 150 print '\optref{%s}{%s}{%s}' % (undocumented, shortopt, longopt) |
bos@133 | 151 else: |
bos@133 | 152 print '\loptref{%s}{%s}' % (undocumented, longopt) |
bos@133 | 153 sys.stdout.flush() |
bos@133 | 154 errors += 1 |
bos@133 | 155 |
bos@133 | 156 sys.exit(errors and 1 or 0) |