From cba6351d62d52f333aa73867899de948ec0db5e3 Mon Sep 17 00:00:00 2001 From: "Gerasimos (Makis) Maropoulos" Date: Tue, 7 Jul 2020 06:11:44 +0300 Subject: [PATCH] HandleDir: customize file/dir listing page through registered view engine Former-commit-id: 98bfd9d5a073c5bc7c2c167e2a72dd7b05bfb24a --- HISTORY.md | 1 + _examples/file-server/file-server/main.go | 154 ++---------------- .../file-server/views/dirlist.html | 121 ++++++++++++++ aliases.go | 1 - core/router/fs.go | 13 +- 5 files changed, 150 insertions(+), 140 deletions(-) create mode 100644 _examples/file-server/file-server/views/dirlist.html diff --git a/HISTORY.md b/HISTORY.md index 384c472a..0034b187 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -379,6 +379,7 @@ Other Improvements: - Fix [#1552](https://github.com/kataras/iris/issues/1552). - Proper listing of root directories on `Party.HandleDir` when its `DirOptions.ShowList` was set to true. + - Customize the file/directory listing page through views, see [example](https://github.com/kataras/iris/tree/master/_examples/file-server/file-server) - Socket Sharding as requested at [#1544](https://github.com/kataras/iris/issues/1544). New `iris.WithSocketSharding` Configurator and `SocketSharding bool` setting. diff --git a/_examples/file-server/file-server/main.go b/_examples/file-server/file-server/main.go index e3501248..7531d504 100644 --- a/_examples/file-server/file-server/main.go +++ b/_examples/file-server/file-server/main.go @@ -3,7 +3,6 @@ package main import ( "crypto/md5" "fmt" - "html/template" "io" "mime/multipart" "os" @@ -28,7 +27,22 @@ const ( func main() { app := iris.New() - app.RegisterView(iris.HTML("./views", ".html")) + view := iris.HTML("./views", ".html") + view.AddFunc("formatBytes", func(b int64) string { + const unit = 1000 + if b < unit { + return fmt.Sprintf("%d B", b) + } + div, exp := int64(unit), 0 + for n := b / unit; n >= unit; n /= unit { + div *= unit + exp++ + } + return fmt.Sprintf("%.1f %cB", + float64(b)/float64(div), "kMGTPE"[exp]) + }) + app.RegisterView(view) + // Serve assets (e.g. javascript, css). // app.HandleDir("/public", "./public") @@ -44,7 +58,8 @@ func main() { ShowList: true, DirList: iris.DirListRich(iris.DirListRichOptions{ // Optionally, use a custom template for listing: - Tmpl: dirListRichTemplate, + // Tmpl: dirListRichTemplate, + TmplName: "dirlist.html", }), }) @@ -107,136 +122,3 @@ func deleteFile(ctx iris.Context) { ctx.Redirect("/files") } - -var dirListRichTemplate = template.Must(template.New("dirlist"). - Funcs(template.FuncMap{ - "formatBytes": func(b int64) string { - const unit = 1000 - if b < unit { - return fmt.Sprintf("%d B", b) - } - div, exp := int64(unit), 0 - for n := b / unit; n >= unit; n /= unit { - div *= unit - exp++ - } - return fmt.Sprintf("%.1f %cB", - float64(b)/float64(div), "kMGTPE"[exp]) - }, - }).Parse(` - - - - - - - {{.Title}} - - - - - - - - - - - - - - {{ range $idx, $file := .Files }} - - - - {{ if $file.Info.IsDir }} - - {{ else }} - - {{ end }} - - - - {{ end }} - -
#NameSizeActions
{{ $idx }}{{ $file.Name }}Dir{{ formatBytes $file.Info.Size }}
- - -`)) diff --git a/_examples/file-server/file-server/views/dirlist.html b/_examples/file-server/file-server/views/dirlist.html new file mode 100644 index 00000000..2fecf72a --- /dev/null +++ b/_examples/file-server/file-server/views/dirlist.html @@ -0,0 +1,121 @@ + + + + + + + {{.Title}} + + + + + + + + + + + + + + + {{ range $idx, $file := .Files }} + + + + {{ if $file.Info.IsDir }} + + {{ else }} + + {{ end }} + + + + {{ end }} + +
#NameSizeActions
{{ $idx }}{{ $file.Name }}Dir{{ formatBytes $file.Info.Size }}
+ + + + \ No newline at end of file diff --git a/aliases.go b/aliases.go index 001053a7..6d5cde24 100644 --- a/aliases.go +++ b/aliases.go @@ -99,7 +99,6 @@ type ( // A shortcut for the `router.DirOptions`, useful when `FileServer` or `HandleDir` is being used. DirOptions = router.DirOptions // DirListRichOptions the options for the `DirListRich` helper function. - // The Tmpl's "dirlist" template will be executed. // A shortcut for the `router.DirListRichOptions`. // Useful when `DirListRich` function is passed to `DirOptions.DirList` field. DirListRichOptions = router.DirListRichOptions diff --git a/core/router/fs.go b/core/router/fs.go index 1fafb7d7..dff49d3f 100644 --- a/core/router/fs.go +++ b/core/router/fs.go @@ -567,9 +567,13 @@ func DirectoryExists(dir string) bool { } // DirListRichOptions the options for the `DirListRich` helper function. -// The Tmpl's "dirlist" template will be executed. type DirListRichOptions struct { + // If not nil then this template's "dirlist" is used to render the listing page. Tmpl *template.Template + // If not empty then this view file is used to render the listing page. + // The view should be registered with `Application.RegisterView`. + // E.g. "dirlist.html" + TmplName string } // DirListRich is a `DirListFunc` which can be passed to `DirOptions.DirList` field @@ -580,8 +584,7 @@ func DirListRich(opts ...DirListRichOptions) DirListFunc { if len(opts) > 0 { options = opts[0] } - - if options.Tmpl == nil { + if options.TmplName == "" && options.Tmpl == nil { options.Tmpl = DirListRichTemplate } @@ -630,6 +633,10 @@ func DirListRich(opts ...DirListRichOptions) DirListFunc { }) } + if options.TmplName != "" { + return ctx.View(options.TmplName, pageData) + } + return options.Tmpl.ExecuteTemplate(ctx, "dirlist", pageData) } }