Ihor Radchenko <yanta...@gmail.com> writes:
> Ignacio Casso <ignacioca...@hotmail.com> writes: > >> Link abbreviations do not work inside property drawers and are instead >> confused with internal links. The following org file illustrates this >> behavior. > > This is to be expected. org-open-at-point does the following: > > ;; No valid link at point. For convenience, look if something > ;; looks like a link under point in some specific places. > ((memq type '(comment comment-block node-property keyword)) > (call-interactively #'org-open-at-point-global)) > > That is, links are only partially recognised inside comments, node > properties, and keywords. > >> I know that there is discussion of whether timestamps and links should >> work or not inside property drawers, but since they currently work, I >> think link abbreviations should be supported too. Let me know if you >> agree and I'll debug the issue and send a patch with a fix proposal. > > I do not think that it is an easy problem to solve properly. > > In the discussion you referenced [1] Nicolas raised the problem that we > cannot modify org-element parser to support links in more contexts as it > may create various issues (e.g. in exporter). > > Without modifying the parser, supporting abbreviations will require code > duplication or referring to internal org-element functions - a fragile > approach. > > I am currently tinkering with an idea to implement several parser > contexts, similar to optional argument in org-at-timestamp-p. > Basically, org-element parser could allow using multiple > named org-element-object-restrictions: 'agenda, 'export, 'lax, etc. > This is not ideal, as Org syntax will be more complex. However, multiple > interpretations of Org syntax are already implemented de facto (e.g. > org-at-timestamp-p). So, centralising the parsing into org-element could > be beneficial. > > Probably, the contexts might be defined by let-bound > org-element-parser-context value. > > Best, > Ihor > > [1] https://orgmode.org/list/877d8llha9....@nicolasgoaziou.fr Actually, I have investigated a little bit and I think the issue is more simple than that: - Link abbreviations rely in the variables `org-link-abbrev-alist' for global abbreviations and `org-link-abbrev-alist-local' for abbreviations defined with #+LINK for a single org file. - `org-open-at-point-global' opens links with `org-link-open-from-string' as opposed to `org-open-at-point', which uses `org-link-open'. - `org-link-open-from-string' ends up using `org-link-open' too, but inside a `with-temp-buffer' form: (defun org-link-open-from-string (s &optional arg) ... (pcase (with-temp-buffer (let ((org-inhibit-startup nil)) (insert s) (org-mode) (goto-char (point-min)) (org-element-link-parser))) (`nil (user-error "No valid link in %S" s)) (link (org-link-open link arg)))) - But in a temporal buffer, `org-link-abbrev-alist-local' is nil, and thus all abbreviations defined with #+LINK are lost. So a simple solution to this would be preserving the value of `org-link-abbrev-alist-local' when switching to the temporal buffer. I think this is orthogonal to the issue of the parser, and it's a bug on its own, since as a user I would expect that evaluating `org-link-open-from-string' would use my current buffer's local values of variables. What do you think? If you agree, I can send a patch fixing it in two lines with something like this: (let ((org-link-abbrev-alist (append org-link-abbrev-alist org-link-abbrev-alist-local))) (pcase (with-temp-buffer ...) ...)) or this: (let ((tmp-var (org-link-abbrev-alist-local))) (pcase (with-temp-buffer (setq org-link-abbrev-alist-local tmp-var) ...) ...)) P.S. There is another variable defined with `defvar-local' in ol.el: `org-target-link-regexp'. I don't know what it is used for but it could potentially suffer from the same problem.