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")))
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
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
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
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
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
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