goatNote

thing2's goat note implementation
Log | Files | Refs

goatNote.py (5591B)


      1 from enum import Enum
      2 import re
      3 import os
      4 
      5 # Assigning numbers to types of data
      6 class tokenTypes (Enum):
      7     HEADING = 1
      8     DATE = 2
      9     TODO = 3
     10     BULLETPOINT = 4
     11 
     12 class date:
     13     day = 0
     14     month = 0
     15     year = 0
     16     def __init__(self, dateString: str):
     17         dateString = dateString.split(".")
     18         self.year = int(dateString[0])
     19         self.month = int(dateString[1])
     20         self.day = int(dateString[2])
     21 
     22     def asString(self):
     23         return f"{str(self.year)}.{str(self.month):{'0'}>2}.{str(self.day):{'0'}>2}"
     24 
     25 
     26 def tokenize(file: str):
     27     headingRe = r"\s*\*\s*([A-z0-9 ]+)\s*\*\s*\[(\d\d\d\d[.]\d\d[.]\d\d)\]\s*{(TO[.]DO|DONE)}\s*"
     28     bulletPointRe = r"-\s*((\s|[A-z0-9])+)\s*"
     29     unprocessed = []
     30     end = False
     31 
     32     while not end:
     33         heading = re.match(headingRe, file)
     34         bulletPoint = re.match(bulletPointRe, file)
     35 
     36         if heading != None:
     37             unprocessed.append(heading.group())
     38             file = file[heading.span()[1]:]
     39 
     40         elif bulletPoint != None:
     41             unprocessed.append(bulletPoint.group())
     42             file = file[bulletPoint.span()[1]:]
     43         else:
     44             end = True
     45 
     46     values = []
     47     types = []
     48     for i in unprocessed:
     49         heading = re.findall(headingRe, i)
     50         bulletPoint = re.findall(bulletPointRe, i)
     51 
     52         if heading != []:
     53             heading = heading[0]
     54             values.append(heading[0])
     55             types.append(tokenTypes.HEADING)
     56 
     57             values.append(date(heading[1]))
     58             types.append(tokenTypes.DATE)
     59 
     60             if heading[2] == "TO.DO":
     61                 values.append(True)
     62             else:
     63                 values.append(False)
     64             types.append(tokenTypes.TODO)
     65 
     66         elif bulletPoint != []:
     67             values.append(bulletPoint[0])
     68             types.append(tokenTypes.BULLETPOINT)
     69 
     70     return values, types
     71 
     72 def printHeading(values, i):
     73     if values[i + 2]:
     74         toDoString = "DONE"
     75     else:
     76         toDoString = "TO.DO"
     77     print(f"{values[i]:{" "}<30}| {values[i+1].asString()} | {toDoString}")
     78 
     79 def view(values, types):
     80     output = ""
     81     for i in range(len(values)):
     82         if types[i] == tokenTypes.HEADING:
     83             output += values[i] + "|"
     84         if types[i] == tokenTypes.DATE:
     85             output += values[i].asString() + "|"
     86         if types[i] == tokenTypes.TODO:
     87             if not values[i]:
     88                 output += "DONE\n"
     89             else:
     90                 output += "TO.DO\n"
     91         if types[i] == tokenTypes.BULLETPOINT:
     92             output += str(values[i][0])
     93     return output
     94 
     95 def outputGoatNote(values, types):
     96     output = ""
     97     for i in range(len(values)):
     98         if types[i] == tokenTypes.HEADING:
     99             output += "* " + values[i] + " * "
    100         if types[i] == tokenTypes.DATE:
    101             output += "[" + values[i].asString() + "] "
    102         if types[i] == tokenTypes.TODO:
    103             if not values[i]:
    104                 output += "{DONE}\n"
    105             else:
    106                 output += "{TO.DO}\n"
    107         if types[i] == tokenTypes.BULLETPOINT:
    108             output += "- " + str(values[i][0])
    109     return output
    110 
    111 # MAIN CODE STARTS HERE Put user into shell then ask for which file to read from
    112 fileName = input("Which GOATED file do you wanna read?? \n")
    113 if fileName == "": fileName = f"{os.environ["HOME"]}/.global.gn"
    114 if ".gn" not in fileName:
    115     print("That's not a goatNote file! Silly goose! Automatically putting you into the global file!")
    116     fileName = f"{os.environ["HOME"]}/.global.gn"
    117 
    118 try: file = open(fileName, "r")
    119 except:
    120     print("ABORT MISSION (couldn't open file)", fileName, "does not exist")
    121     exit(1)
    122 
    123 values, types = tokenize(file.read())
    124 file.close()
    125 
    126 file = open(fileName, "w")
    127 
    128 # Drop user into a shell
    129 print("enter one of the following commands: list, toggle, view, help, save, or type close (make sure to save first!!) to exit program")
    130 line = input(": ").lower().split(" ")
    131 
    132 while line[0] != "close":
    133     if line[0] == "list":
    134         for i in range(len(types)):
    135             if types[i] == tokenTypes.HEADING:
    136                 printHeading(values, i)
    137 
    138     elif line[0] == "toggle":
    139         for i in range(len(types)):
    140             if types[i] == tokenTypes.HEADING:
    141                 if values[i] == line[1]:
    142                     values[i+2] = not values[i+2]
    143                     break
    144 
    145     elif line[0] == "view":
    146         print(view(values, types))
    147 
    148     elif line[0] == "help":
    149         if len(line) == 1: print("enter one of the following commands following the word \"help\": list, toggle, view, formatting, save, or type close (make sure to save first!!) to exit program")
    150         elif line[1] == "list": print("This command allows you to view a list of all the headings you have in one file.")
    151         elif line[1] == "toggle": print("This command allows you to change any specific goatNote from to-do to done. To use this command, type \"toggle (header you want to change)\"")
    152         elif line[1] == "view": print("This command allows you to view and read every goatNote you have in your selected file.")
    153         elif line[1] == "formatting": print("The formatting style for goatNote files is as follows: \n * heading * [yyyy.mm.dd] {TO.TO/DONE} \n - note body")
    154         else: print("enter one of the following commands following the word \"help\": list, toggle, view, formatting, or type close to exit program")
    155 
    156     elif line[0] == "save":
    157         file.write(outputGoatNote(values, types))
    158         file.flush()
    159         #save file
    160 
    161     else:
    162         print("Invalid command :(")
    163 
    164     line = input(": ").lower().split(" ")
    165 
    166 print("byee(closing program)")
    167 file.close()