예제 #1
0
def add_publications(generator):
    """
    Populates context with a list of BibTeX publications.

    Configuration
    -------------
    generator.settings['PUBLICATIONS']:
        Dictionary that contains bibliographies:
          The key denotes the bibliographies name to use in headers
          The values describe the BibTeX files to read
        Mandatory for this plugin.
    generator.settings['PUBLICATIONS_NAVBAR']:
        Bool denoting whether a navigation bar containing links to each bibliography should be produced.
        Defaults to 'True'.
    generator.settings['PUBLICATIONS_HEADER']:
        Bool denoting whether a header (h2) should be produced for each bibliography.
        Defaults to 'True'.
    generator.settings['PUBLICATIONS_SPLIT']:
        Bool denoting whether bibliographies should be split by year (h3).
        Defaults to 'True'.
    generator.settings['PUBLICATIONS_HIGHLIGHTs']:
        String, e.g., a name, that will be entailed in a <strong> tag to highlight.
        Default: empty

    Output
    ------
    generator.context['publications']:
        Dictionary containing the name of the publication list a a key, bibliography entries as a value.
        A bibliography entry contains of a list of tuples (key, year, text, bibtex, pdf, slides, poster).
        See Readme.md for more details.
    """

    if 'PUBLICATIONS' not in generator.settings:
        return
    if 'PUBLICATIONS_NAVBAR' not in generator.settings:
        generator.context['PUBLICATIONS_NAVBAR'] = True

    try:
        from StringIO import StringIO
    except ImportError:
        from io import StringIO
    try:
        from pybtex.database.input.bibtex import Parser
        from pybtex.database.output.bibtex import Writer
        from pybtex.database import BibliographyData, PybtexError
        from pybtex.backends import html
        from pybtex.style.formatting import plain
    except ImportError:
        logger.warn('`pelican_bibtex` failed to load dependency `pybtex`')
        return

    refs = generator.settings['PUBLICATIONS']
    generator.context['publications'] = collections.OrderedDict()

    for rid in refs:
        ref = refs[rid]
        bibfile = os.path.join(generator.settings['PATH'], ref['file'])
        try:
            bibdata_all = Parser().parse_file(bibfile)
        except PybtexError as e:
            logger.warn('`pelican_bibtex` failed to parse file %s: %s' %
                        (bibfile, str(e)))
            return

        if 'title' in ref:
            title = ref['title']
        else:
            title = rid

        if 'header' in ref:
            header = ref['header']
        else:
            header = True

        if 'split' in ref:
            split = ref['split']
        else:
            split = True

        if 'split_link' in ref:
            split_link = ref['split_link']
        else:
            split_link = True

        if 'bottom_link' in ref:
            bottom_link = ref['bottom_link']
        else:
            bottom_link = True

        if 'all_bibtex' in ref:
            all_bibtex = ref['all_bibtex']
        else:
            all_bibtex = False

        if 'highlight' in ref:
            highlights = ref['highlight']
        else:
            highlights = []

        if 'group_type' in ref:
            group_type = ref['group_type']
        else:
            group_type = False

        publications = []

        # format entries
        plain_style = plain.Style()
        html_backend = html.Backend()
        formatted_entries = plain_style.format_entries(
            bibdata_all.entries.values())

        for formatted_entry in formatted_entries:
            key = formatted_entry.key
            entry = bibdata_all.entries[key]
            year = entry.fields.get('year')
            typee = entry.type

            if entry.fields.get('tags'):
                tags = [
                    tag.strip() for tag in entry.fields.get('tags').split(';')
                ]
            else:
                tags = []

            display_tags = [
                x for x in tags if x != "doi-open" and x != "url-open"
            ]

            # This shouldn't really stay in the field dict
            # but new versions of pybtex don't support pop
            pdf = entry.fields.get('pdf', None)
            slides = entry.fields.get('slides', None)
            poster = entry.fields.get('poster', None)
            doi = entry.fields.get('doi', None)
            url = entry.fields.get('url', None)

            #clean fields from appearing in bibtex and on website
            entry_tmp = entry
            for to_del in ['pdf', 'slides', 'poster', 'tags']:
                entry_tmp.fields.pop(to_del, None)

            #render the bibtex string for the entry
            bib_buf = StringIO()
            bibdata_this = BibliographyData(entries={key: entry_tmp})
            Writer().write_stream(bibdata_this, bib_buf)

            #clean more fields from appearing on website
            for to_del in ['doi', 'url']:
                entry_tmp.fields.pop(to_del, None)

            entry_clean = next(
                plain_style.format_entries(bibdata_this.entries.values()),
                None)

            # apply highlight (strong)
            text = entry_clean.text.render(html_backend)
            for replace in highlights:
                text = text.replace(replace,
                                    '<strong>' + replace + '</strong>')

            publications.append(
                (key, typee, year, text, tags, display_tags,
                 bib_buf.getvalue(), pdf, slides, poster, doi, url))

        generator.context['publications'][rid] = {}
        generator.context['publications'][rid]['title'] = title
        generator.context['publications'][rid]['path'] = os.path.basename(
            bibfile)
        generator.context['publications'][rid]['header'] = header
        generator.context['publications'][rid]['split'] = split
        generator.context['publications'][rid]['bottom_link'] = bottom_link
        generator.context['publications'][rid]['split_link'] = split_link
        generator.context['publications'][rid]['all_bibtex'] = all_bibtex
        generator.context['publications'][rid][
            'data'] = collections.OrderedDict()
        if group_type:
            generator.context['publications'][rid]['data'] = sorted(
                publications,
                key=lambda pub:
                (-int(pub[2].replace("in press", "9999")), pub[1]))
        else:
            generator.context['publications'][rid]['data'] = sorted(
                publications,
                key=lambda pub: -int(pub[2].replace("in press", "9999")))
예제 #2
0
    def add_publications(self):
        # Check if PUBLICATIONS_SRC is set
        if 'PUBLICATIONS_SRC' not in self.settings:
            logger.warn('PUBLICATIONS_SRC not set')
            return

        # Try to parse the bibtex files
        pub_dir = self.settings['PUBLICATIONS_SRC']
        try:
            bibdata_all = BibliographyData()
            for file in os.listdir(pub_dir):
                with codecs.open(pub_dir + os.sep + file, 'r',
                                 encoding="utf8") as stream:
                    bibdata = Parser().parse_stream(stream)
                    key, entry = bibdata.entries.items()[0]
                    bibdata_all.entries[key] = entry
        except PybtexError as e:
            logger.warn('`pelican_bibtex` failed to parse file %s: %s' %
                        (file, str(e)))
            return

        # Create Publication objects and add them to a list
        publications = []

        # format entries
        plain_style = plain.Style()
        formatted_entries = list(
            plain_style.format_entries(bibdata_all.entries.values()))

        decoder = latexcodec.lexer.LatexIncrementalDecoder()

        for entry in bibdata_all.entries:
            raw_tex = BibliographyData(entries={
                entry: bibdata_all.entries[entry]
            }).to_string('bibtex')
            #raw_tex += '\n}'
            formatted_entry = list(
                plain_style.format_entries([bibdata_all.entries[entry]]))[0]

            key = formatted_entry.key
            entry = bibdata_all.entries[key]

            year = entry.fields.get('year', 2018)

            authors = entry.fields.get('author', '').split(' and ')
            print(authors)
            parsed_authors = []
            for author in authors:
                if ',' in author:
                    parsed_authors.append(LatexNodes2Text().latex_to_text(
                        re.sub(r'[\{\}]', '', (author.split(',')[1] + ' ' +
                                               author.split(',')[0]).strip())))
                else:
                    parsed_authors.append(
                        LatexNodes2Text().latex_to_text(author))
            authors = parsed_authors

            title = LatexNodes2Text().latex_to_text(
                entry.fields.get('title', ''))

            pdf = entry.fields.get('pdf', None)
            slides = entry.fields.get('slides', None)
            poster = entry.fields.get('poster', None)

            where = ''
            if 'booktitle' in entry.fields:
                where = LatexNodes2Text().latex_to_text(
                    entry.fields.get('booktitle'))
            elif 'journal' in entry.fields:
                where = LatexNodes2Text().latex_to_text(
                    entry.fields.get('journal'))

            abstract = entry.fields.get('abstract', '')

            pub = Publication(key,
                              authors,
                              title,
                              year,
                              where,
                              abstract=abstract,
                              pdf_url=pdf,
                              resource_urls=[('slides', slides),
                                             ('poster', poster)])
            pub.citations['bib'] = raw_tex.rstrip('\r\n')
            publications.append(pub)
            self.publications_per_year[pub.year].append(pub)
            for author in authors:
                if author in self.context['MEDIUS_AUTHORS'].keys():
                    self.publications_per_author[author].append(pub)
            self.publications_per_type[BIBTEX_TYPE_TO_TEXT[entry.type]].append(
                pub)
            self.publications_per_type_rev[pub] = BIBTEX_TYPE_TO_TEXT[
                entry.type]

        return publications
예제 #3
0
def add_publications(generator):
    """
    Populates context with a list of BibTeX publications.

    Configuration
    -------------
    generator.settings['PUBLICATIONS_SRC']:
        Local path to the BibTeX file to read.

    generator.settings['PUBLICATIONS_SPLIT_BY']:
        The name of the bibtex field used for splitting the publications.
        No splitting if title is not provided.

    generator.settings['PUBLICATIONS_UNTAGGED_TITLE']:
        The title of the header for all untagged entries.
        No such list if title is not provided.

    Output
    ------
    generator.context['publications_lists']:
        A map with keys retrieved from the field named in PUBLICATIONS_SPLIT_TAG.
        Values are lists of tuples (key, year, text, bibtex, pdf, slides, poster)
        See Readme.md for more details.

    generator.context['publications']:
        Contains all publications as a list of tuples
        (key, year, text, bibtex, pdf, slides, poster).
        See Readme.md for more details.
    """
    if 'PUBLICATIONS_SRC' not in generator.settings:
        return
    try:
        from StringIO import StringIO
    except ImportError:
        from io import StringIO
    try:
        from pybtex.database.input.bibtex import Parser
        from pybtex.database.output.bibtex import Writer
        from pybtex.database import BibliographyData, PybtexError
        from pybtex.backends import html
        from pybtex.style.formatting import plain
    except ImportError:
        logger.warn('`pelican_bib` failed to load dependency `pybtex`')
        return

    refs_file = generator.settings['PUBLICATIONS_SRC']
    try:
        bibdata_all = Parser().parse_file(refs_file)
    except PybtexError as e:
        logger.warn('`pelican_bib` failed to parse file %s: %s' %
                    (refs_file, str(e)))
        return

    publications = []
    publications_lists = {}
    publications_untagged = []

    split_by = None
    untagged_title = None

    if 'PUBLICATIONS_SPLIT_BY' in generator.settings:
        split_by = generator.settings['PUBLICATIONS_SPLIT_BY']

    if 'PUBLICATIONS_UNTAGGED_TITLE' in generator.settings:
        untagged_title = generator.settings['PUBLICATIONS_UNTAGGED_TITLE']

    # format entries
    plain_style = plain.Style()
    html_backend = html.Backend()
    formatted_entries = plain_style.format_entries(
        bibdata_all.entries.values())

    for formatted_entry in formatted_entries:
        key = formatted_entry.key
        entry = bibdata_all.entries[key]
        year = entry.fields.get('year')
        # This shouldn't really stay in the field dict
        # but new versions of pybtex don't support pop
        pdf = entry.fields.get('pdf', None)
        slides = entry.fields.get('slides', None)
        poster = entry.fields.get('poster', None)

        tags = []
        if split_by:
            tags = entry.fields.get(split_by, [])

            # parse to list, and trim each string
            if tags:

                tags = [tag.strip() for tag in tags.split(',')]

                # create keys in publications_lists if at least one
                # tag is given
                for tag in tags:
                    publications_lists[tag] = publications_lists.get(tag, [])

        #render the bibtex string for the entry
        bib_buf = StringIO()
        bibdata_this = BibliographyData(entries={key: entry})
        Writer().write_stream(bibdata_this, bib_buf)
        text = formatted_entry.text.render(html_backend)

        entry_tuple = {
            'key': key,
            'year': year,
            'text': text,
            'bibtex': bib_buf.getvalue(),
            'pdf': pdf,
            'slides': slides,
            'poster': poster
        }

        publications.append(entry_tuple)

        for tag in tags:
            publications_lists[tag].append(entry_tuple)

        if not tags and untagged_title:
            publications_untagged.append(entry_tuple)

    # append untagged list if title is given
    if untagged_title and publications_untagged:
        publications_lists[untagged_title] = publications_untagged

    # output
    generator.context['publications'] = publications
    generator.context['publications_lists'] = publications_lists
예제 #4
0
def add_publications(generator):
    """
    Populates context with a list of BibTeX publications.

    Configuration
    -------------
    generator.settings['PUBLICATIONS_SRC']:
        local path to the BibTeX file to read.

    Output
    ------
    generator.context['publications']:
        List of tuples (key, year, text, bibtex, pdf, slides, poster).
        See Readme.md for more details.
    """
    if 'PUBLICATIONS_SRC' not in generator.settings:
        return
    try:
        from StringIO import StringIO
    except ImportError:
        from io import StringIO
    try:
        from pybtex.database.input.bibtex import Parser
        from pybtex.database.output.bibtex import Writer
        from pybtex.database import BibliographyData, PybtexError
        from pybtex.backends import html
        from pybtex.style.formatting import plain
    except ImportError:
        logger.warn('`pelican_bibtex` failed to load dependency `pybtex`')
        return

    refs_file = generator.settings['PUBLICATIONS_SRC']
    try:
        bibdata_all = Parser().parse_file(refs_file)
    except PybtexError as e:
        logger.warn('`pelican_bibtex` failed to parse file %s: %s' % (
            refs_file,
            str(e)))
        return

    publications = []

    # format entries
    plain_style = plain.Style()
    html_backend = html.Backend()
    formatted_entries = plain_style.format_entries(bibdata_all.entries.values())

    for formatted_entry in formatted_entries:
        key = formatted_entry.key
        entry = bibdata_all.entries[key]
        year = entry.fields.get('year')
        # This shouldn't really stay in the field dict
        # but new versions of pybtex don't support pop
        pdf = entry.fields.get('pdf', None)
        slides = entry.fields.get('slides', None)
        poster = entry.fields.get('poster', None)

        #render the bibtex string for the entry
        bib_buf = StringIO()
        bibdata_this = BibliographyData(entries={key: entry})
        Writer().write_stream(bibdata_this, bib_buf)
        text = formatted_entry.text.render(html_backend)

        publications.append((key,
                             year,
                             text,
                             bib_buf.getvalue(),
                             pdf,
                             slides,
                             poster))

    generator.context['publications'] = publications
예제 #5
0
def add_publications(generator):
    """
    Populates context with a list of BibTeX publications.

    Configuration
    -------------
    generator.settings['PUBLICATIONS_SRC']:
        local path to the BibTeX file to read.

    Output
    ------
    generator.context['publications']:
        List of tuples (key, year, text, bibtex, pdf, slides, poster).
        See Readme.md for more details.

    """
    # check if settings are provided via pelicanconf.py
    settings_present = False
    for s in ['PUBLICATIONS_SRC', 'PRESENTATIONS_SRC', 'POSTERS_SRC']:
        if s in generator.settings:
            settings_present = True
    if not settings_present:
        return

    try:
        from StringIO import StringIO
    except ImportError:
        from io import StringIO
    try:
        from pybtex.database.input.bibtex import Parser
        from pybtex.database.output.bibtex import Writer
        from pybtex.database import BibliographyData, PybtexError
        from pybtex.backends import html
        from pybtex.style.formatting import plain
    except ImportError:
        logger.warn('`pelican_bibtex` failed to load dependency `pybtex`')
        return

    for s, c in zip(['PUBLICATIONS_SRC', 'PRESENTATIONS_SRC', 'POSTERS_SRC'],
                    ['publications', 'presentations', 'posters']):
        if s not in generator.settings:
            continue
        refs_file = generator.settings[s]
        try:
            bibdata_all = Parser().parse_file(refs_file)
        except PybtexError as e:
            logger.warn('`pelican_bibtex` failed to parse file %s: %s' %
                        (refs_file, str(e)))
            continue

        publications = []

        # format entries
        plain_style = plain.Style()
        html_backend = html.Backend()
        all_entries = bibdata_all.entries.values()

        # remove URL field if DOI is present
        for entry in all_entries:
            if "doi" in entry.fields.keys():
                entry.fields._dict["url"] = ""

        formatted_entries = plain_style.format_entries(all_entries)
        for formatted_entry in formatted_entries:
            key = formatted_entry.key
            entry = bibdata_all.entries[key]
            year = entry.fields.get('year')
            slides = entry.fields.pop('slides', None)
            poster = entry.fields.pop('poster', None)

            # add PDF link if file is present
            # Zotero exports a 'file' field, which contains the 'Zotero' and
            # 'Filesystem' filenames, seperated by ':'
            try:
                filename = entry.fields['file'].split(':')[0]
                if os.access(os.path.join('content', 'download', filename),
                             os.R_OK):
                    pdf = os.path.join('download', filename)
                else:
                    pdf = None
            except KeyError:
                pdf = None

            #render the bibtex string for the entry
            bib_buf = StringIO()
            bibdata_this = BibliographyData(entries={key: entry})
            Writer().write_stream(bibdata_this, bib_buf)
            text = formatted_entry.text.render(html_backend)
            doi = (entry.fields.get('doi')
                   if 'doi' in entry.fields.keys() else "")
            url = (entry.fields.get('url')
                   if 'url' in entry.fields.keys() else "")

            # prettify entries
            # remove BibTeX's {}
            text = text.replace("\{", "")
            text = text.replace("{", "")
            text = text.replace("\}", "")
            text = text.replace("}", "")
            # subscript 2 in NO2, CO2, SO2
            text = text.replace("NO2", "NO<sub>2</sub>")
            text = text.replace("CO2", "CO<sub>2</sub>")
            text = text.replace("CO2", "CO<sub>2</sub>")
            # for posters and presentations, make for nicer printing
            text = text.replace("In <em>", "Presented at <em>")
            # remove empty URL link
            text = text.replace("<a href=\"\">URL:</a>, ", "")

            publications.append((key, year, text, bib_buf.getvalue(), doi, url,
                                 pdf, slides, poster))

            # store the list of artifacts in the generator context
            generator.context[c] = publications
예제 #6
0
def add_publications(generator):
    """
    Populates context with a list of BibTeX publications.

    Configuration
    -------------
    generator.settings['PUBLICATIONS_SRC']:
        local path to the BibTeX file to read.

    Output
    ------
    generator.context['publications']:
        List of tuples (key, year, text, bibtex, pdf, slides, poster).
        See Readme.md for more details.
    """
    if 'PUBLICATIONS_SRC' not in generator.settings:
        return
    try:
        from StringIO import StringIO
    except ImportError:
        from io import StringIO
    try:
        from pybtex.database.input.bibtex import Parser
        from pybtex.database.output.bibtex import Writer
        from pybtex.database import BibliographyData, PybtexError
        from pybtex.backends import html
        from pybtex.style.formatting import plain
    except ImportError:
        LOGGER.warn('`pelican_bibtex` failed to load dependency `pybtex`')
        return

    try:
        bib_items = Parser().parse_file(generator.settings['PUBLICATIONS_SRC'])
    except PybtexError as err:
        LOGGER.warn('`pelican_bibtex` failed to parse file %s: %s',
                    generator.settings['PUBLICATIONS_SRC'],
                    str(err))
        return

    publications = []

    for fmt_entry in plain.Style().format_entries(bib_items.entries.values()):
        key = fmt_entry.key
        entry = bib_items.entries[key]

        # Render the bibtex string for the entry
        buf = StringIO()
        Writer().write_stream(BibliographyData(entries={key: entry}), buf)

        # Prettify BibTeX entries
        text = fmt_entry.text.render(html.Backend())
        text = text.replace(r"\{", "").replace(r"\}", "")
        text = text.replace("{", "").replace("}", "")

        publications.append({'bibtex' : buf.getvalue(),
                             'doi'    : get_field(entry, 'doi'),
                             'entry'  : entrytype(entry.type),
                             'key'    : key,
                             'pdf'    : get_field(entry, 'pdf'),
                             'poster' : get_field(entry, 'poster'),
                             'slides' : get_field(entry, 'slides'),
                             'text'   : text,
                             'url'    : get_field(entry, 'url'),
                             'note'    : get_field(entry, 'note'),
                             'year'   : entry.fields.get('year'),
                             'authorizer': get_field(entry, 'authorizer'),
                             'acceptance': get_field(entry, 'acceptance'),
                             'stats': get_field(entry, 'stats')
                             })

    generator.context['publications'] = publications
예제 #7
0
def add_publications(generator):
    """
    Populates context with a list of BibTeX publications.

    Configuration
    -------------
    generator.settings['PUBLICATIONS_SRC']:
        local path to the BibTeX file to read.

    Output
    ------
    generator.context['publications']:
        List of tuples (key, year, text, bibtex, pdf, slides, poster).
        See Readme.md for more details.
    """
    if 'PUBLICATIONS_SRC' not in generator.settings:
        return
    try:
        from StringIO import StringIO
    except ImportError:
        from io import StringIO
    try:
        from pybtex.database.input.bibtex import Parser
        from pybtex.database.output.bibtex import Writer
        from pybtex.database import BibliographyData, PybtexError
        from pybtex.backends import html
        from pybtex.style.formatting import plain
    except ImportError:
        logger.warn('`pelican_bibtex` failed to load dependency `pybtex`')
        return

    refs_file = generator.settings['PUBLICATIONS_SRC']
    try:
        bibdata_all = Parser().parse_file(refs_file)
    except PybtexError as e:
        logger.error('`pelican_bibtex` failed to parse file %s: %s' % (
            refs_file,
            str(e)))
        exit(1)
        return

    publications = []

    # format entries
    plain_style = plain.Style()
    html_backend = html.Backend()
    formatted_entries = plain_style.format_entries(bibdata_all.entries.values())

    for formatted_entry in formatted_entries:
        key = formatted_entry.key
        entry = bibdata_all.entries[key]
        year = entry.fields.get('year')
        XEcategory = entry.fields.get('XEcategory')
        XEmember = entry.fields.get('XEmember')
        XEProject = entry.fields.get('XEProject')
        url = entry.fields.get('XEurl')

        #render the bibtex string for the entry
        bib_buf = StringIO()
        bibdata_this = BibliographyData(entries={key: entry})
        Writer().write_stream(bibdata_this, bib_buf)
        text = formatted_entry.text.render(html_backend)

        # publications.append((key,
        #                      year,
        #                      text,
        #                      url,
        #                      XEmember,
        #                      XEcategory,
        #                      XEProject
        #                      ))
        publications.append({'key'    : key,
                             'year'   : year,
                             'text'   : text,
                             'url'    : url,
                             'XEmember' : XEmember,
                             'XEcategory' : XEcategory,
                             'XEProject' : XEProject})

    generator.context['publications'] = publications