diff options
context:
space:
mode:
Diffstat (limited to 'source')
-rw-r--r--source/cgit.c6
-rw-r--r--source/cgit.h4
-rw-r--r--source/shared.c33
-rw-r--r--source/ui-shared.c31
4 files changed, 68 insertions, 6 deletions
diff --git a/source/cgit.c b/source/cgit.c
index c824da6..412d5f3 100644
--- a/source/cgit.c
+++ b/source/cgit.c
@@ -199,6 +199,8 @@ static void config_cb(const char *name, const char *value)
ctx.cfg.enable_log_filecount = atoi(value);
else if (!strcmp(name, "enable-log-linecount"))
ctx.cfg.enable_log_linecount = atoi(value);
+ else if (!strcmp(name, "enable-relative-dates"))
+ ctx.cfg.enable_relative_dates = atoi(value);
else if (!strcmp(name, "enable-remote-branches"))
ctx.cfg.enable_remote_branches = atoi(value);
else if (!strcmp(name, "enable-subject-links"))
@@ -311,6 +313,8 @@ static void config_cb(const char *name, const char *value)
ctx.cfg.clone_url = strdup_first_line(value);
else if (!strcmp(name, "local-time"))
ctx.cfg.local_time = atoi(value);
+ else if (!strcmp(name, "date-format"))
+ cgit_parse_date_format(value, &ctx.cfg.date_mode);
else if (!strcmp(name, "commit-sort")) {
if (!strcmp(value, "date"))
ctx.cfg.commit_sort = 1;
@@ -412,6 +416,8 @@ static void prepare_context(void)
ctx.cfg.logo = "/cgit.png";
ctx.cfg.favicon = "/favicon.ico";
ctx.cfg.local_time = 0;
+ ctx.cfg.date_mode = date_mode_from_type(DATE_SHORT);
+ ctx.cfg.enable_relative_dates = 1;
ctx.cfg.enable_http_clone = 1;
ctx.cfg.enable_index_owner = 1;
ctx.cfg.enable_tree_linenumbers = 1;
diff --git a/source/cgit.h b/source/cgit.h
index 78129b5..c41854e 100644
--- a/source/cgit.h
+++ b/source/cgit.h
@@ -7,6 +7,7 @@
#include <archive.h>
#include <commit.h>
+#include <date.h>
#include <diffcore.h>
#include <diff.h>
#include <environment.h>
@@ -217,6 +218,7 @@ struct cgit_config {
char *repository_sort;
char *virtual_root; /* Always ends with '/'. */
char *strict_export;
+ struct date_mode date_mode;
int cache_size;
int cache_dynamic_ttl;
int cache_repo_ttl;
@@ -237,6 +239,7 @@ struct cgit_config {
int enable_commit_graph;
int enable_log_filecount;
int enable_log_linecount;
+ int enable_relative_dates;
int enable_remote_branches;
int enable_subject_links;
int enable_html_serving;
@@ -382,6 +385,7 @@ extern void cgit_parse_url(const char *url);
extern const char *cgit_repobasename(const char *reponame);
extern int cgit_parse_snapshots_mask(const char *str);
+extern void cgit_parse_date_format(const char *format, struct date_mode *mode);
extern const struct object_id *cgit_snapshot_get_sig(const char *ref,
const struct cgit_snapshot_format *f);
extern const unsigned cgit_snapshot_format_bit(const struct cgit_snapshot_format *f);
diff --git a/source/shared.c b/source/shared.c
index 59f1c8e..058d938 100644
--- a/source/shared.c
+++ b/source/shared.c
@@ -439,6 +439,39 @@ int cgit_parse_snapshots_mask(const char *str)
return rv;
}
+/*
+ * Git's parse_date_format() dies on anything it does not recognize, which
+ * would turn a typo in cgitrc into a failed request, so gate it behind the
+ * set of formats cgit documents and leave the mode alone otherwise.
+ */
+void cgit_parse_date_format(const char *format, struct date_mode *mode)
+{
+ static const char * const names[] = {
+ "default", "human", "iso", "iso-strict", "iso8601",
+ "iso8601-strict", "local", "raw", "relative", "rfc",
+ "rfc2822", "short", "unix",
+ };
+ const char *rest;
+ size_t i;
+
+ if (skip_prefix(format, "format:", &rest)) {
+ // an empty strftime format would render every date blank
+ if (*rest)
+ parse_date_format(format, mode);
+ return;
+ }
+
+ for (i = 0; i < ARRAY_SIZE(names); i++) {
+ if (!skip_prefix(format, names[i], &rest))
+ continue;
+ // "iso" also prefixes "iso8601", so keep looking on a partial hit
+ if (*rest && strcmp(rest, "-local"))
+ continue;
+ parse_date_format(format, mode);
+ return;
+ }
+}
+
typedef struct {
char * name;
char * value;
diff --git a/source/ui-shared.c b/source/ui-shared.c
index ace06b2..d023243 100644
--- a/source/ui-shared.c
+++ b/source/ui-shared.c
@@ -672,6 +672,28 @@ const struct date_mode cgit_date_mode(enum date_mode_type type)
return mode;
}
+/*
+ * The mode date-format selects, used wherever an age column falls back to a
+ * calendar date. local-time still forces local rendering on top of it.
+ */
+static const struct date_mode cgit_configured_date_mode(void)
+{
+ struct date_mode mode = ctx.cfg.date_mode;
+
+ if (ctx.cfg.local_time)
+ mode.local = 1;
+ return mode;
+}
+
+static void print_abs_date(time_t t, int tz)
+{
+ html("<span title='");
+ html_attr(show_date(t, tz, cgit_date_mode(DATE_ISO8601)));
+ html("'>");
+ html_txt(show_date(t, tz, cgit_configured_date_mode()));
+ html("</span>");
+}
+
static void print_rel_date(time_t t, int tz, double value,
const char *class, const char *suffix)
{
@@ -691,12 +713,9 @@ void cgit_print_age(time_t t, int tz, time_t max_relative)
if (secs < 0)
secs = 0;
- if (secs > max_relative && max_relative >= 0) {
- html("<span title='");
- html_attr(show_date(t, tz, cgit_date_mode(DATE_ISO8601)));
- html("'>");
- html_txt(show_date(t, tz, cgit_date_mode(DATE_SHORT)));
- html("</span>");
+ if (!ctx.cfg.enable_relative_dates ||
+ (secs > max_relative && max_relative >= 0)) {
+ print_abs_date(t, tz);
return;
}