Capture org-mode with sexp

I am trying to create a capture template that converts a url into an org-mode link with <title> as the link name.

My conversion function looks like this:

 (defun get-page-title (url) "Get title of web page, whose url can be found in the current line" ;; Get title of web page, with the help of functions in url.el (with-current-buffer (url-retrieve-synchronously url) ;; find title by grep the html code (goto-char 0) (re-search-forward "<title>\\([^<]*\\)</title>" nil t 1) (setq web_title_str (match-string 1)) ;; find charset by grep the html code (goto-char 0) ;; find the charset, assume utf-8 otherwise (if (re-search-forward "charset=\\([-0-9a-zA-Z]*\\)" nil t 1) (setq coding_charset (downcase (match-string 1))) (setq coding_charset "utf-8") ;; decode the string of title. (setq web_title_str (decode-coding-string web_title_str (intern coding_charset))) ) (concat "[[" url "][" web_title_str "]]") )) 

When called from normal emacs lisp code, it returns the correct result. But when used in this org-capture-template it returns only bad url .

 setq org-capture-templates (quote (("l" "Link" entry (file+headline "" "Links") "* \"%c\" %(get-page-title \"%c\")")))) 

Is the extension order different? Do I need to avoid the string differently? Magic? The first %c is just them for debugging the string and is actually printed as "url".

Please don’t even bother pointing out that parsing XML using regular expression is the wrong approach. Cthulhu already haunting me, and this will not worsen the situation.

+8
emacs org-mode
source share
3 answers

The problem is the order in which the template options are expanded. Simple % patterns expand after evaluating sexp. The original error message still contains the template and thus extends to the contents of the clipboard, and therefore the error message does not contain the string that was originally passed to get-page-title .

The solution is to access the kill ring from sexp:

 %(get-page-title (current-kill 0)) 

EDIT . This behavior is now logged in org mode.

+7
source share

Was there a solution to use org-protocol.el? http://orgmode.org/worg/org-contrib/org-protocol.html

I just tested it with the following template (adding a subtitle for the desired title as the title).

Template:

 ("t" "Testing Template" entry (file+headline "~/org/capture.org" "Testing") "* %^{Title}\n** %:description\n\n Source: %u, %c\n\n%i" :empty-lines 1) 

Then using a browser (in my case with Opera, although the examples are for Firefox, Uzbl, Acrobat and Conkeror), I was able to capture the following:

 ** Testing for StackExchange *** org-protocol.el - Intercept calls from emacsclient to trigger custom actions Source: [2011-08-05 Fri], [[http://orgmode.org/worg/org-contrib/org-protocol.html] [org-protocol.el - Intercept calls from emacsclient to trigger custom actions]] org-protocol intercepts calls from emacsclient to trigger custom actions without external dependencies. 

(I broke org-link, just to minimize scrolling, it wasn’t on two lines initially)

+6
source share

@aboabo separates an undocumented variable in https://stackoverflow.com/a/312960/ which provides a more general solution to the question of how to use sexp with keyword values ​​in a template (outside of the kill ring). The variable org-store-link-plist stores all the information passed to the capture. Thus, you can access your values ​​directly from such a function:

 (defun url() (plist-get org-store-link-plist :url)) ("w" "capture" entry (file "~/refile.org") "* [[%:link][%:description]] :NOTE:\n%(url)%U\n" :immediate-finish t) 

PS. According to the man page (quote below) this sounds to me the same as your approach to the question. But I agree that you are describing what is really going on - it seems like a mistake regarding the manual.

% (sexp) Evaluate Elisp sexp and replace the result. For convenience,%: keyword (see below) placeholders in the expression will be expanded to this.

+2
source share

All Articles