mirror of
https://github.com/caddyserver/caddy.git
synced 2025-01-13 22:36:27 +03:00
browse: Customizable default sort options (#6468)
* fileserver: add `sort` options * fix: test * fileserver: check options in `Provison` * fileserver: more obvious err alerts in sort options
This commit is contained in:
parent
840094ac65
commit
b198678174
5 changed files with 103 additions and 4 deletions
|
@ -0,0 +1,36 @@
|
||||||
|
:80
|
||||||
|
|
||||||
|
file_server browse {
|
||||||
|
sort size desc
|
||||||
|
}
|
||||||
|
----------
|
||||||
|
{
|
||||||
|
"apps": {
|
||||||
|
"http": {
|
||||||
|
"servers": {
|
||||||
|
"srv0": {
|
||||||
|
"listen": [
|
||||||
|
":80"
|
||||||
|
],
|
||||||
|
"routes": [
|
||||||
|
{
|
||||||
|
"handle": [
|
||||||
|
{
|
||||||
|
"browse": {},
|
||||||
|
"handler": "file_server",
|
||||||
|
"hide": [
|
||||||
|
"./Caddyfile"
|
||||||
|
],
|
||||||
|
"sort": [
|
||||||
|
"size",
|
||||||
|
"desc"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -206,11 +206,34 @@ func (fsrv *FileServer) loadDirectoryContents(ctx context.Context, fileSystem fs
|
||||||
// browseApplyQueryParams applies query parameters to the listing.
|
// browseApplyQueryParams applies query parameters to the listing.
|
||||||
// It mutates the listing and may set cookies.
|
// It mutates the listing and may set cookies.
|
||||||
func (fsrv *FileServer) browseApplyQueryParams(w http.ResponseWriter, r *http.Request, listing *browseTemplateContext) {
|
func (fsrv *FileServer) browseApplyQueryParams(w http.ResponseWriter, r *http.Request, listing *browseTemplateContext) {
|
||||||
|
var orderParam, sortParam string
|
||||||
|
|
||||||
|
// The configs in Caddyfile have lower priority than Query params,
|
||||||
|
// so put it at first.
|
||||||
|
for idx, item := range fsrv.SortOptions {
|
||||||
|
// Only `sort` & `order`, 2 params are allowed
|
||||||
|
if idx >= 2 {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
switch item {
|
||||||
|
case sortByName, sortByNameDirFirst, sortBySize, sortByTime:
|
||||||
|
sortParam = item
|
||||||
|
case sortOrderAsc, sortOrderDesc:
|
||||||
|
orderParam = item
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
layoutParam := r.URL.Query().Get("layout")
|
layoutParam := r.URL.Query().Get("layout")
|
||||||
sortParam := r.URL.Query().Get("sort")
|
|
||||||
orderParam := r.URL.Query().Get("order")
|
|
||||||
limitParam := r.URL.Query().Get("limit")
|
limitParam := r.URL.Query().Get("limit")
|
||||||
offsetParam := r.URL.Query().Get("offset")
|
offsetParam := r.URL.Query().Get("offset")
|
||||||
|
sortParamTmp := r.URL.Query().Get("sort")
|
||||||
|
if sortParamTmp != "" {
|
||||||
|
sortParam = sortParamTmp
|
||||||
|
}
|
||||||
|
orderParamTmp := r.URL.Query().Get("order")
|
||||||
|
if orderParamTmp != "" {
|
||||||
|
orderParam = orderParamTmp
|
||||||
|
}
|
||||||
|
|
||||||
switch layoutParam {
|
switch layoutParam {
|
||||||
case "list", "grid", "":
|
case "list", "grid", "":
|
||||||
|
@ -233,11 +256,11 @@ func (fsrv *FileServer) browseApplyQueryParams(w http.ResponseWriter, r *http.Re
|
||||||
// then figure out the order
|
// then figure out the order
|
||||||
switch orderParam {
|
switch orderParam {
|
||||||
case "":
|
case "":
|
||||||
orderParam = "asc"
|
orderParam = sortOrderAsc
|
||||||
if orderCookie, orderErr := r.Cookie("order"); orderErr == nil {
|
if orderCookie, orderErr := r.Cookie("order"); orderErr == nil {
|
||||||
orderParam = orderCookie.Value
|
orderParam = orderCookie.Value
|
||||||
}
|
}
|
||||||
case "asc", "desc":
|
case sortOrderAsc, sortOrderDesc:
|
||||||
http.SetCookie(w, &http.Cookie{Name: "order", Value: orderParam, Secure: r.TLS != nil})
|
http.SetCookie(w, &http.Cookie{Name: "order", Value: orderParam, Secure: r.TLS != nil})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -373,4 +373,7 @@ const (
|
||||||
sortByNameDirFirst = "namedirfirst"
|
sortByNameDirFirst = "namedirfirst"
|
||||||
sortBySize = "size"
|
sortBySize = "size"
|
||||||
sortByTime = "time"
|
sortByTime = "time"
|
||||||
|
|
||||||
|
sortOrderAsc = "asc"
|
||||||
|
sortOrderDesc = "desc"
|
||||||
)
|
)
|
||||||
|
|
|
@ -171,6 +171,17 @@ func (fsrv *FileServer) UnmarshalCaddyfile(d *caddyfile.Dispenser) error {
|
||||||
}
|
}
|
||||||
fsrv.EtagFileExtensions = etagFileExtensions
|
fsrv.EtagFileExtensions = etagFileExtensions
|
||||||
|
|
||||||
|
case "sort":
|
||||||
|
for d.NextArg() {
|
||||||
|
dVal := d.Val()
|
||||||
|
switch dVal {
|
||||||
|
case sortByName, sortBySize, sortByTime, sortOrderAsc, sortOrderDesc:
|
||||||
|
fsrv.SortOptions = append(fsrv.SortOptions, dVal)
|
||||||
|
default:
|
||||||
|
return d.Errf("unknown sort option '%s'", dVal)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
default:
|
default:
|
||||||
return d.Errf("unknown subdirective '%s'", d.Val())
|
return d.Errf("unknown subdirective '%s'", d.Val())
|
||||||
}
|
}
|
||||||
|
|
|
@ -153,6 +153,16 @@ type FileServer struct {
|
||||||
// a 404 error. By default, this is false (disabled).
|
// a 404 error. By default, this is false (disabled).
|
||||||
PassThru bool `json:"pass_thru,omitempty"`
|
PassThru bool `json:"pass_thru,omitempty"`
|
||||||
|
|
||||||
|
// Override the default sort.
|
||||||
|
// It includes the following options:
|
||||||
|
// - sort_by: name(default), namedirfirst, size, time
|
||||||
|
// - order: asc(default), desc
|
||||||
|
// eg.:
|
||||||
|
// - `sort time desc` will sort by time in descending order
|
||||||
|
// - `sort size` will sort by size in ascending order
|
||||||
|
// The first option must be `sort_by` and the second option must be `order` (if exists).
|
||||||
|
SortOptions []string `json:"sort,omitempty"`
|
||||||
|
|
||||||
// Selection of encoders to use to check for precompressed files.
|
// Selection of encoders to use to check for precompressed files.
|
||||||
PrecompressedRaw caddy.ModuleMap `json:"precompressed,omitempty" caddy:"namespace=http.precompressed"`
|
PrecompressedRaw caddy.ModuleMap `json:"precompressed,omitempty" caddy:"namespace=http.precompressed"`
|
||||||
|
|
||||||
|
@ -236,6 +246,22 @@ func (fsrv *FileServer) Provision(ctx caddy.Context) error {
|
||||||
fsrv.precompressors[ae] = p
|
fsrv.precompressors[ae] = p
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// check sort options
|
||||||
|
for idx, sortOption := range fsrv.SortOptions {
|
||||||
|
switch idx {
|
||||||
|
case 0:
|
||||||
|
if sortOption != sortByName && sortOption != sortByNameDirFirst && sortOption != sortBySize && sortOption != sortByTime {
|
||||||
|
return fmt.Errorf("the first option must be one of the following: %s, %s, %s, %s, but got %s", sortByName, sortByNameDirFirst, sortBySize, sortByTime, sortOption)
|
||||||
|
}
|
||||||
|
case 1:
|
||||||
|
if sortOption != sortOrderAsc && sortOption != sortOrderDesc {
|
||||||
|
return fmt.Errorf("the second option must be one of the following: %s, %s, but got %s", sortOrderAsc, sortOrderDesc, sortOption)
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
return fmt.Errorf("only max 2 sort options are allowed, but got %d", idx+1)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue