Hide blocks with specified tag in queries

Hi,
i thought it’s trivial, but i can’t get it to work… I’ve got notes like below:

- some block #test
	- block A
		- AAA
		- aaa
	- block B #archive
		- bbb
		- bbb
	- bloc C
		- CCCC
		- cccc #archive
- some second block
	- block D
		- ddd #test
		- DDD

now, i want to build a query, which’ll show me all block with #test tag, without blocks with #archive.

I thought, that simple:

{{query (and [[test]] (not [[archive]]))}}

should do the job, but that shows me only
Screenshot_20240512_012942

Could someone help me with that?

1 Like

What should it show instead?

I’d like to see everything, what isn’t marked as archive, so in above example:

- some block #test
	- block A
		- AAA
		- aaa
	- bloc C
		- CCCC
- some second block
	- block D
		- ddd #test
	

This is not possible with a simple query, but it is with an advanced one.

  • Based on your example, that query should return all non-archived blocks that either:
    • contain tag #test
      • e.g. blocks some block and ddd
    • have an ancestor block that contains tag #test
      • e.g. blocks aaa and CCCC
    • have a descendant block that contains tag #test
      • e.g. blocks some second block and block D
  • However, could you clarify the following things in your example:
    • What exactly qualifies block DDD to be part of the results?
      • The above cases don’t capture it. What other case should be included to capture it?
    • What should happen with the descendants of #archive (i.e. blocks bbb) if they happen to contain tag #test themselves?

Sorry, my mistake - block DDD shouldn’t be visible (i’ve already edited previous post)

about “some second block” - it doesn’t have to be visible as long as i can see “ddd” (it’s even better when it’s hided), so we can make it a bit simpler removing your third condition

tag #archive is the most important, so it should always hide block, which contains it (and all subblocks of that block), regardless occurrence of #test tag

Try this:

#+BEGIN_QUERY
{:query [:find (pull ?b [*])
   :in $ %
   :where
     [?yes :block/name "test"]
     (or-join [?b ?yes]
       [?b :block/refs ?yes]
       (and
         (ancestor ?a ?b)
         [?a :block/refs ?yes]
       )
     )
     (not
       [?no :block/name "archive"]
       (or-join [?b ?no]
         [?b :block/refs ?no]
         (and
           (ancestor ?a ?b)
           [?a :block/refs ?no]
         )
         (and
           (descendant ?d ?b)
           [?d :block/refs ?no]
         )
       )
     )
 ]
 :inputs [
   [
     [
       [ancestor ?a ?b]
       [?b :block/parent ?a]
     ]
     [
       [ancestor ?a ?b]
       [?parent :block/parent ?a]
       (ancestor ?parent ?b)
     ]
     [
       [descendant ?d ?b]
       [?d :block/parent ?b]
     ]
     [
       [descendant ?d ?b]
       [?d :block/parent ?child]
       (descendant ?child ?b)
     ]
   ]
 ]
}
#+END_QUERY
2 Likes

Works as expected, thank you for your help