emacs-orgmode
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [O] org-exp-bibtex missing in git?


From: aaronecay
Subject: Re: [O] org-exp-bibtex missing in git?
Date: Thu, 07 Mar 2013 00:38:55 -0500
User-agent: Notmuch/0.15.2+43~ge848af8 (http://notmuchmail.org) Emacs/24.3.50.1 (x86_64-unknown-linux-gnu)

2013ko martxoak 6an, Bastien-ek idatzi zuen:
> I'd suggest to treat org-link-abbrev-alist and locally defined
> abbreviated links differently when opening the link at point and
> when exporting the buffer.
> 
> At expand time, the exporter could attach a list of export functions
> (filters?) to the expanded link, depending on the local setting for
> the abbreviated link or `org-link-abbrev-alist'.  For example:
> 
>  #+LINK: cite file:my.bib::%s org-latex-bibtex-link
>  
>  (setq org-link-abbrev-alist
>    '(("cite" "file:my.bib::%s" 'org-latex-bibtex-link)))
>  
> Then org-latex-bibtex-link would internally find the link, process
> the BibTeX entry and return a sensible \cite{...} string.
> 
> What do you think?

I’m not sure I understand this proposal correctly.  Specifically, the
exporter needs to know to insert a link to the bib file in the header of
the document (for BibLaTeX, this is the \addbibresource command); I’m
not sure where that information would come from in this proposal: would
the backend have to inspect the value of ‘org-link-abbrev-alist’?

I’ve got some mostly-working code that exports citations, only for
latex, using a different approach (similar to Eric’s).  I’ve cleaned it
up some, and attached it as a patch to this email.  It uses the
following syntax for links: [[type:key;pre;post][desc]].  I agree with
Eric that an expanded syntax for encoding pre and post citation commands
would be welcome.  This code does insert the commands to load the bibtex
file(s) into the document’s header.  It shoudl support multiple bib
files, as well as setting the file with an EXPORT_BIBLIOGRAPHY property
on a subtree, though I haven’t tested either of those functions
thoroughly.  It also supports following a link to either a bibtex file
or (if you manage your bibliography with org-bibtex) an org file.

Things it doesn’t yet do:
- automatically insert the latex code to print the bibliography (because
  I couldn’t think of a way to do this customizably enough – someone
  might want to have the bibliography at the end, not at the end, one
  bibliography per section, ...)
- automatically insert the proper \usepackage into the header.  I think
  the code should eventually do this, but Nicolas might disagree that
  that should instead go into org-latex-classes.

Obviously this code needs work, but perhaps it can be a base on which to
build.  Supporting non-biblatex latex packages is an obvious low-hanging
fruit.  Support for HTML could probably come from citeproc-js
(https://bitbucket.org/fbennett/citeproc-js/wiki/Home), but I will leave
work on that to someone who is more familiar with HTML/JS/the ox-html
backend than I.

>From 044f84632ecf8518184f45802a97a9fa91f9a6d6 Mon Sep 17 00:00:00 2001
From: Aaron Ecay <address@hidden>
Date: Thu, 7 Mar 2013 00:22:07 -0500
Subject: [PATCH] Support export of bibliography links (WIP)

---
 lisp/ox-bib.el   | 108 +++++++++++++++++++++++++++++++++++++++++++++++++++++++
 lisp/ox-latex.el |   8 +++++
 lisp/ox.el       |   1 +
 3 files changed, 117 insertions(+)
 create mode 100644 lisp/ox-bib.el

diff --git a/lisp/ox-bib.el b/lisp/ox-bib.el
new file mode 100644
index 0000000..d726e31
--- /dev/null
+++ b/lisp/ox-bib.el
@@ -0,0 +1,108 @@
+(require 'bibtex)
+(require 'ox)
+
+(defvar ox-bib-find-entries-in-org-file nil
+  "Whether to look for bibliogrpahy entries in an org mode file
+or a bibtex file.")
+
+(defun ox-bib-get-bibliography ()
+  (mapcar (lambda (s)
+            (org-no-properties s))
+         ;; Don't explode if before the first headline
+          (or
+           (condition-case nil
+               (plist-get (org-export-get-environment nil t) :bibliography)
+             (error nil))
+           (save-excursion
+             (widen)
+             (goto-char (point-min))
+             (plist-get (org-export-get-environment) :bibliography)))))
+
+(defun ox-bib-get-key (path &optional desc)
+  "Extract cite key from a link path and desc.
+
+Currently expects links in the format:
+\[[type:key;pre;post;][desc]]"
+  (nth 0 (split-string path ";")))
+
+(defun ox-bib-get-pre (path &optional desc)
+  "Extract pre-citation arg from a link path and desc.
+
+Currently expects links in the format:
+\[[type:key;pre;post;][desc]]"
+  (or (nth 1 (split-string path ";")) ""))
+
+(defun ox-bib-get-post (path &optional desc)
+  "Extract post-citation arg from a link path and desc.
+
+Currently expects links in the format:
+\[[type:key;pre;post;][desc]]"
+  (or (nth 2 (split-string path ";")) ""))
+
+;; Adapted from org-find-entry-with-custom-id; there might be a better
+;; way to do this
+(defun org-find-entry-with-custom-id (ident)
+  (let ((id ident)
+        (case-fold-search nil))
+    (save-excursion
+      (save-restriction
+        (widen)
+        (goto-char (point-min))
+        (when (re-search-forward
+               (concat "^[ \t]*:CUSTOM_ID:[ \t]+" (regexp-quote id) "[ \t]*$")
+               nil t)
+          (org-back-to-heading t)
+          (point))))))
+
+(defun ox-bib-cite-follow (path)
+  (let* ((files (ox-bib-get-bibliography))
+        (key (ox-bib-get-key path))
+        file done)
+    (when ox-bib-find-entries-in-org-file
+      (setq files
+           (mapcar (lambda (s)
+                     (replace-regexp-in-string "\\.bib\\'" ".org" s))
+                   files)))
+    (while (and (car-safe files) (not done))
+      (setq file (car-safe files))
+      (when (file-exists-p file)
+        (let* ((buf (find-file-noselect file))
+
+              (pos (with-current-buffer buf
+                     (cond
+                      (ox-bib-find-entries-in-org-file
+                       (org-find-entry-with-custom-id key))
+                      (t (bibtex-search-entry key))))))
+         (when pos
+           (setq done (cons buf pos)))))
+      (setq files (cdr files)))
+    (if done
+       (progn
+          (pop-to-buffer (car done))
+         (goto-char (cdr done))
+          (when ox-bib-find-entries-in-org-file
+            (org-show-context)))
+      (message "Citation not found: %s" key))))
+
+(defun ox-bib-textcite-export (path desc format)
+  (cond
+   ((org-export-derived-backend-p format 'latex)
+    (let ((key (ox-bib-get-key path desc))
+         (pre (ox-bib-get-pre path desc))
+         (post (ox-bib-get-post path desc)))
+      (format "\\textcite[%s][%s]{%s}" pre post key)))
+   (t
+    (format "<textcite to: %s>" path))))
+
+(defun ox-bib-parencite-export (path desc format)
+  (cond
+   ((org-export-derived-backend-p format 'latex)
+    (let ((key (ox-bib-get-key path desc))
+          (pre (ox-bib-get-pre path desc))
+          (post (ox-bib-get-post path desc)))
+      (format "\\parencite[%s][%s]{%s}" pre post key)))
+   (t
+    (format "<parencite to: %s>" path))))
+
+(org-add-link-type "textcite" #'ox-bib-cite-follow #'ox-bib-textcite-export)
+(org-add-link-type "parencite" #'ox-bib-cite-follow #'ox-bib-parencite-export)
diff --git a/lisp/ox-latex.el b/lisp/ox-latex.el
index 8a5b6a6..ed5dcad 100644
--- a/lisp/ox-latex.el
+++ b/lisp/ox-latex.el
@@ -1153,6 +1153,14 @@ holding export options."
               (or (plist-get info :description) "")
               (if (not (plist-get info :with-creator)) ""
                 (plist-get info :creator))))
+     ;; Bibliography
+     (let* ((bibs (plist-get info :bibliography))
+            (bib-cmds (mapconcat (lambda (s)
+                                   (format "\\addbibresource{%s}" s))
+                                 bibs "\n")))
+       (if bibs
+          (concat bib-cmds "\n")
+        ""))
      ;; Document start.
      "\\begin{document}\n\n"
      ;; Title command.
diff --git a/lisp/ox.el b/lisp/ox.el
index 3a0764d..bdff5ee 100644
--- a/lisp/ox.el
+++ b/lisp/ox.el
@@ -118,6 +118,7 @@
     (:select-tags "SELECT_TAGS" nil org-export-select-tags split)
     (:time-stamp-file nil "timestamp" org-export-time-stamp-file)
     (:title "TITLE" nil nil space)
+    (:bibliography "BIBLIOGRAPHY" nil nil split)
     (:with-archived-trees nil "arch" org-export-with-archived-trees)
     (:with-author nil "author" org-export-with-author)
     (:with-clocks nil "c" org-export-with-clocks)
-- 
1.8.1.5


-- 
Aaron Ecay

reply via email to

[Prev in Thread] Current Thread [Next in Thread]