summaryrefslogtreecommitdiff
path: root/handlers.go
diff options
context:
space:
mode:
authortjp <tjp@ctrl-c.club>2023-11-14 15:44:00 -0700
committertjp <tjp@ctrl-c.club>2023-11-14 15:44:00 -0700
commit105022b22d4b297057a7a946e3d6e1202bc6d1d5 (patch)
tree840eea2a699f28aac1443b2275f9a05abb098fb5 /handlers.go
parente8122362a0af5a499dcba182d6e7b41bd4b3eccf (diff)
Protocol refactor
Diffstat (limited to 'handlers.go')
-rw-r--r--handlers.go86
1 files changed, 86 insertions, 0 deletions
diff --git a/handlers.go b/handlers.go
new file mode 100644
index 0000000..4b71b28
--- /dev/null
+++ b/handlers.go
@@ -0,0 +1,86 @@
+package syw
+
+import (
+ "bytes"
+ "context"
+ "os"
+ "path"
+ "path/filepath"
+ "strings"
+ "text/template"
+
+ "tildegit.org/tjp/sliderule"
+)
+
+const (
+ repokey = "syw_repo"
+ reponamekey = "repository"
+)
+
+func rootDirHandler(proto protocol, repodir string, tmpl *template.Template, tmplname string) sliderule.Handler {
+ return sliderule.HandlerFunc(func(ctx context.Context, request *sliderule.Request) *sliderule.Response {
+ entries, err := os.ReadDir(repodir)
+ if err != nil {
+ return proto.TemporaryServerError(err)
+ }
+
+ names := []string{}
+ for _, item := range entries {
+ if Open(filepath.Join(repodir, item.Name())) != nil {
+ names = append(names, item.Name())
+ }
+ }
+
+ data := proto.TemplateBaseData(ctx, request)
+ data["Repos"] = names
+ buf := &bytes.Buffer{}
+ if err := tmpl.ExecuteTemplate(buf, tmplname, data); err != nil {
+ return proto.TemporaryServerError(err)
+ }
+
+ return proto.Success(tmplname, buf)
+ })
+}
+
+func repoRouteHandler(proto protocol, tmpl *template.Template, tmplname string) sliderule.Handler {
+ return sliderule.HandlerFunc(func(ctx context.Context, request *sliderule.Request) *sliderule.Response {
+ data := repoTmplData(proto, ctx, request)
+ buf := &bytes.Buffer{}
+ if err := tmpl.ExecuteTemplate(buf, tmplname, data); err != nil {
+ return proto.TemporaryServerError(err)
+ }
+ return proto.Success(tmplname, buf)
+ })
+}
+
+func treePathHandler(proto protocol, tmpl *template.Template, tmplname string) sliderule.Handler {
+ return sliderule.HandlerFunc(func(ctx context.Context, request *sliderule.Request) *sliderule.Response {
+ params := sliderule.RouteParams(ctx)
+ if params["path"] == "" || strings.HasSuffix(params["path"], "/") {
+ return repoRouteHandler(proto, tmpl, tmplname).Handle(ctx, request)
+ }
+
+ body, err := ctx.Value(repokey).(*Repository).Blob(ctx, params["ref"], params["path"])
+ if err != nil {
+ return proto.TemporaryServerError(err)
+ }
+ return proto.Success(path.Base(params["path"]), bytes.NewBuffer(body))
+ })
+}
+
+func repoTmplData(proto protocol, ctx context.Context, request *sliderule.Request) map[string]any {
+ data := proto.TemplateBaseData(ctx, request)
+ for k, v := range proto.TemplateRepoData(ctx, request) {
+ data[k] = v
+ }
+ return data
+}
+
+func assignRepo(repodir string) sliderule.Middleware {
+ return func(h sliderule.Handler) sliderule.Handler {
+ return sliderule.HandlerFunc(func(ctx context.Context, request *sliderule.Request) *sliderule.Response {
+ repo := Open(filepath.Join(repodir, sliderule.RouteParams(ctx)[reponamekey]))
+ return h.Handle(context.WithValue(ctx, repokey, repo), request) //nolint:staticcheck
+ })
+ }
+}