Address omangin's code review.

* This fixes the logic in the `pubs add` command so that an arxiv ID doesn't
  overwrite a DOI.  This also changes the logic so that if an invalid DOI, ISBN,
  or arXiv ID is provided the program will raise an error.

* The code now uses the bibtexparser package to generate the bibtex file for
  arxiv papers.

* A dedicated exception is added for references that can't be found.
main
J. Antognini 7 years ago
parent 30f5f86c9d
commit ccdbe72eb7

@ -1,9 +1,14 @@
"""Interface for Remote Bibliographic APIs"""
import requests
import bibtexparser
from bibtexparser.bibdatabase import BibDatabase
import feedparser
from bs4 import BeautifulSoup
from uis import get_ui
class ReferenceNotFoundException(Exception):
pass
def doi2bibtex(doi):
@ -38,22 +43,21 @@ def arxiv2bibtex(arxiv_id):
entry = feed.entries[0]
if 'title' not in entry:
ui = get_ui()
ui.error('malformed arXiv ID: {}'.format(arxiv_id))
bibtex = None
raise ReferenceNotFoundException('arXiv ID not found.')
elif 'arxiv_doi' in entry:
bibtex = doi2bibtex(entry['arxiv_doi'])
else:
# Create a bibentry from the metadata.
bibtex = '@misc{{{},\n'.format(arxiv_id)
bibtex += 'Author = {'
for i, author in enumerate(entry['authors']):
bibtex += author['name']
if i < len(entry['authors']) - 1:
bibtex += ' and '
bibtex += '},\n'
bibtex += 'Title = {{{}}},\n'.format(entry['title'].strip('\n'))
bibtex += 'Year = {{{}}},\n'.format(entry['published_parsed'].tm_year)
bibtex += 'Eprint = {{arXiv:{}}},\n'.format(arxiv_id)
bibtex += '}'
db = BibDatabase()
author_str = ' and '.join(
[author['name'] for author in entry['authors']])
db.entries = [{
'ENTRYTYPE': 'misc',
'ID': arxiv_id,
'author': author_str,
'title': entry['title'],
'year': str(entry['published_parsed'].tm_year),
'Eprint': arxiv_id,
}]
bibtex = bibtexparser.dumps(db)
return bibtex

@ -84,28 +84,33 @@ def command(conf, args):
# get bibtex entry
if bibfile is None:
if args.doi is None and args.isbn is None:
if args.doi is None and args.isbn is None and args.arxiv is None:
bibentry = bibentry_from_editor(conf, ui, rp)
else:
bibentry = None
if args.doi is not None:
bibentry_raw = apis.doi2bibtex(args.doi)
bibentry = rp.databroker.verify(bibentry_raw)
if bibentry is None:
ui.error('invalid doi {} or unable to retrieve bibfile from it.'.format(args.doi))
if args.isbn is not None:
bibentry_raw = apis.isbn2bibtex(args.isbn)
bibentry = rp.databroker.verify(bibentry_raw)
if bibentry is None:
ui.error('invalid isbn {} or unable to retrieve bibfile from it.'.format(args.isbn))
# TODO distinguish between cases, offer to open the error page in a webbrowser.
# TODO offer to confirm/change citekey
if args.arxiv is not None:
bibentry_raw = apis.arxiv2bibtex(args.arxiv)
bibentry = rp.databroker.verify(bibentry_raw)
if bibentry is None:
ui.error('invalid arxiv id {} or unable to retrieve bibfile from it.'.format(args.arxiv_id))
if bibentry is None:
try:
if args.doi is not None:
bibentry_raw = apis.doi2bibtex(args.doi)
bibentry = rp.databroker.verify(bibentry_raw)
if bibentry is None:
raise apis.ReferenceNotFoundException(
'invalid doi {} or unable to retrieve bibfile from it.'.format(args.doi))
elif args.isbn is not None:
bibentry_raw = apis.isbn2bibtex(args.isbn)
bibentry = rp.databroker.verify(bibentry_raw)
if bibentry is None:
raise apis.ReferenceNotFoundException(
'invalid isbn {} or unable to retrieve bibfile from it.'.format(args.isbn))
# TODO distinguish between cases, offer to open the error page in a webbrowser.
# TODO offer to confirm/change citekey
elif args.arxiv is not None:
bibentry_raw = apis.arxiv2bibtex(args.arxiv)
bibentry = rp.databroker.verify(bibentry_raw)
if bibentry is None:
raise apis.ReferenceNotFoundException(
'invalid arxiv id {} or unable to retrieve bibfile from it.'.format(args.arxiv_id))
except apis.ReferenceNotFoundException as e:
ui.error(e.message)
ui.exit(1)
else:
bibentry_raw = content.get_content(bibfile, ui=ui)

Loading…
Cancel
Save