Merge: v0.8.5

This commit is contained in:
Adam Porter 2024-02-21 05:47:17 -06:00
commit f5cda3d127
4 changed files with 167 additions and 147 deletions

View file

@ -557,6 +557,12 @@ Simple links may also be written manually in either sexp or non-sexp form, like:
Nothing new yet.
** 0.8.5
*Fixes*
+ Predicate ~heading~ incorrectly matched strings as regular expressions, sometimes returning incorrect results. (See [[https://github.com/alphapapa/org-ql/discussions/410][discussion]]. Thanks to [[https://github.com/al3xandru][Alex Popescu]] for reporting.)
+ Predicates ~ancestor~ and ~parent~ did not normalize their sub-queries, sometimes returning incorrect results. ([[https://github.com/alphapapa/org-ql/issues/365][#365]]. Thanks to [[https://github.com/kofm][Gabriele Mongiano]] for reporting.)
** 0.8.4
*Fixes*

View file

@ -1461,40 +1461,16 @@ Org effort string, like \"5\" or \"0:05\"."
(list :regexp (rx bol (0+ space) ":STYLE:" (1+ space) "habit" (0+ space) eol))))
:body (org-is-habit-p))
(org-ql-defpred (heading h) (&rest strings)
(org-ql-defpred (heading h) (&rest _strings)
"Return non-nil if current entry's heading matches all STRINGS.
Matching is done case-insensitively."
:coalesce t
:normalizers ((`(,predicate-names . ,args)
;; "h" alias.
`(heading ,@args)))
;; TODO: Adjust regexp to avoid matching in tag list.
:preambles ((`(,predicate-names)
;; This clause protects against the case in which the
;; arguments are nil, which would cause an error in
;; `rx-to-string' in other clauses. This can happen
;; with `org-ql-completing-read', e.g. when the input
;; is "h:" while the user is typing.
(list :regexp (rx bol (1+ "*") (1+ blank) (0+ nonl))
:case-fold t :query query))
(`(,predicate-names ,string)
;; Only one string: match with preamble, then let predicate confirm (because
;; the match could be in e.g. the tags rather than the heading text).
(list :regexp (rx-to-string `(seq bol (1+ "*") (1+ blank) (0+ nonl)
,string)
'no-group)
:case-fold t :query query))
(`(,predicate-names . ,strings)
;; Multiple strings: use preamble to match against first
;; string, then let the predicate match the rest.
(list :regexp (rx-to-string `(seq bol (1+ "*") (1+ blank) (0+ nonl)
,(car strings))
'no-group)
:case-fold t :query query)))
;; TODO: In Org 9.2+, `org-get-heading' takes 2 more arguments.
:body (let ((heading (org-get-heading 'no-tags 'no-todo))
(case-fold-search t))
(--all? (string-match it heading) strings)))
;; NOTE: Each string argument must be converted to a regexp
;; for testing by the body, so we just normalize to the
;; `heading-regexp' predicate, leaving this predicate as
;; one that merely regexp-quotes its arguments.
`(heading-regexp ,@(mapcar #'regexp-quote args)))))
(org-ql-defpred (heading-regexp h*) (&rest regexps)
"Return non-nil if current entry's heading matches all REGEXPS (regexp strings).
@ -2101,7 +2077,7 @@ With KEYWORDS, return non-nil if its keyword is one of KEYWORDS."
:normalizers ((`(,predicate-names
;; Avoid infinitely compiling already-compiled functions.
,(and query (guard (not (byte-code-function-p query)))))
`(ancestors ,(org-ql--query-predicate (rec query))))
`(ancestors ,(org-ql--query-predicate (org-ql--normalize-query query))))
(`(,predicate-names) '(ancestors (lambda () t))))
:body
(org-with-wide-buffer
@ -2113,7 +2089,7 @@ With KEYWORDS, return non-nil if its keyword is one of KEYWORDS."
:normalizers ((`(,predicate-names
;; Avoid infinitely compiling already-compiled functions.
,(and query (guard (not (byte-code-function-p query)))))
`(parent ,(org-ql--query-predicate (rec query))))
`(parent ,(org-ql--query-predicate (org-ql--normalize-query query))))
(`(,predicate-names) '(parent (lambda () t))))
:body
(org-with-wide-buffer

View file

@ -73,6 +73,7 @@ Functions / Macros
Changelog
* 0.9-pre: 09-pre.
* 0.8.5: 085.
* 0.8.4: 084.
* 0.8.3: 083.
* 0.8.2: 082.
@ -1034,6 +1035,7 @@ releases.
* Menu:
* 0.9-pre: 09-pre.
* 0.8.5: 085.
* 0.8.4: 084.
* 0.8.3: 083.
* 0.8.2: 082.
@ -1071,7 +1073,7 @@ releases.
* 0.1: 01.

File: README.info, Node: 09-pre, Next: 084, Up: Changelog
File: README.info, Node: 09-pre, Next: 085, Up: Changelog
5.1 0.9-pre
===========
@ -1079,9 +1081,26 @@ File: README.info, Node: 09-pre, Next: 084, Up: Changelog
Nothing new yet.

File: README.info, Node: 084, Next: 083, Prev: 09-pre, Up: Changelog
File: README.info, Node: 085, Next: 084, Prev: 09-pre, Up: Changelog
5.2 0.8.4
5.2 0.8.5
=========
*Fixes*
• Predicate heading incorrectly matched strings as regular
expressions, sometimes returning incorrect results. (See
discussion (https://github.com/alphapapa/org-ql/discussions/410).
Thanks to Alex Popescu (https://github.com/al3xandru) for
reporting.)
• Predicates ancestor and parent did not normalize their
sub-queries, sometimes returning incorrect results. (#365
(https://github.com/alphapapa/org-ql/issues/365). Thanks to
Gabriele Mongiano (https://github.com/kofm) for reporting.)

File: README.info, Node: 084, Next: 083, Prev: 085, Up: Changelog
5.3 0.8.4
=========
*Fixes*
@ -1095,7 +1114,7 @@ File: README.info, Node: 084, Next: 083, Prev: 09-pre, Up: Changelog

File: README.info, Node: 083, Next: 082, Prev: 084, Up: Changelog
5.3 0.8.3
5.4 0.8.3
=========
*Fixes*
@ -1108,7 +1127,7 @@ File: README.info, Node: 083, Next: 082, Prev: 084, Up: Changelog

File: README.info, Node: 082, Next: 081, Prev: 083, Up: Changelog
5.4 0.8.2
5.5 0.8.2
=========
*Fixes*
@ -1122,7 +1141,7 @@ File: README.info, Node: 082, Next: 081, Prev: 083, Up: Changelog

File: README.info, Node: 081, Next: 08, Prev: 082, Up: Changelog
5.5 0.8.1
5.6 0.8.1
=========
*Fixes*
@ -1137,7 +1156,7 @@ File: README.info, Node: 081, Next: 08, Prev: 082, Up: Changelog

File: README.info, Node: 08, Next: 074, Prev: 081, Up: Changelog
5.6 0.8
5.7 0.8
=======
*Additions*
@ -1193,7 +1212,7 @@ File: README.info, Node: 08, Next: 074, Prev: 081, Up: Changelog

File: README.info, Node: 074, Next: 073, Prev: 08, Up: Changelog
5.7 0.7.4
5.8 0.7.4
=========
*Fixes*
@ -1203,7 +1222,7 @@ File: README.info, Node: 074, Next: 073, Prev: 08, Up: Changelog

File: README.info, Node: 073, Next: 072, Prev: 074, Up: Changelog
5.8 0.7.3
5.9 0.7.3
=========
*Fixes*
@ -1221,8 +1240,8 @@ File: README.info, Node: 073, Next: 072, Prev: 074, Up: Changelog

File: README.info, Node: 072, Next: 071, Prev: 073, Up: Changelog
5.9 0.7.2
=========
5.10 0.7.2
==========
*Fixes*
• Timestamp predicates are more tolerant of partial input (e.g.
@ -1242,7 +1261,7 @@ File: README.info, Node: 072, Next: 071, Prev: 073, Up: Changelog

File: README.info, Node: 071, Next: 07, Prev: 072, Up: Changelog
5.10 0.7.1
5.11 0.7.1
==========
*Fixes*
@ -1261,7 +1280,7 @@ File: README.info, Node: 071, Next: 07, Prev: 072, Up: Changelog

File: README.info, Node: 07, Next: 063, Prev: 071, Up: Changelog
5.11 0.7
5.12 0.7
========
*Added*
@ -1320,7 +1339,7 @@ File: README.info, Node: 07, Next: 063, Prev: 071, Up: Changelog

File: README.info, Node: 063, Next: 062, Prev: 07, Up: Changelog
5.12 0.6.3
5.13 0.6.3
==========
*Fixed*
@ -1336,7 +1355,7 @@ File: README.info, Node: 063, Next: 062, Prev: 07, Up: Changelog

File: README.info, Node: 062, Next: 061, Prev: 063, Up: Changelog
5.13 0.6.2
5.14 0.6.2
==========
*Fixed*
@ -1347,7 +1366,7 @@ File: README.info, Node: 062, Next: 061, Prev: 063, Up: Changelog

File: README.info, Node: 061, Next: 06, Prev: 062, Up: Changelog
5.14 0.6.1
5.15 0.6.1
==========
*Fixed*
@ -1365,7 +1384,7 @@ File: README.info, Node: 061, Next: 06, Prev: 062, Up: Changelog

File: README.info, Node: 06, Next: 052, Prev: 061, Up: Changelog
5.15 0.6
5.16 0.6
========
*Added*
@ -1432,7 +1451,7 @@ File: README.info, Node: 06, Next: 052, Prev: 061, Up: Changelog

File: README.info, Node: 052, Next: 051, Prev: 06, Up: Changelog
5.16 0.5.2
5.17 0.5.2
==========
*Fixed*
@ -1443,7 +1462,7 @@ File: README.info, Node: 052, Next: 051, Prev: 06, Up: Changelog

File: README.info, Node: 051, Next: 05, Prev: 052, Up: Changelog
5.17 0.5.1
5.18 0.5.1
==========
*Fixed*
@ -1456,7 +1475,7 @@ File: README.info, Node: 051, Next: 05, Prev: 052, Up: Changelog

File: README.info, Node: 05, Next: 049, Prev: 051, Up: Changelog
5.18 0.5
5.19 0.5
========
*Added*
@ -1497,7 +1516,7 @@ File: README.info, Node: 05, Next: 049, Prev: 051, Up: Changelog

File: README.info, Node: 049, Next: 048, Prev: 05, Up: Changelog
5.19 0.4.9
5.20 0.4.9
==========
*Fixed*
@ -1508,7 +1527,7 @@ File: README.info, Node: 049, Next: 048, Prev: 05, Up: Changelog

File: README.info, Node: 048, Next: 047, Prev: 049, Up: Changelog
5.20 0.4.8
5.21 0.4.8
==========
*Fixed*
@ -1520,7 +1539,7 @@ File: README.info, Node: 048, Next: 047, Prev: 049, Up: Changelog

File: README.info, Node: 047, Next: 046, Prev: 048, Up: Changelog
5.21 0.4.7
5.22 0.4.7
==========
*Fixed*
@ -1533,7 +1552,7 @@ File: README.info, Node: 047, Next: 046, Prev: 048, Up: Changelog

File: README.info, Node: 046, Next: 045, Prev: 047, Up: Changelog
5.22 0.4.6
5.23 0.4.6
==========
*Fixed*
@ -1546,7 +1565,7 @@ File: README.info, Node: 046, Next: 045, Prev: 047, Up: Changelog

File: README.info, Node: 045, Next: 044, Prev: 046, Up: Changelog
5.23 0.4.5
5.24 0.4.5
==========
*Fixed*
@ -1558,7 +1577,7 @@ File: README.info, Node: 045, Next: 044, Prev: 046, Up: Changelog

File: README.info, Node: 044, Next: 043, Prev: 045, Up: Changelog
5.24 0.4.4
5.25 0.4.4
==========
*Fixed*
@ -1570,7 +1589,7 @@ File: README.info, Node: 044, Next: 043, Prev: 045, Up: Changelog

File: README.info, Node: 043, Next: 042, Prev: 044, Up: Changelog
5.25 0.4.3
5.26 0.4.3
==========
*Fixed*
@ -1580,7 +1599,7 @@ File: README.info, Node: 043, Next: 042, Prev: 044, Up: Changelog

File: README.info, Node: 042, Next: 041, Prev: 043, Up: Changelog
5.26 0.4.2
5.27 0.4.2
==========
*Fixed*
@ -1589,7 +1608,7 @@ File: README.info, Node: 042, Next: 041, Prev: 043, Up: Changelog

File: README.info, Node: 041, Next: 04, Prev: 042, Up: Changelog
5.27 0.4.1
5.28 0.4.1
==========
*Fixed*
@ -1599,7 +1618,7 @@ File: README.info, Node: 041, Next: 04, Prev: 042, Up: Changelog

File: README.info, Node: 04, Next: 032, Prev: 041, Up: Changelog
5.28 0.4
5.29 0.4
========
_Note:_ The next release, 0.5, may include changes which will require
@ -1680,7 +1699,7 @@ automatically, as they will be pushed to the master branch when ready.

File: README.info, Node: 032, Next: 031, Prev: 04, Up: Changelog
5.29 0.3.2
5.30 0.3.2
==========
*Fixed*
@ -1693,7 +1712,7 @@ File: README.info, Node: 032, Next: 031, Prev: 04, Up: Changelog

File: README.info, Node: 031, Next: 03, Prev: 032, Up: Changelog
5.30 0.3.1
5.31 0.3.1
==========
*Fixed*
@ -1703,7 +1722,7 @@ File: README.info, Node: 031, Next: 03, Prev: 032, Up: Changelog

File: README.info, Node: 03, Next: 023, Prev: 031, Up: Changelog
5.31 0.3
5.32 0.3
========
*Added*
@ -1771,7 +1790,7 @@ File: README.info, Node: 03, Next: 023, Prev: 031, Up: Changelog

File: README.info, Node: 023, Next: 022, Prev: 03, Up: Changelog
5.32 0.2.3
5.33 0.2.3
==========
*Fixed*
@ -1781,7 +1800,7 @@ File: README.info, Node: 023, Next: 022, Prev: 03, Up: Changelog

File: README.info, Node: 022, Next: 021, Prev: 023, Up: Changelog
5.33 0.2.2
5.34 0.2.2
==========
*Fixed*
@ -1792,7 +1811,7 @@ File: README.info, Node: 022, Next: 021, Prev: 023, Up: Changelog

File: README.info, Node: 021, Next: 02, Prev: 022, Up: Changelog
5.34 0.2.1
5.35 0.2.1
==========
*Fixed*
@ -1802,7 +1821,7 @@ File: README.info, Node: 021, Next: 02, Prev: 022, Up: Changelog

File: README.info, Node: 02, Next: 01, Prev: 021, Up: Changelog
5.35 0.2
5.36 0.2
========
*Added*
@ -1885,7 +1904,7 @@ File: README.info, Node: 02, Next: 01, Prev: 021, Up: Changelog

File: README.info, Node: 01, Prev: 02, Up: Changelog
5.36 0.1
5.37 0.1
========
First tagged release.
@ -1943,81 +1962,82 @@ GPLv3

Tag Table:
Node: Top225
Node: Contents1926
Node: Screenshots2049
Node: Installation2167
Node: Quelpa2681
Node: Helm support3209
Node: Usage3612
Node: Commands4010
Node: org-ql-find4475
Node: org-ql-open-link5383
Node: org-ql-refile6238
Node: org-ql-search6566
Node: helm-org-ql8497
Node: org-ql-view8875
Node: org-ql-view-sidebar9405
Node: org-ql-view-recent-items9785
Node: org-ql-sparse-tree10281
Node: Queries11081
Node: Non-sexp query syntax12198
Node: General predicates13957
Node: Ancestor/descendant predicates20882
Node: Date/time predicates22010
Node: Functions / Macros25134
Node: Agenda-like views25432
Ref: Function org-ql-block25594
Node: Listing / acting-on results26855
Ref: Caching27063
Ref: Function org-ql-select27976
Ref: Function org-ql-query30402
Ref: Macro org-ql (deprecated)32176
Node: Custom predicates32491
Ref: Macro org-ql-defpred32715
Node: Dynamic block36156
Node: Links38880
Node: Tips39567
Node: Changelog39891
Node: 09-pre40782
Node: 08440889
Node: 08341344
Node: 08241685
Node: 08142078
Node: 0842499
Node: 07445223
Node: 07345446
Node: 07246178
Node: 07147097
Node: 0747908
Node: 06350774
Node: 06251307
Node: 06151614
Node: 0652184
Node: 05255240
Node: 05155542
Node: 0555967
Node: 04957498
Node: 04857780
Node: 04758129
Node: 04658538
Node: 04558946
Node: 04459307
Node: 04359666
Node: 04259869
Node: 04160030
Node: 0460277
Node: 03264378
Node: 03164781
Node: 0364978
Node: 02368278
Node: 02268512
Node: 02168792
Node: 0268997
Node: 0173075
Node: Notes73176
Node: Comparison with Org Agenda searches73338
Node: org-sidebar74227
Node: License74506
Node: Contents1940
Node: Screenshots2063
Node: Installation2181
Node: Quelpa2695
Node: Helm support3223
Node: Usage3626
Node: Commands4024
Node: org-ql-find4489
Node: org-ql-open-link5397
Node: org-ql-refile6252
Node: org-ql-search6580
Node: helm-org-ql8511
Node: org-ql-view8889
Node: org-ql-view-sidebar9419
Node: org-ql-view-recent-items9799
Node: org-ql-sparse-tree10295
Node: Queries11095
Node: Non-sexp query syntax12212
Node: General predicates13971
Node: Ancestor/descendant predicates20896
Node: Date/time predicates22024
Node: Functions / Macros25148
Node: Agenda-like views25446
Ref: Function org-ql-block25608
Node: Listing / acting-on results26869
Ref: Caching27077
Ref: Function org-ql-select27990
Ref: Function org-ql-query30416
Ref: Macro org-ql (deprecated)32190
Node: Custom predicates32505
Ref: Macro org-ql-defpred32729
Node: Dynamic block36170
Node: Links38894
Node: Tips39581
Node: Changelog39905
Node: 09-pre40810
Node: 08540917
Node: 08441576
Node: 08342028
Node: 08242369
Node: 08142762
Node: 0843183
Node: 07445907
Node: 07346130
Node: 07246862
Node: 07147783
Node: 0748594
Node: 06351460
Node: 06251993
Node: 06152300
Node: 0652870
Node: 05255926
Node: 05156228
Node: 0556653
Node: 04958184
Node: 04858466
Node: 04758815
Node: 04659224
Node: 04559632
Node: 04459993
Node: 04360352
Node: 04260555
Node: 04160716
Node: 0460963
Node: 03265064
Node: 03165467
Node: 0365664
Node: 02368964
Node: 02269198
Node: 02169478
Node: 0269683
Node: 0173761
Node: Notes73862
Node: Comparison with Org Agenda searches74024
Node: org-sidebar74913
Node: License75192

End Tag Table

View file

@ -218,7 +218,8 @@ with keyword arg NOW in PLIST."
(it "coalesces a single AND clause that uses two predicates (and preserves predicate order)"
(expect (org-ql--normalize-query '(and (rifle "foo") (rifle "bar")
(heading "baz") (heading "buz")))
:to-equal '(and (rifle :regexps '("foo" "bar")) (heading "baz" "buz"))))
;; NOTE: `heading' is normalized to `heading-regexp'.
:to-equal '(and (rifle :regexps '("foo" "bar")) (heading-regexp "baz" "buz"))))
(it "preserves independent OR clauses"
(expect (org-ql--normalize-query '(and (or (rifle "foo") (rifle "bar"))
(or (rifle "baz") (rifle "buz"))))
@ -253,6 +254,18 @@ with keyword arg NOW in PLIST."
(expect (org-ql--normalize-query "\"quoted phrase\"")
:to-equal '(rifle :regexps '("\"quoted phrase\""))))
(describe "Ancestor/Parent predicates"
;; NOTE: Because the ancestor and parent predicates byte-compile their
;; subquery predicates, we have to test the byte-compiled forms here.
(expect (org-ql--normalize-query '(ancestors "scheduled"))
;; No colon after keyword, so not a predicate query.
:to-equal ;; '(ancestors (rifle :regexps '("scheduled")))
`(ancestors #[nil "\300\301\302\"\207" [rifle :regexps ("scheduled")] 3]))
(expect (org-ql--normalize-query '(parent "scheduled"))
;; No colon after keyword, so not a predicate query.
:to-equal ;; '(parent (rifle :regexps '("scheduled")))
`(parent #[nil "\300\301\302\"\207" [rifle :regexps ("scheduled")] 3])))
(describe "Plain strings"
(it "normalizes plain strings to the default predicate (using AND)"
(expect (org-ql--normalize-query '(and "string1" "string2"))
@ -1112,7 +1125,12 @@ with keyword arg NOW in PLIST."
'("Take over the world")))
(org-ql-it "with two arguments"
(org-ql-expect ('(heading "Take over" "world"))
'("Take over the world"))))
'("Take over the world")))
(org-ql-it "does not match strings as regexps"
(org-ql-expect ('(heading "over"))
'("Take over the universe" "Take over the world" "Take over Mars" "Take over the moon"))
(org-ql-expect ('(heading "[over]"))
nil)))
(describe "(heading-regexp)"
(org-ql-it "with one argument"