Make Advanced Queries reusable

It would be nice to make advanced queries or their parts reusable in Logseq.

Having that, you don’t need to type them multiple times (adhoc-queries, multiple locations in graph) and can omit redundant query code.

According to learndatalogtoday.org, rules are an easy way to do that:

You can abstract away reusable parts of your queries into rules, give them meaningful names and forget about the implementation details, just like you can with functions in your favorite programming language.

So what about adding a additional :query/rules entry to config.edn, similar to existent :query/views and :query/result-transforms for pre-defined :view, :result-transform functions? Then auto-include these to be usable in every advanced query.

Not so well-working alternatives:

  • templates - still redundant, as they are just like copy/pasted text; can get ugly for bigger queries
  • macro/command - didn’t work for me, seems to be not suited well for code incl. format/quoting etc.

Together with Add :pages to :default-queries in config this could make a powerful and flexible query system.

To cover the case «multiple locations in graph» you can embed the block with query. It will work if there is no modifications on query OR if it relies on dynamic variables :query-page / :current-page

1 Like

Yeah, but would the embedded block see the page it was embedded in as the current page or would it see the original block it was from as the current page?

It seems like that doesn’t quite fit the bill, like for example, for this:

https://luhmann-logseq.notion.site/A-new-approach-to-project-management-in-Logseq-8b36dd5eb25d4b9e9882742b5ee4368e

See the demo:
2023-04-21 18.38.42

1 Like

Thanks for the hint @stdword, this is a good starting point.
But sometimes more flexibility is needed than just dynamic variables :current-page and co. For example to centralize complex query logic in one place or using arbitrary variable values.
My suggestion is to add additional reusable rules to Logseq globally, similar to reusable functions in code.

Well, I totally have a plans to add something about making queries to 🏛 Full House Templates plugin.
Don’t have a vision of how it would look like, but you can subscribe for updates here.

1 Like

Sharing a collection of query functions here: Advanced Query Collection
Feel free to share your query/transforms and views. They will be added to list.

2 Likes

Aaah, I found this thread searching to see if this was possible, so definitely adding my support for this feature! I have a common clause defining an “active” task in a lot of my queries, and would be much cleaner and less error-prone to abstract it into a single rule:

(or-join [?b ?today]
         (and [?b :block/scheduled ?scheduleddate]
              [(<= ?scheduleddate ?today)])
         (not [?b :block/scheduled _]))
3 Likes

+1 My use case is having the same exclusionary rules across about 8 queries, that’s nearly 8 lines per query and I have to remember to update all 8 queries. I’d love a way to associate a one line rule I can add each time to call on those rules globally.

I agree this is a very useful feature for advanced query users.
My note system for example. I constant query with page properties + block properties + text match inside block
I have a query for that but I feel instead of copying and pasting the query and updating inputs from time to time would be great I can use {{my_properties_query page_property block_property_1 block_tag_1}} which will be easier.
Also. I am ok with a configurable template as @stdword mentioned as a workaround.

2 Likes

Just implemented some way of parametrizing queries:

Advantages:

  • JavaScript, not datalog
  • Ability to use parameters for rendering as standard plugin feature

Limitations:

  • supported only pages now, not blocks
  • not suitable for complex queries with joins
  • there is no nice output table with columns
  • via plugin: no mobile

See detailed documentation here.

2 Likes

Three simple ideas to increase reusability of Advanced Queries

  1. Make :rules customizable in config.edn
    Just like it works now for :query/result-transforms & :query/views. It is pretty easy to implement.
  2. Add :embed-block as :inputs
    Just like :current-block works now. But :embed-block should be the :db/id of block which embeds the block with query. With that approach we can use the same one query with block embedding and parametrize it via embed block properties. Example:
    - param:: value
      {{embed ((666cd068-133c-4b30-9df4-1dd8a94179cb))}}
    - param:: another-value
      {{embed ((666cd068-133c-4b30-9df4-1dd8a94179cb))}}
    
    Where the ((666cd068-133c-4b30-9df4-1dd8a94179cb)) is the reference to block with query:
    #+BEGIN_QUERY
    {
      :inputs [:embed-block]
      :query [:find ?value
      :in $ ?embed-block
      :where
        (property ?embed-block :param ?value)
    
        ;; ... any way of usage ?value
      ]
    }
    #+END_QUERY
    
    This will lead to result: the only one query, but ability to parametrize it as we need:
  3. Add :query-result as :inputs
    Now the result of query in parent block can be used in child blocks via {{function ...}} macro, but this way is very limited. It would be very useful to reuse the query result in child blocks via advanced queries.

:pray: Vote for this comment and the whole topic

5 Likes

Hello! Some time ago I wrote here:

Well, I totally have a plans to add something about making queries

And I’ve just added Table View to 🏛 Full House Templates plugin. This is not a solution for parametrizing Logseq Advanced Queries, but can help a lot in more frictionless programming to retrieve data from your graph.

2024-07-22 19.09.33

See details in documentation.