Subtree agenda restriction is ignored by org-ql-block
yantar92 opened this issue · comments
When I try to apply restriction to an agenda with org-ql-block
, the buffer restriction works as expected, but not the subtree restriction. Instead of only listing matching items from the subtree, org-ql acts as if it was a buffer restriction.
This would probably be fixable, but IIRC the agenda restriction code is not so straightforward.
In general, the org-ql-block feature is not intended to be completely compatible with or to respect all agenda features. To make it so would defeat some of the purpose of org-ql, which is to reimplement some of the agenda's features (maybe most of them, eventually) in a more usable way. The org-ql-block feature exists because it is useful and was simple to implement to the current extent. I probably won't put much effort into adding compatibility with features like this, because I'd rather work on a better agenda-like view (e.g. the wip/view-section
branch).
I see. May I know how the wip/view-section
is different from the existing agenda?
I took another look at the Org Agenda restriction code and found that supporting it isn't as complicated as I expected. This seems to work. Please let me know how it works for you. Thanks.
I just tried the laterst git version of org-ql. Does not seem to work, even though your code looks reasonable. I tried to debug a bit and found that org-agenda-overriding-restriction
was set to nil for some reason (within scope of org-ql-search-block).
As you can see in the code, org-agenda-overriding-restriction
is not bound by this package. Please try to reproduce in emacs -q
or emacs-sandbox.sh to ensure it's not a problem in your config.
I used the following init.el loaded after emacs -q:
(setq straight-repository-branch "develop")
(setq straight-vc-git-default-protocol 'ssh)
(eval-and-compile
(defvar bootstrap-version)
(let ((bootstrap-file
(expand-file-name "straight/repos/straight.el/bootstrap.el" user-emacs-directory))
(bootstrap-version 5))
(unless (file-exists-p bootstrap-file)
(with-current-buffer
(url-retrieve-synchronously
"https://raw.githubusercontent.com/raxod502/straight.el/develop/install.el"
'silent 'inhibit-cookies)
(goto-char (point-max))
(eval-print-last-sexp)))
(load bootstrap-file nil 'nomessage)))
(setq load-prefer-newer t)
(eval-and-compile
(setq load-path (append '("~/.emacs.d/site-lisp/") load-path))
(setq load-path (append (directory-files "~/.emacs.d/site-lisp/" t "^[^.]" t) load-path)))
(eval-and-compile (straight-use-package 'use-package))
(use-package org-ql
:demand t
:straight (org-ql :type git :host github :repo "alphapapa/org-ql")
:init (use-package org-ql-search :demand t))
(defun yant/org-ql-focused-agenda-block (&rest args)
"Return expression, suitable for `org-agenda-custom-commands', which matches focused agenda view."
(org-ql-block
'(and (todo)
(not (priority "C")))))
(add-to-list 'org-agenda-custom-commands
`("D" "Focused agenda (ql version)"
((yant/org-ql-focused-agenda-block))
((org-ql-block-header "Focused agenda(ql version)"))))
The "D" agenda should provide equivalent of default List of TODO entries. However, the org-ql version still gives todos from all the file, ignoring subtree restriction. If needed, I can also provide the .org file.
One blind guess is that org-ql-block
does not have (require 'org-agenda)
, while org-agenda-overriding-restriction
is defined in lexical scope of org-agenda.el
only.
It works for me.
emacs-sandbox.sh -i org-ql
.- Eval:
(setf org-agenda-custom-commands
'(("x" ""
((org-ql-block '(and (todo) (tags "Emacs")))))))
- Open Org file, navigate to subtree.
M-x org-agenda-set-restriction-lock RET
.M-x org-agenda RET x
.
Result: Only entries from the subtree are displayed.
One blind guess is that org-ql-block does not have (require 'org-agenda), while org-agenda-overriding-restriction is defined in lexical scope of org-agenda.el only.
No, org-agenda-overriding-restriction
is a special variable defined in org-agenda.el
, and org-agenda
is already loaded by (require 'org-super-agenda)
. If that were not the case, a compile warning would be raised about an undefined variable.
M-x org-agenda-set-restriction-lock RET.
also made it work for me. I was using M-x org-agenda
< < D
or < < t
with point at the beginning of the subtree.
What command does < <
call and what does it do?
Pressing <
while Agenda Commands buffer is shown will cycle buffer restriction -> subtree restriction -> no restriction for the following agenda view.
I'm asking what Emacs command function is called by the code.
Here's what I see:
org-agenda-set-restriction-lock
sets variableorg-agenda-overriding-restriction
.org-agenda
(search to comment;; Establish the restriction, if any
) does not set variableorg-agenda-overriding-restriction
. Other than that, it seems to do the same things thatorg-agenda-set-restriction-lock
does.- Variable
org-agenda-overriding-restriction
is not documented, so its purpose in Org Agenda is unclear. However, it seems like the only way to determine whether the restriction is intended to be a subtree or a whole file.
Therefore I conclude that the fact that org-agenda
does not set org-agenda-overriding-restriction
may be an oversight and/or a bug that should be fixed. At least, having it set org-agenda-overriding-restriction
would probably do no harm, and would enable other code to determine what the desired restriction mode is, which would make the < <
sequence work here.
As well, the fact that some restriction-setting code seems to be duplicated in org-agenda
and org-agenda-set-restriction-lock
should probably be rectified. If the potential oversight I mentioned is indeed one, having the code duplicated contributed to it happening.
Would you be willing to file a report or raise the discussion on the Org list? I very rarely use Agenda restrictions myself.
I think that there is actually a way to determine if the restriction is set to file or subtree without a need to access to org-agenda-overriding-restriction
. Looking at the code of org-agenda-set-restriction-lock
and the place in org-agenda
where org-agenda-get-restriction-and-command
is called, I can conclude that all you need is three variables: org-agenda-restrict
, org-agenda-restrict-begin
, and org-agenda-restrict-end
. The first variable is non-nil when either 'file or 'subtree/'region restriction is in use. However, the last two are only non-nil when subtree/region restriction is active.
Fixed in 0f5cf5e and 0.4.9. Thanks.