From f969bcbe590a22815b57daf119ec202ce83c63e9 Mon Sep 17 00:00:00 2001 From: Paul Beckingham Date: Fri, 6 Jun 2014 19:43:20 -0400 Subject: [PATCH] DOM - Extended DOM support: ..year ..month ..day ..week ..weekday ..julian ..hour ..minute ..second .tags. .annotations..entry .annotations..entry.year .annotations..entry.month .annotations..entry.day .annotations..entry.week .annotations..entry.weekday .annotations..entry.julian .annotations..entry.hour .annotations..entry.minute .annotations..entry.second .annotations..description --- src/DOM.cpp | 158 ++++++++++++++++++++++++++++++++++++++------------- test/dom.2.t | 42 +++++++++++--- 2 files changed, 150 insertions(+), 50 deletions(-) diff --git a/src/DOM.cpp b/src/DOM.cpp index 83269b000..b6f2a4f36 100644 --- a/src/DOM.cpp +++ b/src/DOM.cpp @@ -26,8 +26,11 @@ #include #include +#include +#include #include #include +#include #include #include #include @@ -194,20 +197,26 @@ bool DOM::get (const std::string& name, std::string& value) // .year // .month // .day +// .week +// .weekday +// .julian // .hour // .minute // .second // -// . Includes virtual tags +// tags. Includes virtual tags // -// ..entry -// ..entry.year -// ..entry.month -// ..entry.day -// ..entry.hour -// ..entry.minute -// ..entry.second -// ..description +// annotations..entry +// annotations..entry.year +// annotations..entry.month +// annotations..entry.day +// annotations..entry.week +// annotations..entry.weekday +// annotations..entry.julian +// annotations..entry.hour +// annotations..entry.minute +// annotations..entry.second +// annotations..description // bool DOM::get (const std::string& name, const Task& task, std::string& value) { @@ -247,23 +256,19 @@ bool DOM::get (const std::string& name, const Task& task, std::string& value) std::string uuid; bool proceed = false; - if (n.getInt (id)) + if (n.getInt (id) && n.depleted ()) { - if (n.skip ('.')) - { - if (id == task.id) - ref = task; - else - context.tdb2.get (id, ref); - - proceed = true; - } + if (id == task.id) + ref = task; else - n.restore (); + context.tdb2.get (id, ref); + + proceed = true; } - else if (n.getUUID (uuid)) + else { - if (n.skip ('.')) + n.restore (); + if (n.getUUID (uuid) && n.depleted ()) { if (uuid == task.get ("uuid")) ref = task; @@ -297,33 +302,104 @@ bool DOM::get (const std::string& name, const Task& task, std::string& value) } else if (elements.size () == 3) { - // .year - // .month - // .day - // .hour - // .minute - // .second - - // . - if (elements[1] == "tag") + // tags. + if (canonical == "tags") { value = ref.hasTag (elements[2]) ? elements[2] : ""; return true; } + + Column* column = context.columns[canonical]; + if (column && column->type () == "date") + { + // .year + // .month + // .day + // .week + // .weekday + // .julian + // .hour + // .minute + // .second + Date date (ref.get_date (canonical)); + if (elements[2] == "year") { value = format (date.year ()); return true; } + else if (elements[2] == "month") { value = format (date.month ()); return true; } + else if (elements[2] == "day") { value = format (date.day ()); return true; } + else if (elements[2] == "week") { value = format (date.week ()); return true; } + else if (elements[2] == "weekday") { value = format (date.dayOfWeek ()); return true; } + else if (elements[2] == "julian") { value = format (date.dayOfYear ()); return true; } + else if (elements[2] == "hour") { value = format (date.hour ()); return true; } + else if (elements[2] == "minute") { value = format (date.minute ()); return true; } + else if (elements[2] == "second") { value = format (date.second ()); return true; } + } } - else if (elements.size () == 3) + } + else if (elements[1] == "annotations") + { + if (elements.size () == 4) { - // ..entry - // ..description + std::map annos; + ref.getAnnotations (annos); + + int a = strtol (elements[2].c_str (), NULL, 10); + int count = 0; + + // Count off the 'a'th annotation. + std::map ::iterator i; + for (i = annos.begin (); i != annos.end (); ++i) + { + if (++count == a) + { + if (elements[3] == "entry") + { + // annotation_1234567890 + // 0 ^11 + value = i->first.substr (11); + return true; + } + else if (elements[3] == "description") + { + value = i->second; + return true; + } + } + } } - else if (elements.size () == 4) + else if (elements.size () == 5) { - // ..entry.year - // ..entry.month - // ..entry.day - // ..entry.hour - // ..entry.minute - // ..entry.second + std::map annos; + ref.getAnnotations (annos); + + int a = strtol (elements[2].c_str (), NULL, 10); + int count = 0; + + // Count off the 'a'th annotation. + std::map ::iterator i; + for (i = annos.begin (); i != annos.end (); ++i) + { + if (++count == a) + { + // ..entry.year + // ..entry.month + // ..entry.day + // ..entry.week + // ..entry.weekday + // ..entry.julian + // ..entry.hour + // ..entry.minute + // ..entry.second + Date date (i->first.substr (11)); + if (elements[4] == "year") { value = format (date.year ()); return true; } + else if (elements[4] == "month") { value = format (date.month ()); return true; } + else if (elements[4] == "day") { value = format (date.day ()); return true; } + else if (elements[4] == "week") { value = format (date.week ()); return true; } + else if (elements[4] == "weekday") { value = format (date.dayOfWeek ()); return true; } + else if (elements[4] == "julian") { value = format (date.dayOfYear ()); return true; } + else if (elements[4] == "hour") { value = format (date.hour ()); return true; } + else if (elements[4] == "minute") { value = format (date.minute ()); return true; } + else if (elements[4] == "second") { value = format (date.second ()); return true; } + } + } } } } diff --git a/test/dom.2.t b/test/dom.2.t index 645723dd5..1767b4315 100755 --- a/test/dom.2.t +++ b/test/dom.2.t @@ -27,7 +27,7 @@ use strict; use warnings; -use Test::More tests => 12; +use Test::More tests => 20; # Ensure environment has no influence. delete $ENV{'TASKDATA'}; @@ -73,11 +73,35 @@ like ($output, qr/^$/, "DOM 4.description --> ''"); $output = qx{../src/task rc:$rc _get 3.tags 2>&1}; like ($output, qr/^tag1,tag2$/, "$ut: ."); -$output = qx{../src/task rc:$rc _get 3.tag.tag1 2>&1}; -like ($output, qr/^tag1,tag2$/, "$ut: .tag.tag1"); +$output = qx{../src/task rc:$rc _get 3.tags.tag1 2>&1}; +like ($output, qr/^tag1$/, "$ut: .tags.tag1"); -$output = qx{../src/task rc:$rc _get 3.tag.OVERDUE 2>&1}; -like ($output, qr/^OVERDUE$/, "$ut: .tag."); +$output = qx{../src/task rc:$rc _get 3.tags.OVERDUE 2>&1}; +like ($output, qr/^OVERDUE$/, "$ut: .tags."); + +$output = qx{../src/task rc:$rc _get 3.due.year 2>&1}; +like ($output, qr/^\d{4}$/, "$ut: .due.year"); + +$output = qx{../src/task rc:$rc _get 3.due.month 2>&1}; +like ($output, qr/^\d{1,2}$/, "$ut: .due.month"); + +$output = qx{../src/task rc:$rc _get 3.due.day 2>&1}; +like ($output, qr/^\d{1,2}$/, "$ut: .due.day"); + +$output = qx{../src/task rc:$rc _get 3.due.week 2>&1}; +like ($output, qr/^\d{1,2}$/, "$ut: .due.week"); + +$output = qx{../src/task rc:$rc _get 3.due.weekday 2>&1}; +like ($output, qr/^\d{1}$/, "$ut: .due.weekday"); + +$output = qx{../src/task rc:$rc _get 3.due.hour 2>&1}; +like ($output, qr/^\d{1,2}$/, "$ut: .due.hour"); + +$output = qx{../src/task rc:$rc _get 3.due.minute 2>&1}; +like ($output, qr/^\d{1,2}$/, "$ut: .due.minute"); + +$output = qx{../src/task rc:$rc _get 3.due.second 2>&1}; +like ($output, qr/^\d{1,2}$/, "$ut: .due.second"); $output = qx{../src/task rc:$rc _get 3.due.year 2>&1}; like ($output, qr/^\d{4}$/, "$ut: .due.year"); @@ -85,11 +109,11 @@ like ($output, qr/^\d{4}$/, "$ut: .due.year"); qx{../src/task rc:$rc 3 annotate note 2>&1}; ok ($? == 0, "$ut: add annotation"); -$output = qx{../src/task rc:$rc _get 3.annotation.1.entry 2>&1}; -like ($output, qr/^\d+$/, "$ut: .annotation.1.entry"); +$output = qx{../src/task rc:$rc _get 3.annotations.1.entry 2>&1}; +like ($output, qr/^\d+$/, "$ut: .annotations.1.entry"); -$output = qx{../src/task rc:$rc _get 3.annotation.1.description 2>&1}; -like ($output, qr/^note$/, "$ut: .annotation.1.description"); +$output = qx{../src/task rc:$rc _get 3.annotations.1.description 2>&1}; +like ($output, qr/^note$/, "$ut: .annotations.1.description"); # Cleanup. unlink qw(pending.data completed.data undo.data backlog.data), $rc;