aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAndinus <andinus@nand.sh>2021-07-29 19:52:07 +0530
committerAndinus <andinus@nand.sh>2021-07-29 19:52:07 +0530
commit26bdd23908890052271aace2db77980d7e27c354 (patch)
tree61d0ee423eb99147e84375b600efdef9fe134917
parent5f7f94b800c8f6425d3e6ad8823a6b84a67978f8 (diff)
downloadlacerta-26bdd23908890052271aace2db77980d7e27c354.tar.gz
Add initial implementation
-rw-r--r--lib/Lacerta/CLI.rakumod78
1 files changed, 78 insertions, 0 deletions
diff --git a/lib/Lacerta/CLI.rakumod b/lib/Lacerta/CLI.rakumod
new file mode 100644
index 0000000..d6b80bc
--- /dev/null
+++ b/lib/Lacerta/CLI.rakumod
@@ -0,0 +1,78 @@
+use Terminal::Table;
+use Terminal::Spinners;
+
+# Parses the WhatsApp logs.
+grammar WhatsApp {
+ token TOP {
+ || <Text>
+ || <Notice>
+ }
+
+ token Notice { <date> ', ' <time> ' - ' <message> }
+ token Text { <date> ', ' <time> ' - ' <name> ': ' <message> }
+
+ token date { (\d+) ** 3 % '/' }
+ token time { (\d+) ** 2 % ':' }
+ token name { [[\w|\s]+ | '+' \d+ [\d+|\s]+] }
+ token number { '+' \d+ [\d+|\s]+ }
+ token message { .* }
+}
+
+#| parses WhatsApp export
+sub MAIN (
+ Str $profile-name = "Andinus", #= WhatsApp profile name
+ Str $input where *.IO.f = "input", #= input log file to parse
+
+) {
+ my WhatsApp @logs;
+ {
+ my $bar = Bar.new: :type<equals>;
+ $bar.show: 0;
+
+ my Int $count = 0;
+ my Int $total = $input.IO.lines.elems; # Roughly the number of messages.
+ my Int $interval = $total div 40; # Interval for update.
+
+ @logs = gather for $input.IO.lines -> $line {
+ if WhatsApp.parse($line) -> $m { take $m }
+ $bar.show: $count / $total * 100 if $count++ %% $interval;
+ }
+ $bar.show: 100;
+
+ put "\n" ~ "Parsed {@logs.elems} logs in " ~ (now - ENTER now) ~ "s";
+ }
+
+ {
+ my @data;
+ my @given-data;
+ push @data, <Name Messages Words Deleted Media MostActiveHour Left>;
+ push @given-data, <Name FucksGiven>;
+ for @logs.grep(*<Text>).map(*<Text>).map(*<name>.Str).unique -> $name {
+ with @logs.grep(*<Text>).map(*<Text>).grep(*<name>.Str eq $name) {
+ @data.push(
+ (
+ $name,
+ .elems.Str,
+ .map(*<message>.words).sum.Str,
+ .grep(*<message> eq "You deleted this message"|"This message was deleted").elems.Str,
+ .grep(*<message> eq "<Media omitted>").elems.Str,
+ .map(*<time>[0][0].Int).Bag.max(*.values).key.Str,
+ $name eq $profile-name
+ ?? @logs.grep(*<Notice>).grep(*<Notice><message> eq "You left").elems.Str
+ !! @logs.grep(*<Notice>).grep(*<Notice><message> eq "{$name} left").elems.Str,
+ )
+ );
+
+ @given-data.push(
+ (
+ $name,
+ .grep(*<message>.lc.contains("fuck")).elems.Str,
+ )
+ );
+ }
+ }
+ put "Generated data in " ~ (now - ENTER now) ~ "s";
+ print-table(@data, :style<single>);
+ print-table(@given-data, :style<single>);
+ }
+}