A minimal self-hosted git browser on Rust axum: bare repos rendered as a website with commits, diffs, syntax-highlighted blobs, atom feeds, and clone over HTTPS.
axumdockergitgit-browsergitoxidegixrustself-hosted
1{% extends "base.html" %}
2{% block title %}{{ repo.name }} · {{ commit.short_id }}{% endblock %}
3
4{% block breadcrumbs %}
5<div class="breadcrumbs">
6 <div class="container">
7 <a href="/">repos</a> / <a href="/{{ repo.name }}">{{ repo.name }}</a> / <a href="/{{ repo.name }}/log">log</a> / <strong>{{ commit.short_id }}</strong>
8 </div>
9</div>
10{% endblock %}
11
12{% block main %}
13<section class="commit-head">
14 <h1>{{ commit.summary }}</h1>
15 <p class="meta">
16 <span class="sha">{{ commit.short_id }}</span>
17 by <strong>{{ commit.author }}</strong>
18 · {{ commit.time|naturaltime }}
19 </p>
20 {% if commit.message and commit.message|length > commit.summary|length + 1 %}
21 <pre class="commit-msg">{{ commit.message }}</pre>
22 {% endif %}
23</section>
24
25<section class="diff">
26 {% for f in files %}
27 <article class="file-diff">
28 <header class="file-diff__head">
29 <span class="status status--{{ f.status }}">{{ f.status }}</span>
30 <span class="path">{% if f.old_path %}{{ f.old_path }} → {% endif %}{{ f.path }}</span>
31 </header>
32 {% if f.is_binary %}
33 <p class="empty">binary file</p>
34 {% else %}
35 {% for h in f.hunks %}
36 {# No literal newlines inside the <pre>: .line is display:block so each
37 span already starts a new line. A trailing \n in the source would
38 double the vertical space per line. #}
39 <pre class="hunk"><span class="hunk-hdr">{{ h.header }}</span>{% for l in h.lines %}<span class="line line--{{ l.kind }}">{{ l.text }}</span>{% endfor %}</pre>
40 {% endfor %}
41 {% endif %}
42 </article>
43 {% endfor %}
44</section>
45{% endblock %}