commit c8c1bdc0d41666d6f7448938be8acb6d6af38588
parent f6800c76a107b76c4c9a004e1946b745ea4615e9
Author: Jacob R. Edwards <jacob@jacobedwards.org>
Date: Tue, 19 Mar 2024 20:25:02 -0700
Add archive page
This page displays a summary of finished periods and allows you to
display or export them.
Diffstat:
4 files changed, 114 insertions(+), 3 deletions(-)
diff --git a/Makefile b/Makefile
@@ -5,7 +5,7 @@ lddflags = ${LDDFLAGS} -static -L/usr/local/lib -lkcgi -lkcgihtml -lz -lsqlbox -
prefix = /var/www/htdocs/${name}.primus.lan
pages = pages/index.c pages/login.c pages/logout.c \
- pages/account.c pages/main.c pages/export.c
+ pages/account.c pages/main.c pages/export.c pages/archive.c
hdrsrc = page.c html.c user.c stmt.c key.c times.c
src = ${hdrsrc} ${pages} pages/util.c
hdr = ${hdrsrc:.c=.h} util.h pages/util.h pages/pages.h
diff --git a/pages/archive.c b/pages/archive.c
@@ -0,0 +1,107 @@
+#include <assert.h>
+#define const
+
+#include <time.h>
+
+#include "common.h"
+#include "pages.h"
+#include "../times.h"
+
+enum kcgi_err
+showform(struct pagedata *pd, char *name, int page, int64_t period)
+{
+ enum kcgi_err status;
+
+ if ((status = khtml_attr(&pd->html, KELEM_FORM,
+ KATTR_ACTION, pd->pages[page], KATTR__MAX)) != KCGI_OK ||
+ (status = khtml_attrx(&pd->html, KELEM_INPUT,
+ KATTR_TYPE, KATTRX_STRING, "hidden",
+ KATTR_NAME, KATTRX_STRING, pd->keys[KeyPeriod].name,
+ KATTR_VALUE, KATTRX_INT, period,
+ KATTR__MAX)) != KCGI_OK ||
+ (status = khtml_attr(&pd->html, KELEM_INPUT,
+ KATTR_TYPE, "submit",
+ KATTR_VALUE, name, KATTR__MAX)) != KCGI_OK ||
+ (status = khtml_closeelem(&pd->html, 1)) != KCGI_OK)
+ return status;
+ return KCGI_OK;
+}
+
+enum kcgi_err
+showperiod(struct pagedata *pd, struct timesheet **rts)
+{
+ enum kcgi_err status;
+ time_t from, to;
+ struct timesheet *ts, *lts;
+ time_t duration;
+ unsigned int period;
+ unsigned int count;
+
+ ts = *rts;
+ assert(ts->set & StartTimeFlag);
+ from = ts->times[StartTime];
+
+ duration = 0;
+ period = ts->period;
+ count = 0;
+ for (; ts && ts->period == period; ts = ts->next) {
+ duration += getduration(ts);
+ lts = ts;
+ ++count;
+ }
+
+ assert(lts->set & EndTimeFlag);
+ to = lts->times[EndTime];
+
+ if ((status = khtml_attrx(&pd->html, KELEM_LI,
+ KATTR_VALUE, KATTRX_INT, (int64_t)period,
+ KATTR__MAX)) != KCGI_OK ||
+ (status = htmldate(pd, from)) != KCGI_OK ||
+ (status = khtml_puts(&pd->html, " to ")) != KCGI_OK ||
+ (status = htmldate(pd, to)) != KCGI_OK ||
+ (status = khtml_printf(&pd->html, "; %d entries, ", count)) != KCGI_OK ||
+ (status = htmlduration(pd, duration, NULL, 0)) != KCGI_OK ||
+ (status = khtml_puts(&pd->html, " hours")) != KCGI_OK ||
+ (status = showform(pd, "Show", PageMain, period)) != KCGI_OK ||
+ (status = showform(pd, "Export", PageExport, period)) != KCGI_OK ||
+ (status = khtml_closeelem(&pd->html, 1)))
+ return status;
+
+ *rts = ts;
+ return KCGI_OK;
+}
+
+enum kcgi_err
+pagearchive(struct pagedata *pd)
+{
+ static char *css[] = { "css/main.css", NULL };
+ static struct pagetemplate template = {
+ "Archive",
+ .css = css
+ };
+
+ enum kcgi_err status;
+ struct timesheet *times, *firsttimes;
+
+ startpage(pd, &template, KHTTP_200);
+
+ if (!pd->user)
+ errorpage(pd, KHTTP_401);
+
+ if (gettimes(pd, pd->user->hash, -1, ×))
+ return KCGI_SYSTEM;
+
+ if ((status = htmlwithin(pd, KELEM_H1, "Archive")) != KCGI_OK ||
+ (status = htmlwithin(pd, KELEM_H2, "Periods")) != KCGI_OK ||
+ (status = khtml_elem(&pd->html, KELEM_OL)) != KCGI_OK)
+ return status;
+
+ firsttimes = times;
+ while (times && showperiod(pd, ×) == KCGI_OK)
+ ;
+ freetimesheet(firsttimes);
+
+ if ((status = khtml_closeelem(&pd->html, 1)) != KCGI_OK)
+ return status;
+ return endpage(pd, &template);
+}
diff --git a/pages/pages.h b/pages/pages.h
@@ -5,6 +5,7 @@ enum Page {
PageAccount,
PageMain,
PageExport,
+ PageArchive,
PageMax
};
@@ -14,3 +15,4 @@ enum kcgi_err pagelogout(struct pagedata *pd);
enum kcgi_err pageaccount(struct pagedata *pd);
enum kcgi_err pageexport(struct pagedata *pd);
enum kcgi_err pagemain(struct pagedata *pd);
+enum kcgi_err pagearchive(struct pagedata *pd);
diff --git a/timekeeper.c b/timekeeper.c
@@ -34,7 +34,8 @@ static char *pages[] = {
[PageLogout] = "logout",
[PageAccount] = "account",
[PageMain] = "main",
- [PageExport] = "export"
+ [PageExport] = "export",
+ [PageArchive] = "archive"
};
int
@@ -67,7 +68,8 @@ main(void)
[PageLogout] = pagelogout,
[PageAccount] = pageaccount,
[PageMain] = pagemain,
- [PageExport] = pageexport
+ [PageExport] = pageexport,
+ [PageArchive] = pagearchive
};
memset(&cfg, 0, sizeof(cfg));