Project

General

Profile

1 6620 aaronmk
#!/usr/bin/env python
2
# Translates a data dictionary spreadsheet to Redmine formatting
3
4
import csv
5
import re
6
import sys
7
8
# Spreadsheet format
9
source_sep = ', '
10
11
##### URLs
12
13 6636 aaronmk
url_comment_re = r'(?:\([^)]*\))'
14
15 6620 aaronmk
def simplify_url(url): return re.sub(r'\(.*?\)', r'', url)
16
17 6635 aaronmk
def url_comment_text(comment):
18
    if not comment: return comment
19
20 6638 aaronmk
    match = re.match(r'^\(\d*:?(.*?)\)$', comment)
21 6635 aaronmk
    assert match
22
    text, = match.groups()
23
    return text
24
25 6620 aaronmk
def url_term(url):
26 6637 aaronmk
    '''Prefixes any provider in the URL to the term name, to create a namespace.
27
    Each hierarchical component of the provider is stored in a URL comment.
28
    '''
29
    match = re.match(r'^('+url_comment_re+r'*).*?([\w:-]+)$', url)
30 6620 aaronmk
    assert match
31 6637 aaronmk
    provider_str, term = match.groups()
32
    provider = map(url_comment_text, re.findall(url_comment_re, provider_str))
33
34
    return ':'.join(provider+[term])
35 6620 aaronmk
36
##### Redmine
37
38 6632 aaronmk
def redmine_bold(text): return '*'+text+'*'
39
40 6620 aaronmk
def redmine_url(text, url):
41
    if url: return '"'+text+'":'+url
42
    else: return text
43
44
def source2redmine_url(url):
45 6623 aaronmk
    if url: return redmine_url(url_term(url), simplify_url(url))
46
    else: return ''
47 6620 aaronmk
48
class RedmineTableWriter:
49
    '''Formats rows as a Redmine table'''
50
51
    def __init__(self, stream):
52
        self.stream = stream
53
54
    def writerow(self, row):
55
        self.stream.write(('|'.join(['']+row+['']))+'\n')
56
57
58
def main():
59 6633 aaronmk
    try: _prog_name, term_col, sources_col = sys.argv
60 6626 aaronmk
    except ValueError: raise SystemExit('Usage: '+sys.argv[0]
61 6633 aaronmk
        +' <spreadsheet term_col# sources_col# >redmine')
62
    term_col, sources_col = map(int, [term_col, sources_col])
63 6626 aaronmk
64 6632 aaronmk
    # Translate input
65 6620 aaronmk
    reader = csv.reader(sys.stdin)
66
    writer = RedmineTableWriter(sys.stdout)
67 6632 aaronmk
    writer.writerow(map(redmine_bold, reader.next())) # header
68 6620 aaronmk
    for row in reader:
69
        term = row[term_col]
70 6634 aaronmk
        sources = row[sources_col].split(source_sep)
71 6620 aaronmk
72 6634 aaronmk
        row[term_col] = redmine_url(term, simplify_url(sources[0]))
73 6632 aaronmk
        row[sources_col] = source_sep.join(map(source2redmine_url, sources))
74 6628 aaronmk
75 6632 aaronmk
        writer.writerow(row)
76 6620 aaronmk
77
main()