r4ulill0 / nittei

Nittei is a minimalist plain text based calendar.
MIT License
0 stars 0 forks source link

Read and model calendar elements #3

Open r4ulill0 opened 6 months ago

r4ulill0 commented 6 months ago
r4ulill0 commented 6 months ago

We are going to use pest as stated in #1.

There will be no backtracking while reading calendar files. In simple terms nittei just queries dates against a list of dates so having the file already taking an O(N) cost seems like an unavoidable problem without setting up a database which is against our plain-text policy.

We have to always try to compare the given date against all configured dates in the calendar, so O(N) it's the minimum cost without modifying its structure (again, plain-text policy). Parsing the file should be also linear if we avoid look-aheads in the grammar.

There are 2 possible paths:

I'm not completely sure if we can optimize every query and if we should. Even with a calendar with 500K lines (30Mb for a text file) a program like cat is able to read it in less than half a second (0.338s). So if a person has that many tasks/events in a year (an average of 1369 tasks per day) and wants to handle them with nittei, waiting a couple seconds for a query doesn't seem that bad. This also applies for people that uses a calendar file to plan their entire lifetime with a reasonable amount of tasks per day (20) rearching to 700K tasks to query after 100 years. Even assuming no tasks are removed after completion, waiting less than half a second doesn't seem that bad, although after filtering I'm pretty sure that time will go up.

The most reasonable way to handle this I think it is to compare while parsing, populating a vector of items that match the queried date. At the end the overall logic should look like the following:

sequenceDiagram
participant FS as FileSystem
participant P as PestParser
participant F1 as Filter1
participant F2 as Filter2
FS->>P: readFile()
loop For every item
P->>P:getCalendarItem()
loop For every filter
P->>F1:filter(item, condition)
note right of F1: This is where the optimization <br> and main query logic will happen
P->>F2:filter(item, condition)
end
end

So we don't need anything more than a vector to store the matching items and the local variables to manage filtering.

For the pretty printing seems enough with the "statement" pairs and some trait for pretty print them.

We could create our own model to avoid dependencies with pest types in the future, but this will be optional for now.

r4ulill0 commented 5 months ago

Chosen terminal cli argument parser is bpaf as it only adds overhead for features you use. There were other alternatives see comparison but I think bpaf was the best option for this project.