Goit

Simple and lightweight Git web server
git clone http://git.omkov.net/Goit
Log | Tree | Refs | README | Download

AuthorJakob Wakeling <[email protected]>
Date2023-07-26 00:39:54
Commit6f00d17f424fc5a475bb6121163d4b9b625e1e14
Parent8e4646b2a71f4f8a862be7b31ff7ff9e0e294bc4

Handle directories on the repository tree page

Diffstat

M res/admin/index.html | 2 +-
M res/admin/repo_edit.html | 2 +-
M res/admin/repos.html | 2 +-
M res/admin/user_create.html | 2 +-
M res/admin/user_edit.html | 2 +-
M res/admin/users.html | 2 +-
M res/error.html | 2 +-
M res/index.html | 2 +-
M res/repo/create.html | 2 +-
M res/repo/log.html | 2 +-
M res/repo/refs.html | 2 +-
M res/repo/tree.html | 4 ++--
M res/style.css | 6 +++---
M res/user/login.html | 2 +-
M res/user/sessions.html | 2 +-
M src/repo/tree.go | 56 ++++++++++++++++++++++++++++++++++++++++++++------------
M src/util/util.go | 20 ++++++++++----------

17 files changed, 72 insertions, 40 deletions

diff --git a/res/admin/index.html b/res/admin/index.html
index c2f95de..f42f931 100644
--- a/res/admin/index.html
+++ b/res/admin/index.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 	<table>
 		<tr>
diff --git a/res/admin/repo_edit.html b/res/admin/repo_edit.html
index 43d177e..4cb6fdb 100644
--- a/res/admin/repo_edit.html
+++ b/res/admin/repo_edit.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 	<main>
 		<h1>{{.Title}}</h1>
diff --git a/res/admin/repos.html b/res/admin/repos.html
index 5458c8c..e2da387 100644
--- a/res/admin/repos.html
+++ b/res/admin/repos.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 	<header>
 		<table>
diff --git a/res/admin/user_create.html b/res/admin/user_create.html
index cea4814..7edeb6e 100644
--- a/res/admin/user_create.html
+++ b/res/admin/user_create.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 	<main>
 		<h1>{{.Title}}</h1>
diff --git a/res/admin/user_edit.html b/res/admin/user_edit.html
index 13ca379..43badf4 100644
--- a/res/admin/user_edit.html
+++ b/res/admin/user_edit.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 	<main>
 		<h1>{{.Title}}</h1>
diff --git a/res/admin/users.html b/res/admin/users.html
index f224ae1..d37db37 100644
--- a/res/admin/users.html
+++ b/res/admin/users.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 	<header>
 		<table>
diff --git a/res/error.html b/res/error.html
index 1a00cdc..79fa76b 100644
--- a/res/error.html
+++ b/res/error.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>
+<head lang="en-GB">
 	<meta charset="UTF-8">
 	<title>{{.Status}}</title>
 	<meta name="viewport" content="width=device-width, initial-scale=1.0">
diff --git a/res/index.html b/res/index.html
index a482024..6ad6a4c 100644
--- a/res/index.html
+++ b/res/index.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 	<header>
 		<table>
diff --git a/res/repo/create.html b/res/repo/create.html
index c3b3035..46641ad 100644
--- a/res/repo/create.html
+++ b/res/repo/create.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 	<header>
 		<table>
diff --git a/res/repo/log.html b/res/repo/log.html
index 6dad3e7..f88337e 100644
--- a/res/repo/log.html
+++ b/res/repo/log.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 	<header>{{template "repo/header" .}}</header><hr>
 	<main>
diff --git a/res/repo/refs.html b/res/repo/refs.html
index 4b9097c..bfed21c 100644
--- a/res/repo/refs.html
+++ b/res/repo/refs.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 	<header>{{template "repo/header" .}}</header><hr>
 	<main>
diff --git a/res/repo/tree.html b/res/repo/tree.html
index 714fd31..9e2a1ff 100644
--- a/res/repo/tree.html
+++ b/res/repo/tree.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 	<header>{{template "repo/header" .}}</header><hr>
 	<main>
@@ -17,7 +17,7 @@
 					{{range .Files}}
 						<tr>
 							<td>{{.Mode}}</td>
-							<td><a href="/{{$.Name}}/tree/{{.Name}}">{{.Name}}</a></td>
+							<td><a href="/{{$.Name}}/tree/{{.Path}}">{{.Name}}</a></td>
 							<td align="right" {{if .B}}style="padding-right: calc(2ch + 0.4em);"{{end}}>{{.Size}}</td>
 							<td>log blame raw download</td>
 						</tr>
diff --git a/res/style.css b/res/style.css
index 9f3f842..e14b47f 100644
--- a/res/style.css
+++ b/res/style.css
@@ -1,12 +1,12 @@
 html { background-color: #111111; color: #888888; height: 100%; }
-body { font-family: monospace; margin: 1em; }
+body { font-family: monospace; margin: 1rem; }
 
 a { color: #FF7E00; text-decoration: none; }
 a:hover { text-decoration: underline; }
 h1, h2 { font-size: 1em; margin: 0; }
-hr { border: 0; height: 1em; margin: 0; }
+hr { border: 0; height: 1rem; margin: 0; }
 
-table td { padding: 0 0.4em; }
+table td { padding: 0 0.4rem; }
 table td:empty::after { content: "\00a0"; }
 
 main table tr:hover td { background-color: #222222; }
diff --git a/res/user/login.html b/res/user/login.html
index 24c080d..f7890de 100644
--- a/res/user/login.html
+++ b/res/user/login.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 <body>
 	<h1>Login</h1>
diff --git a/res/user/sessions.html b/res/user/sessions.html
index 3fe4086..2fea513 100644
--- a/res/user/sessions.html
+++ b/res/user/sessions.html
@@ -1,5 +1,5 @@
 <!DOCTYPE html>
-<head>{{template "base/head" .}}</head>
+<head lang="en-GB">{{template "base/head" .}}</head>
 <body>
 	<header>{{template "user/header" .}}</header><hr>
 	<main>
diff --git a/src/repo/tree.go b/src/repo/tree.go
index e3f22e1..3a61555 100644
--- a/src/repo/tree.go
+++ b/src/repo/tree.go
@@ -1,8 +1,11 @@
 package repo
 
 import (
+	"errors"
 	"log"
 	"net/http"
+	"path"
+	"sort"
 	"strings"
 
 	goit "github.com/Jamozed/Goit/src"
@@ -15,6 +18,7 @@ import (
 
 func HandleTree(w http.ResponseWriter, r *http.Request) {
 	_, uid := goit.AuthCookie(w, r, true)
+	treepath := mux.Vars(r)["path"]
 
 	repo, err := goit.GetRepoByName(mux.Vars(r)["repo"])
 	if err != nil {
@@ -26,8 +30,8 @@ func HandleTree(w http.ResponseWriter, r *http.Request) {
 	}
 
 	type row struct {
-		Mode, Name, Size string
-		B                bool
+		Mode, Name, Path, Size string
+		B                      bool
 	}
 	data := struct {
 		Title, Name, Description, Url string
@@ -59,25 +63,53 @@ func HandleTree(w http.ResponseWriter, r *http.Request) {
 		return
 	}
 
-	iter, err := commit.Tree()
+	tree, err := commit.Tree()
 	if err != nil {
 		log.Println("[/repo/tree]", err.Error())
 		goit.HttpError(w, http.StatusInternalServerError)
 		return
 	}
 
-	if err := iter.Files().ForEach(func(f *object.File) error {
-		size := humanize.IBytes(uint64(f.Size))
+	if treepath != "" {
+		data.Files = append(data.Files, row{Mode: "d---------", Name: "..", Path: path.Dir(treepath)})
+
+		tree, err = tree.Tree(treepath)
+		if errors.Is(err, object.ErrDirectoryNotFound) {
+			goit.HttpError(w, http.StatusNotFound)
+			return
+		} else if err != nil {
+			log.Println("[/repo/tree]", err.Error())
+			goit.HttpError(w, http.StatusInternalServerError)
+			return
+		}
+	}
+
+	sort.SliceStable(tree.Entries, func(i, j int) bool {
+		if tree.Entries[i].Mode&0o40000 != 0 && tree.Entries[j].Mode&0o40000 == 0 {
+			return true
+		}
+
+		return tree.Entries[i].Name < tree.Entries[j].Name
+	})
+
+	for _, v := range tree.Entries {
+		size := ""
+
+		if v.Mode&0o40000 == 0 {
+			file, err := tree.File(v.Name)
+			if err != nil {
+				log.Println("[/repo/tree]", err.Error())
+				goit.HttpError(w, http.StatusInternalServerError)
+				return
+			}
+
+			size = humanize.IBytes(uint64(file.Size))
+		}
+
 		data.Files = append(data.Files, row{
-			Mode: util.ModeString(uint32(f.Mode)), Name: f.Name, Size: size,
+			Mode: util.ModeString(uint32(v.Mode)), Name: v.Name, Path: path.Join(treepath, v.Name), Size: size,
 			B: util.If(strings.HasSuffix(size, " B"), true, false),
 		})
-
-		return nil
-	}); err != nil {
-		log.Println("[/repo/tree]", err.Error())
-		goit.HttpError(w, http.StatusInternalServerError)
-		return
 	}
 
 	if err := goit.Tmpl.ExecuteTemplate(w, "repo/tree", data); err != nil {
diff --git a/src/util/util.go b/src/util/util.go
index 0a75dd8..e16f483 100644
--- a/src/util/util.go
+++ b/src/util/util.go
@@ -37,15 +37,15 @@ func Cookie(r *http.Request, name string) *http.Cookie {
 }
 
 func ModeString(mode uint32) string {
-	s := "-"
-	s += If((mode&0b100000000) != 0, "r", "-")
-	s += If((mode&0b010000000) != 0, "w", "-")
-	s += If((mode&0b001000000) != 0, "x", "-")
-	s += If((mode&0b000100000) != 0, "r", "-")
-	s += If((mode&0b000010000) != 0, "w", "-")
-	s += If((mode&0b000001000) != 0, "x", "-")
-	s += If((mode&0b000000100) != 0, "r", "-")
-	s += If((mode&0b000000010) != 0, "w", "-")
-	s += If((mode&0b000000001) != 0, "x", "-")
+	s := If((mode&0o40000) != 0, "d", "-")
+	s += If((mode&0o400) != 0, "r", "-")
+	s += If((mode&0o200) != 0, "w", "-")
+	s += If((mode&0o100) != 0, "x", "-")
+	s += If((mode&0o040) != 0, "r", "-")
+	s += If((mode&0o020) != 0, "w", "-")
+	s += If((mode&0o010) != 0, "x", "-")
+	s += If((mode&0o004) != 0, "r", "-")
+	s += If((mode&0o002) != 0, "w", "-")
+	s += If((mode&0o001) != 0, "x", "-")
 	return s
 }