-
Notifications
You must be signed in to change notification settings - Fork 142
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #121 from Xeophon/main
feat: Add bib-generator
- Loading branch information
Showing
5 changed files
with
128 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,9 @@ | ||
# bib-generator | ||
Generates a bib entry from a matching regex using espanso. | ||
|
||
Requires Python 3 installed on your system. | ||
|
||
## Usage | ||
Just write `:cite:<your search>:` anywhere, it will show 5 results in a form and then replace your text with the .bib entry you selected in the form. It uses the [DBLP](https://dblp.org/) API under the hood, which is restricted to computer science papers only. I highly recommend searching with `<Author> <Some parts of the title>` to improve the search results, as `<Some parts of the title>` often results in irrelevant results. | ||
|
||
Note: Espanso limits the regex matches to 30 characters ([Source](https://github.com/espanso/espanso/security)), so you must limit your query. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
name: "bib-generator" | ||
title: "Bib Generator" | ||
homepage: https://github.com/Xeophon/hub/tree/main/packages/bib-generator | ||
description: Generate a BibTex entry by searching through DBLP | ||
version: 1.0.0 | ||
author: Xeophon | ||
tags: ["bib", "academia", "research"] |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,55 @@ | ||
import sys | ||
import urllib.request | ||
import urllib.parse | ||
import re | ||
|
||
|
||
def get_bib_info(bib): | ||
"""Extracts author, title, and year from a given bib entry.""" | ||
author = re.search(r"author\s*=\s*{(.*?)}", bib, re.DOTALL) | ||
if author is None: | ||
author = re.search(r"editor\s*=\s*{(.*?)}", bib, re.DOTALL) | ||
author = author.group(1) if author is not None else "Unknown" | ||
title = re.search(r"title\s*=\s*{(.*?)}", bib, re.DOTALL).group(1) | ||
year = re.search(r"year\s*=\s*{(.*?)}", bib).group(1) | ||
return author, title, year | ||
|
||
|
||
def format_bib_key(author, title, year): | ||
"""Formats the bib key using author's last name, first three words of the title, and the year.""" | ||
author_lastname = author.split(" and")[0].split()[-1].lower() | ||
first_three_words = "".join( | ||
re.sub(r"[^a-zA-Z]", "", word) for word in title.split()[:3] | ||
) | ||
key = f"{author_lastname}{first_three_words}{year}" | ||
return key | ||
|
||
|
||
def extract_url(selected_entry): | ||
"""Extracts the URL part from the selected entry in the espanso form""" | ||
pattern = r"\(([^()]*\/.*\/[^()]*)\)$" | ||
match = re.search(pattern, selected_entry) | ||
if match: | ||
return match.group(1) | ||
else: | ||
return None | ||
|
||
|
||
def get_bib(selected_entry): | ||
"""Gets the bib from the selected entry in the espanso form""" | ||
full_url = f"https://dblp.org/rec/{extract_url(selected_entry)}.bib" | ||
with urllib.request.urlopen(full_url) as bib_response: | ||
bib = bib_response.read().decode() | ||
if "not found" not in bib: | ||
author, title, year = get_bib_info(bib) | ||
key = format_bib_key(author, title, year) | ||
output = re.sub(r"\{DBLP:.*?\,", "{" + key + ",", bib) | ||
else: | ||
output = "Not found in DBLP" | ||
print(output) | ||
|
||
|
||
try: | ||
get_bib(sys.argv[1]) | ||
except Exception as e: | ||
output = str(e) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,29 @@ | ||
import urllib.request | ||
import urllib.parse | ||
import json | ||
import sys | ||
|
||
|
||
def search(query): | ||
"""Searches for a publication and retrieves the top 5 matches.""" | ||
options = {"q": query, "format": "json", "h": 5} | ||
output = "" | ||
url = f"https://dblp.org/search/publ/api?{urllib.parse.urlencode(options)}" | ||
with urllib.request.urlopen(url) as response: | ||
data = json.loads(response.read().decode()) | ||
hit = data.get("result", {}).get("hits", {}).get("hit", []) | ||
|
||
if hit: | ||
for item in hit: | ||
info = item.get("info", {}) | ||
title = info.get("title", "No title found") | ||
output += f"{title} ({info.get('url').replace("https://dblp.org/rec/", "")})\n" | ||
else: | ||
print("No results found in DBLP") | ||
print(output.strip()) | ||
|
||
|
||
try: | ||
search(sys.argv[1]) | ||
except Exception as e: | ||
output = str(e) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,28 @@ | ||
matches: | ||
- regex: ":cite:(?P<citation>.*?):" | ||
replace: "{{final}}" | ||
vars: | ||
- name: dblp_search_results | ||
type: script | ||
params: | ||
args: | ||
- python | ||
- "%CONFIG%/match/packages/bib-generator/dblp_multi_search.py" | ||
- "{{citation}}" | ||
- name: form1 | ||
type: form | ||
params: | ||
layout: | | ||
Select bib entry: | ||
[[entries]] | ||
fields: | ||
entries: | ||
type: list | ||
values: "{{dblp_search_results}}" | ||
- name: final | ||
type: script | ||
params: | ||
args: | ||
- python | ||
- "%CONFIG%/match/packages/bib-generator/bib_generator.py" | ||
- "{{form1.entries}}" |