emacs-orgmode
[Top][All Lists]
Advanced

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

[O] Agenda-like/query language project: org-agenda-ng/org-ql


From: Adam Porter
Subject: [O] Agenda-like/query language project: org-agenda-ng/org-ql
Date: Thu, 10 May 2018 16:41:27 -0500
User-agent: Gnus/5.13 (Gnus v5.13) Emacs/25.2 (gnu/linux)

Hi all,

I've made some improvements to my experimental "org-agenda-ng" project
which might be interesting to some of you.  It also works as a kind of
"query language" for Org files, providing a lispy DSL to
match/filter/select entries in Org files.  It's on GitHub at:

https://github.com/alphapapa/org-agenda-ng

Note that the agenda-like view that it creates is largely compatible
with agenda-related code, because it makes strings with the same
text-properties as the canonical Org agenda view (not guaranteed to be
comprehensive, it's a WIP, but it does most that I'm aware of).  For
example, org-super-agenda can group its views the same way it groups
"real" Org agenda views.

Here are some examples:

#+BEGIN_SRC elisp
  ;; Show an agenda-like view of items in all agenda files with TODO and 
SOMEDAY keywords which are
  ;; tagged "computer" or "Emacs" and in the category "main":
  (org-agenda-ng org-agenda-files
    (and (todo "TODO" "SOMEDAY")
         (tags "computer" "Emacs")
         (category "main")))

  ;; Show an agenda-like view of all habits:
  (org-agenda-ng org-agenda-files
    (habit))

  ;; Show an agenda-like view similar to a "traditional" Org agenda:
  (org-agenda-ng "~/org/main.org"
    (or (habit)
        (date = today)
        (deadline <=)
        (scheduled <= today)
        (and (todo "DONE" "CANCELLED")
             (closed = today))))

  ;; Return a list of Org entry elements which are not done, are tagged 
"Emacs", and have
  ;; priority B or higher:
  (org-ql org-agenda-files
    (and (not (done))
         (tags "Emacs")
         (priority >= "B"))) ;; => ((headline (:raw-value "org-board" :begin 
1220270 :end 1220403 ...)) ...)

  ;; Find the same entries as before, but return a list of heading positions:
  (org-ql "~/org/main.org"
    (and (not (done))
         (tags "Emacs")
         (priority >= "B"))
    :action-fn (lambda (element)
                 (org-element-property :begin element)))  ;; => (44154 46469 
56008 63965 100008 ...)

  ;; Or you can use mapcar around it to get the same result (API is WIP):
  (mapcar (lambda (element)
            (org-element-property :begin element))
          (org-ql "~/org/main.org"
            (and (not (done))
                 (tags "Emacs")
                 (priority >= "B"))))  ;; => (44154 46469 56008 63965 100008 
...)
#+END_SRC

There are a few more ideas I have for improvements, but it has been
whittled down to where I'm fairly happy with it.  I will probably adjust
the org-ql :action-fn so that users can directly control what function
is used to return each matching result, instead of always using
org-element-headline-parser as it currently does (which would improve
performance when users don't need all the element properties).  I may
add some more matchers too, like for properties, regexps, etc.

Performance is not quite on par with the traditional agenda code (which
is more optimized, but also more complicated), but it's pretty good, and
good enough to be useful, I think.  And if Emacs ever gains a faster
Elisp implementation, I think it would be fast enough in all cases.

So my question is, would anyone find this generally useful?  Should I
consider polishing it up and releasing it as a package (in which case,
it would probably be called something like org-ql rather than
org-agenda-ng, and the agenda-like views would be ancillary)?

Any questions, ideas, suggestions, and contributions are welcome.

Thanks,
Adam




reply via email to

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