This repository provides User Manual for setting up a Docker environment tailored for testing DGTD code.
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 

170 lines
5.7 KiB

# vim: fileencoding=utf-8
# Copyright (c) 2006-2019 Andrey Golovigin
#
# Permission is hereby granted, free of charge, to any person obtaining
# a copy of this software and associated documentation files (the
# "Software"), to deal in the Software without restriction, including
# without limitation the rights to use, copy, modify, merge, publish,
# distribute, sublicense, and/or sell copies of the Software, and to
# permit persons to whom the Software is furnished to do so, subject to
# the following conditions:
#
# The above copyright notice and this permission notice shall be
# included in all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
# IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
# CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
# TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
# SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
from __future__ import unicode_literals
import codecs
from pybtex.bibtex.exceptions import BibTeXError
from pybtex.bibtex.utils import scan_bibtex_string
from pybtex.database.output import BaseWriter
class Writer(BaseWriter):
"""Outputs BibTeX markup"""
unicode_io = True
def quote(self, s):
r"""
>>> w = Writer()
>>> print(w.quote('The World'))
"The World"
>>> print(w.quote(r'The \emph{World}'))
"The \emph{World}"
>>> print(w.quote(r'The "World"'))
{The "World"}
>>> try:
... print(w.quote(r'The {World'))
... except BibTeXError as error:
... print(error)
String has unmatched braces: The {World
"""
self.check_braces(s)
if '"' not in s:
return '"%s"' % s
else:
return '{%s}' % s
def check_braces(self, s):
"""
Raise an exception if the given string has unmatched braces.
>>> w = Writer()
>>> w.check_braces('Cat eats carrots.')
>>> w.check_braces('Cat eats {carrots}.')
>>> w.check_braces('Cat eats {carrots{}}.')
>>> w.check_braces('')
>>> w.check_braces('end}')
>>> try:
... w.check_braces('{')
... except BibTeXError as error:
... print(error)
String has unmatched braces: {
>>> w.check_braces('{test}}')
>>> try:
... w.check_braces('{{test}')
... except BibTeXError as error:
... print(error)
String has unmatched braces: {{test}
"""
tokens = list(scan_bibtex_string(s))
if tokens:
end_brace_level = tokens[-1][1]
if end_brace_level != 0:
raise BibTeXError('String has unmatched braces: %s' % s)
def _encode(self, text):
r"""Encode text as LaTeX.
>>> w = Writer(encoding='ASCII')
>>> print(w._encode(u'1970–1971.'))
1970--1971.
>>> w = Writer(encoding='UTF-8')
>>> print(w._encode(u'1970–1971.'))
1970–1971.
>>> w = Writer(encoding='UTF-8')
>>> print(w._encode(u'100% noir'))
100\% noir
"""
import latexcodec # NOQA
return codecs.encode(text, 'ulatex+{}'.format(self.encoding))
def _encode_with_comments(self, text):
r"""Encode text as LaTeX, preserve comments.
>>> w = Writer(encoding='ASCII')
>>> print(w._encode_with_comments(u'1970–1971. %% † RIP †'))
1970--1971. %% \dag\ RIP \dag
>>> w = Writer(encoding='UTF-8')
>>> print(w._encode_with_comments(u'1970–1971. %% † RIP †'))
1970–1971. %% † RIP †
"""
return u'%'.join(self._encode(part) for part in text.split(u'%'))
def _write_field(self, stream, type, value):
stream.write(u',\n %s = %s' % (type, self.quote(self._encode(value))))
def _format_name(self, stream, person):
def join(l):
return ' '.join([name for name in l if name])
first = person.get_part_as_text('first')
middle = person.get_part_as_text('middle')
prelast = person.get_part_as_text('prelast')
last = person.get_part_as_text('last')
lineage = person.get_part_as_text('lineage')
s = ''
if last:
s += join([prelast, last])
if lineage:
s += ', %s' % lineage
if first or middle:
s += ', '
s += join([first, middle])
return s
def _write_persons(self, stream, persons, role):
# persons = getattr(entry, role + 's')
if persons:
names = u' and '.join(self._format_name(stream, person) for person in persons)
self._write_field(stream, role, names)
def _write_preamble(self, stream, preamble):
if preamble:
stream.write(u'@preamble{%s}\n\n' % self.quote(self._encode_with_comments(preamble)))
def write_stream(self, bib_data, stream):
self._write_preamble(stream, bib_data.preamble)
first = True
for key, entry in bib_data.entries.items():
if not first:
stream.write(u'\n')
first = False
stream.write(u'@%s' % entry.original_type)
stream.write(u'{%s' % key)
# for role in ('author', 'editor'):
for role, persons in entry.persons.items():
self._write_persons(stream, persons, role)
for type, value in entry.fields.items():
self._write_field(stream, type, value)
stream.write(u'\n}\n')