Coming from the Ledger half of the Free accounting world, I'm used to
the fact that transaction metadata propagates down to postings. Please
correct me if I'm wrong, but this doesn't seem to be the case in
Beancount, at least according to my experiments with bean-query.

I'm fine with Beancount model for this. But when querying it is
sometimes handy to have a way to lookup a metadata *first* in a posting,
and then fallback to the parent transaction if the metadata key is not
defined in the posting. Is there a way to implement this in Beancount
SQL language? E.g., is there a boolean (or n-ary) operator that takes
two (or more) values and return the first of them that is not NULL?

Either way, it might be helpful to have a SQL function that will lookup
a metadata key first in a posting and then fallbacks on the parent
transaction. Attached you can find a proposal for such a function,
called ANY_META for lack of better naming ideas.

It works for me, but I'm open to better suggestion on how to
"hierarchically" lookup metadata within transactions.

Cheers.
-- 
Stefano Zacchiroli . [email protected] . upsilon.cc/zack . . o . . . o . o
Computer Science Professor . CTO Software Heritage . . . . . o . . . o o
Former Debian Project Leader . OSI Board Director  . . . o o o . . . o .
« the first rule of tautology club is the first rule of tautology club »

-- 
You received this message because you are subscribed to the Google Groups 
"Beancount" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To post to this group, send email to [email protected].
To view this discussion on the web visit 
https://groups.google.com/d/msgid/beancount/20161114143819.ry4mhqp2ermizo3c%40upsilon.cc.
For more options, visit https://groups.google.com/d/optout.
>From aa65ae27a2472d4a3c1ec9c0eaea9a25a3e91dc2 Mon Sep 17 00:00:00 2001
From: Stefano Zacchiroli <[email protected]>
Date: Mon, 14 Nov 2016 15:29:58 +0100
Subject: [PATCH] add new ANY_META() SQL function to query posting OR entry
 metadata

the function will first lookup the given metadata key in the current
posting, falling back to the parent transaction if and only if the key
is not defined for the posting
---
 src/python/beancount/query/query_env.py | 24 ++++++++++++++++++++++++
 1 file changed, 24 insertions(+)

diff --git a/src/python/beancount/query/query_env.py b/src/python/beancount/query/query_env.py
index 850422c..a345665 100644
--- a/src/python/beancount/query/query_env.py
+++ b/src/python/beancount/query/query_env.py
@@ -244,6 +244,29 @@ class EntryMeta(query_compile.EvalFunction):
             return None
         return meta.get(args[0], None)
 
+class AnyMeta(query_compile.EvalFunction):
+    "Get metadata key of the Posting, falling back to parent Transaction"
+    __intypes__ = [str]
+
+    def __init__(self, operands):
+        super().__init__(operands, object)
+
+    def __call__(self, context):
+        args = self.eval_args(context)
+
+        meta_key = args[0]
+        entry_meta = context.entry.meta
+        posting_meta = context.posting.meta
+
+        # note: if the looked up key is explicitly defined in posting as None,
+        # we return it as such, rather than falling back to parent Transaction
+        if posting_meta and meta_key in posting_meta:
+            return posting_meta.get(meta_key, None)
+        elif entry_meta and meta_key in entry_meta:
+            return entry_meta.get(meta_key, None)
+        else:
+            return None
+
 class OpenMeta(query_compile.EvalFunction):
     "Get the metadata dict of the open directive of the account."
     __intypes__ = [str]
@@ -629,6 +652,7 @@ SIMPLE_FUNCTIONS = {
     'close_date'                                         : CloseDate,
     'meta'                                               : Meta,
     'entry_meta'                                         : EntryMeta,
+    'any_meta'                                           : AnyMeta,
     'open_meta'                                          : OpenMeta,
     'commodity_meta'                                     : CommodityMeta,
     'account_sortkey'                                    : AccountSortKey,
-- 
2.10.2

Reply via email to