summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLeon Rische <leon.rische@me.com>2020-05-01 14:13:10 +0200
committerLeon Rische <leon.rische@me.com>2020-05-01 14:13:20 +0200
commita2aa55e2855e415ee52a46e36bdfa2060a01f744 (patch)
tree1c4052190a7b1b5b1f10c8b1c5ba2dc99a4091cf
parentba0307070ccccdd195a96af9214b69340beecb1d (diff)
Track tags in position indexer
-rw-r--r--awk/index_cards.awk15
-rw-r--r--awk/index_positions.awk50
-rw-r--r--awk/utils.awk9
-rw-r--r--org-fc.el72
4 files changed, 101 insertions, 45 deletions
diff --git a/awk/index_cards.awk b/awk/index_cards.awk
index 27c50b9..0785543 100644
--- a/awk/index_cards.awk
+++ b/awk/index_cards.awk
@@ -6,6 +6,8 @@ BEGIN {
review_data_drawer = ":" or_default(review_data_drawer, "REVIEW_DATA") ":";
type_property = or_default(type_property, "FC_TYPE");
created_property = or_default(created_property, "FC_CREATED");
+
+ print "(";
}
## Heading Parsing
@@ -40,7 +42,18 @@ in_properties && /:END:/ {
id = properties["ID"];
type = properties[type_property];
created = properties[created_property];
- print FILENAME "\t" id "\t" type "\t" suspended "\t" created;
+ print " (" \
+ ":path \"" FILENAME "\"" \
+ " :id \"" id "\"" \
+ " :type " type \
+ " :suspended " (suspended ? "t" : "nil") \
+ " :created \"" created "\"" \
+ ")"
+
in_properties = 0;
in_card = 0;
}
+
+END {
+ print ")";
+}
diff --git a/awk/index_positions.awk b/awk/index_positions.awk
index e409f52..c1c883c 100644
--- a/awk/index_positions.awk
+++ b/awk/index_positions.awk
@@ -7,14 +7,32 @@ BEGIN {
review_data_drawer = ":" or_default(review_data_drawer, "REVIEW_DATA") ":";
type_property = or_default(type_property, "FC_TYPE");
created_property = or_default(created_property, "FC_CREATED");
+
+ print "(";
+}
+
+BEGINFILE {
+ # Stack of parent headline tags, level 0 is used for filetags
+ parent_tags[0] = "";
+}
+
+## Filetags
+
+match($0, /#\+FILETAGS:[ \t]+(.*)/, a) {
+ parent_tags[0] = a[1];
}
## Heading Parsing
-/^\*+[ \t]+.*$/ {
+match($0, /^(\*)+[ \t]+.*$/, a) {
+ level = length(a[1]);
+ tags = ""
+
# tag re based on org-tag-re
- match($0, /^\*+[ \t]+.*[ \t]+(:([a-zA-Z0-9_@#%]+:)+)$/, a)
- tags = a[1]
+ if (match($0, /^\*+[ \t]+.*[ \t]+(:([a-zA-Z0-9_@#%]+:)+)$/, b) != 0) {
+ tags = b[1];
+ }
+ parent_tags[level] = tags;
id = "none";
@@ -24,6 +42,8 @@ BEGIN {
} else {
in_card = 0;
}
+
+ last_level = level;
next
}
@@ -66,8 +86,30 @@ in_data && /^\|.*\|$/ {
interval = trim($5);
due = trim_surrounding($6);
+ inherited_tags = "";
+ for (i = 0; i < level; i++) {
+ inherited_tags = combine_tags(inherited_tags, parent_tags[i]);
+ }
+ local_tags = parent_tags[level];
+
if (!(filter_due == "1") || (due < now && suspended == "0")) {
- print FILENAME "\t" id "\t" type "\t" suspended "\t" position "\t" ease "\t" box "\t" interval "\t" due "\t" inherited_tags "\t" local_tags;
+ print "(" \
+ ":path \"" FILENAME "\"" \
+ " :id \"" id "\"" \
+ " :type " type \
+ " :suspended " (suspended ? "t" : "nil") \
+ " :position \"" position "\"" \
+ " :ease " ease \
+ " :box " box \
+ " :interval " interval \
+ " :due \"" due "\"" \
+ " :inherited-tags \"" inherited_tags "\"" \
+ " :local-tags \"" local_tags "\"" \
+ ")"
}
}
}
+
+END {
+ print ")";
+}
diff --git a/awk/utils.awk b/awk/utils.awk
index 01295a2..7384ea0 100644
--- a/awk/utils.awk
+++ b/awk/utils.awk
@@ -21,3 +21,12 @@ function time_days_ago(n) {
function or_default(var, def) {
return (var != "") ? var : def;
}
+
+# Combine two tag strings
+function combine_tags(tags1, tags2) {
+ if (tags1 == "") {
+ return tags2;
+ } else {
+ return substr(tags1, 0, length(tags1) - 1) tags2
+ }
+}
diff --git a/org-fc.el b/org-fc.el
index b219f8d..ea675e0 100644
--- a/org-fc.el
+++ b/org-fc.el
@@ -1204,7 +1204,8 @@ file (absolute path) as input."
('number (string-to-number element))
('symbol (intern element))
('keyword (intern (concat ":" element)))
- ('bool (string= element "1")))
+ ('bool (string= element "1"))
+ ('tags (split-string element ":" t)))
element))
(defun org-fc-tsv--parse-row (headers elements)
@@ -1225,40 +1226,25 @@ Each element is parsed using its header specification."
(lambda (row) (org-fc-tsv--parse-row headers (split-string row "\t")))
(split-string input "\n" t)))
-(defvar org-fc-awk-card-headers
- '(:path :id (:type . symbol) (:suspended . bool) (:created . date))
- "Headers of the card indexer.")
-
-(defvar org-fc-awk-position-headers
- '(:path
- :id
- (:type . symbol)
- (:suspended . bool)
- :position
- (:ease . number)
- (:box . box)
- (:interval . interval)
- (:due . date))
- "Headers of the position indexer.")
-
-(defvar org-fc-awk-review-stats-headers
- '((:total . number) (:again . number) (:hard . number) (:good . number) (:easy . number))
- "Headers of the review stat aggregator.")
-
;;;; AWK Wrapper Functions
(cl-defun org-fc-awk-cards (&optional (paths org-fc-directories))
"List all cards in PATHS."
- (org-fc-tsv-parse
- org-fc-awk-card-headers
- (shell-command-to-string
- (org-fc-awk--pipe
- (org-fc-awk--find paths)
- (org-fc-awk--xargs
- (org-fc-awk--command
- "awk/index_cards.awk"
- :utils t
- :variables (org-fc-awk--indexer-variables)))))))
+ (mapcar
+ (lambda (pos)
+ (plist-put
+ pos
+ :created
+ (parse-iso8601-time-string (plist-get pos :created))))
+ (read
+ (shell-command-to-string
+ (org-fc-awk--pipe
+ (org-fc-awk--find paths)
+ (org-fc-awk--xargs
+ (org-fc-awk--command
+ "awk/index_cards.awk"
+ :utils t
+ :variables (org-fc-awk--indexer-variables))))))))
(cl-defun org-fc-awk-stats-cards (&optional (paths org-fc-directories))
"Statistics for all cards in PATHS."
@@ -1268,7 +1254,7 @@ Each element is parsed using its header specification."
(org-fc-awk--find paths)
(org-fc-awk--xargs
(org-fc-awk--command
- "awk/index_cards.awk"
+ "awk/index_cards_tsv.awk"
:utils t
:variables (org-fc-awk--indexer-variables)))
(org-fc-awk--command "awk/stats_cards.awk" :utils t)))))
@@ -1283,13 +1269,19 @@ If FILTER-DUE is non-nil, only list non-suspended cards that are
due for review."
(mapcar
(lambda (pos)
- (plist-put pos
- :tags
- (org-fc-combine-tags
- (plist-get pos :inherited-tags)
- (plist-get pos :local-tags))))
- (org-fc-tsv-parse
- org-fc-awk-position-headers
+ (plist-put
+ (plist-put
+ (plist-put
+ (plist-put
+ pos
+ :tags
+ (org-fc-combine-tags
+ (split-string (plist-get pos :inherited-tags) ":" t)
+ (split-string (plist-get pos :local-tags) ":" t)))
+ :due (parse-iso8601-time-string (plist-get pos :due)))
+ :inherited-tags (split-string (plist-get pos :inherited-tags) ":" t))
+ :local-tags (split-string (plist-get pos :local-tags) ":" t)))
+ (read
(shell-command-to-string
(org-fc-awk--pipe
(org-fc-awk--find paths)
@@ -1310,7 +1302,7 @@ due for review."
(org-fc-awk--find paths)
(org-fc-awk--xargs
(org-fc-awk--command
- "awk/index_positions.awk"
+ "awk/index_positions_tsv.awk"
:utils t
:variables (org-fc-awk--indexer-variables)))
(org-fc-awk--command "awk/stats_positions.awk")))))