File: authorlist_format.py

package info (click to toggle)
xraydb 4.5.3-2
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 50,668 kB
  • sloc: python: 3,317; makefile: 75; sh: 18
file content (78 lines) | stat: -rw-r--r-- 3,109 bytes parent folder | download | duplicates (2)
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
67
68
69
70
71
72
73
74
75
76
77
78
import re
import unicodedata
from collections import Counter

from pybtex.style.formatting.unsrt import Style as UnsrtStyle
from pybtex.style.formatting.plain import Style as PlainStyle
from pybtex.style.labels import BaseLabelStyle
from pybtex.plugin import register_plugin

_alphanum_ = re.compile('[^A-Za-z0-9-]+', re.UNICODE)

def strip_accents(s):
    return ''.join((c for c in unicodedata.normalize('NFD', s)
                    if not unicodedata.combining(c)))

def lastname(p):
    s = strip_accents(''.join(p.prelast_names + p.last_names))
    return _alphanum_.sub('', s)

class AuthorsLabelStyle(BaseLabelStyle):
    def format_labels(self, sorted_entries):
        labels = [self.format_label(entry) for entry in sorted_entries]
        count = Counter(labels)
        counted = Counter()
        for label in labels:
            if count[label] == 1:
                yield label
            else:
                yield label + chr(ord('a') + counted[label])
                counted.update([label])

    def format_label(self, entry):
        # see alpha.bst calc.label
        org    = entry.type in ("proceedings", "manual")
        editor = entry.type in ("book", "inbook", "proceedings",
                                "inproceedings")
        author = entry.type not in ("proceedings")
        label = self.generate_label(entry, author=author,
                                    editor=editor, org=org)
        if "year" in entry.fields:
            label = "{:s} ({:s})".format(label, entry.fields["year"])
        return label

    def generate_label(self, entry, author=True, editor=True, org=True):
        result = entry.fields["key"] if "key" in entry.fields else entry.key
        if author and "author" in entry.persons:
            result = self.names2label(entry.persons["author"])
        elif editor and "editor" in entry.persons:
            result = self.names2label(entry.persons["editor"])
        elif org and "organization" in entry.fields:
            result = entry.fields["organization"]
            if result.startswith("The "):
                result = result[4:]
        return result

    def names2label(self, persons):
        numnames = len(persons)
        if numnames == 1:
            result = lastname(persons[0])
        elif numnames == 2:
            result = '{:s} and {:s}'.format(lastname(persons[0]),
                                            lastname(persons[1]))
        elif numnames == 3:
            result = '{:s}, {:s}, and {:s}'.format(lastname(persons[0]),
                                                   lastname(persons[1]),
                                                   lastname(persons[2]))
        else:
            result = '{:s} et al.'.format(lastname(persons[0]))
        return result

class AuthorListPlainStyle(PlainStyle):
    default_label_style = AuthorsLabelStyle

class AuthorListUnsrtStyle(UnsrtStyle):
    default_label_style = AuthorsLabelStyle

register_plugin('pybtex.style.formatting', 'authorlist', AuthorListPlainStyle)
register_plugin('pybtex.style.formatting', 'authorlist_unsrt', AuthorListUnsrtStyle)