diff --git a/2024-12-14dayplan.ics b/2024-12-14dayplan.ics new file mode 100644 index 0000000..092898b --- /dev/null +++ b/2024-12-14dayplan.ics @@ -0,0 +1,53 @@ +BEGIN:VCALENDAR +VERSION:2.0 +PRODID:-//hacksw/handcal//NONSGML v1.0//EN +BEGIN:VEVENT +UID:Anal0 +DTSTAMP:20241214T205645Z +DTSTART:20241214T205645Z +DTEND:20241214T214145Z +SUMMARY:Anal +END:VEVENT +BEGIN:VEVENT +UID:Anal1 +DTSTAMP:20241214T205645Z +DTSTART:20241214T215145Z +DTEND:20241214T223645Z +SUMMARY:Anal +END:VEVENT +BEGIN:VEVENT +UID:LinAlg2 +DTSTAMP:20241214T205645Z +DTSTART:20241214T224645Z +DTEND:20241214T233145Z +SUMMARY:LinAlg +END:VEVENT +BEGIN:VEVENT +UID:Anal3 +DTSTAMP:20241214T205645Z +DTSTART:20241214T234145Z +DTEND:20241215T 02645Z +SUMMARY:Anal +END:VEVENT +BEGIN:VEVENT +UID:LinAlg4 +DTSTAMP:20241214T205645Z +DTSTART:20241215T 03645Z +DTEND:20241215T 12145Z +SUMMARY:LinAlg +END:VEVENT +BEGIN:VEVENT +UID:Anal5 +DTSTAMP:20241214T205645Z +DTSTART:20241215T 13145Z +DTEND:20241215T 21645Z +SUMMARY:Anal +END:VEVENT +BEGIN:VEVENT +UID:LinAlg6 +DTSTAMP:20241214T205645Z +DTSTART:20241215T 22645Z +DTEND:20241215T 31145Z +SUMMARY:LinAlg +END:VEVENT +END:VCALENDAR diff --git a/db.csv b/db.csv new file mode 100644 index 0000000..10e3b1e --- /dev/null +++ b/db.csv @@ -0,0 +1,3 @@ +LinAlg,1734206162,1747252562,4,0 +TM1,1734206175,1755201375,3,0 +Anal,1734206198,1749930998,5,0 diff --git a/iCal.c b/iCal.c new file mode 100644 index 0000000..8117f34 --- /dev/null +++ b/iCal.c @@ -0,0 +1,134 @@ + +const char *iCalHeader = "BEGIN:VCALENDAR\r\n" + "VERSION:2.0\r\n" + "PRODID:-//hacksw/handcal//NONSGML v1.0//EN\r\n"; +const char *iCalEvent = "BEGIN:VEVENT\r\n" + "UID:%s%d\r\n" + "DTSTAMP:%s\r\n" + "DTSTART:%s\r\n" + "DTEND:%s\r\n" + "SUMMARY:%s\r\n" + "END:VEVENT\r\n"; + +const char *iCalFileExtension = "ics"; + +/* + * Wikipedia + * + *The body of the iCalendar object (the icalbody) contains single-line Calendar + * Properties that apply to the entire calendar, as well as one or more blocks + * of multiple lines that each define a Calendar Component such as an event, + * journal entry, alarm, or one of several other types. Here is a simple example + * of an iCalendar object with a single calendar containing a single Calendar + * Component, a "Bastille Day Party" event starting at 5pm on July 14, 1997, and + * ending at 4am the following morning:[10] + + + +BEGIN:VCALENDAR +VERSION:2.0 +PRODID:-//hacksw/handcal//NONSGML v1.0//EN +BEGIN:VEVENT +UID:uid1@example.com +ORGANIZER;CN=John Doe:MAILTO:john.doe@example.com +DTSTART:19970714T170000Z +DTEND:19970715T040000Z +SUMMARY:Bastille Day Party +GEO:48.85299;2.36885 +END:VEVENT +END:VCALENDAR + + +The UID field distributes updates when a scheduled event changes. When the event +is first generated a globally unique identifier is created. If a later event is +distributed with the same UID, it replaces the original one. An example UID +might be Y2007S2C131M5@example.edu, for the 5th meeting of class 131 in semester +2 at a hypothetical college. Email-style UIDs are now considered bad practice, +with a UUID recommended instead.[11] + +The most common representation of date and time is a tz timestamp such as +20010911T124640Z with the format TZ for a total fixed length of 16 characters. Z +indicates the use of UTC (referring to its Zulu time zone).[12] When used in +DTSTART and DTEND properties, start times are inclusive while end times are not. +This allows an event's end time to be the same as a consecutive event's start +without those events overlapping and potentially creating (false) scheduling +conflicts.[13] + + + */ + +int exportiCal(llist *events_ll) { + + llist *ev_ll = events_ll; + + llistPrintE(ev_ll); + + printf("%s", iCalHeader); + + time_t now = time(NULL); + struct tm lc; + localtime_r(&now, &lc); + + // gen filename & open for write + char nameBuf[32]; + strftime(nameBuf, 32 - 12, "%F", &lc); + strcat(nameBuf, "dayplan.ics"); + FILE *fp = fopen(nameBuf, "w"); + if (fp == NULL) { + planLog("fopen failed!!", 1); + return 1; + } + // write iCal header to file + fprintf(fp, "%s", iCalHeader); + + // for every event in events_ll create VEVENT str and write to fp + int count = 0; + while (ev_ll != NULL) { + // gen iCal compatible time str + Event *current = ev_ll->data; + struct tm startlc; + struct tm endlc; + localtime_r(¤t->plannedStartTime, &startlc); + localtime_r(¤t->plannedEndTime, &endlc); + char timeStartBuf[17]; + char timeEndBuf[17]; + char timeStamp[17]; + strftime(timeStamp, 17, "%Y%m%dT%k%M%SZ", &lc); + printf("%s\n", timeStamp); + strftime(timeStartBuf, 17, "%Y%m%dT%k%M%SZ", &startlc); + printf("%s\n", timeStartBuf); + strftime(timeEndBuf, 17, "%Y%m%dT%k%M%SZ", &endlc); + printf("%s\n", timeEndBuf); + + fprintf(fp, iCalEvent, current->task->name, count, timeStamp, timeStartBuf, + timeEndBuf, current->task->name); + ev_ll = ev_ll->next; + count += 1; + } + + // after all events are written end cal with + // END:VCALENDAR + fprintf(fp, "END:VCALENDAR\r\n"); + fclose(fp); + + return 0; +} + +const char *taskFileFormat = "%s,%lu,%lu,%d,%lu\n"; +int taskLlToFile(llist *tll) { + // open file + FILE *fp = fopen("db.csv", "w"); + if (fp == NULL) + return -1; + llist *c = tll; + while (c != NULL) { + Task *ct = (Task *)c->data; + fprintf(fp, taskFileFormat, ct->name, ct->created, ct->deadline, + ct->priority, ct->spare); + c = c->next; + } + fclose(fp); + + return 0; +} diff --git a/src/uis.c b/src/uis.c new file mode 100644 index 0000000..979e9a7 --- /dev/null +++ b/src/uis.c @@ -0,0 +1,124 @@ +#include "llist.h" +#include "planner.h" +#include +#include +#include +#include +#include + +typedef struct { + char *name; + char *helpStr; + void (*handler)(int argc, char **argv, void *ret); +} Command; + +void addTask(int argc, char **argv, void *ret); +void getTasks(int argc, char **argv, void *ret); +void createPlan(int argc, char **argv, void *ret); +void help_handler(int argc, char **argv, void *ret); +void quit_handler(int argc, char **argv, void *ret); +// Define a list of commands +Command commands[] = { + {"add", + "add task with: add ", + addTask}, + {"getTasks", "TO BE IMPLEMENTED", getTasks}, + {"gen", "Generate timetable with: gen ", createPlan}, + {"help", "Display Help", help_handler}, + {"quit", "Quit program", quit_handler}, +}; + +int main() { + printf("Time Management optimizer!\n"); + llist *taskL = llistNew(NULL, cmpTaskN); + assert(taskL != NULL); + + while (1) { + // Read user input + char *input = NULL; + size_t inputLen; + printf("> "); + getline(&input, &inputLen, stdin); + assert(input != NULL); + + // Parse input into individual commands and arguments + char *token = strtok(input, " \n"); + int argc = 0; + char **argv = NULL; + while (token) { + argv = realloc(argv, (argc + 1) * sizeof(char *)); + argv[argc++] = token; + token = strtok(NULL, " "); + } + + // Find matchin command handler + for (int i = 0; i < sizeof(commands) / sizeof(commands[0]); i++) { + if (strcmp(commands[i].name, argv[0]) == 0) { + commands[i].handler(argc, argv, taskL); + break; + } + } + free(input); + } + + return 0; +} + +/* + * to add task write name deadline(days from now) priority + */ +void addTask(int argc, char **argv, void *ret) { + if (argc != 4) { // invalig input + help_handler(1, &argv[0], NULL); + } else { + + llist *tasksLL = ret; + int days, prio; + char *name = strdup(argv[1]); + // parse task + if (sscanf(argv[2], "%d", &days) < 0 || sscanf(argv[3], "%d", &prio) < 0) { + printf("addTasksscanferr\n"); + exit(1); + } + time_t now = time(NULL); + struct tm *lc = localtime(&now); + lc->tm_mon += days; + time_t deadline = mktime(lc); + + Task *r = newTask(name, now, deadline, prio, 0); + llistAppend(tasksLL, r); + printf("added task:\n"); + printTask(r); + printf("currentTaskList:\n"); + llistPrintT(tasksLL->next); + } +} + +/* + * generate plan, store to ical and store updated tasks to db + */ +void createPlan(int argc, char **argv, void *ret) { + printf("creating plan\n"); + llist *taskLL = ret; + taskLL = taskLL->next; + llistPrintT(taskLL); + time_t now = time(NULL); + struct tm *lc = localtime(&now); + lc->tm_hour += atoi(argv[1]); + genPlan(taskLL, mktime(lc)); +} +void help_handler(int argc, char **argv, void *ret) { + printf("available Commands:\n"); + for (int i = 0; i < sizeof(commands) / sizeof(commands[0]); i++) { + printf("%s:%s\n", commands[i].name, commands[i].helpStr); + } +} +void getTasks(int argc, char **argv, void *ret) { + // TODO get form db +} + +void quit_handler(int argc, char **argv, void *ret) { + printf("Goodbye!\n"); + llistFreeT((llist *)ret); + exit(0); +} diff --git a/src/uis.h b/src/uis.h new file mode 100644 index 0000000..e69de29