Compare commits

..

No commits in common. "a87d9a26fd0bf9475ed3653f812d7379644b5b78" and "9274162b4b245c744578e6c199ea2f11782385b9" have entirely different histories.

8 changed files with 56 additions and 225 deletions

View File

@ -116,12 +116,11 @@ Flags:
--case-sensitive use case-sensitive matching for filters --case-sensitive use case-sensitive matching for filters
--code enable support for source code files --code enable support for source code files
--code-theme string theme for source code syntax highlighting (default "solarized-dark256") --code-theme string theme for source code syntax highlighting (default "solarized-dark256")
--disable-buttons disable first/prev/next/last buttons
--exit-on-error shut down webserver on error, instead of just printing the error --exit-on-error shut down webserver on error, instead of just printing the error
--fallback serve files as application/octet-stream if no matching format is registered --fallback serve files as application/octet-stream if no matching format is registered
-f, --filter enable filtering -f, --filter enable filtering
--flash enable support for shockwave flash files (via ruffle.rs) --flash enable support for shockwave flash files (via ruffle.rs)
--fun add a bit of excitement to your day --fun adds a bit of excitement to your day
--handlers display registered handlers (for debugging) --handlers display registered handlers (for debugging)
-h, --help help for roulette -h, --help help for roulette
--images enable support for image files --images enable support for image files

View File

@ -87,7 +87,7 @@ func newFile(list []string, sortOrder string, regexes *regexes, formats types.Ty
} }
case sortOrder == "desc": case sortOrder == "desc":
for { for {
splitPath.number = splitPath.increment() splitPath.increment()
path, err = tryExtensions(splitPath, formats) path, err = tryExtensions(splitPath, formats)
if err != nil { if err != nil {
@ -95,7 +95,7 @@ func newFile(list []string, sortOrder string, regexes *regexes, formats types.Ty
} }
if path == "" { if path == "" {
splitPath.number = splitPath.decrement() splitPath.decrement()
path, err = tryExtensions(splitPath, formats) path, err = tryExtensions(splitPath, formats)
if err != nil { if err != nil {
@ -119,9 +119,9 @@ func nextFile(filePath, sortOrder string, regexes *regexes, formats types.Types)
switch { switch {
case sortOrder == "asc": case sortOrder == "asc":
splitPath.number = splitPath.increment() splitPath.increment()
case sortOrder == "desc": case sortOrder == "desc":
splitPath.number = splitPath.decrement() splitPath.decrement()
default: default:
return "", nil return "", nil
} }

View File

@ -186,15 +186,13 @@ func registerIndexHandlers(mux *httprouter.Router, args []string, index *fileInd
func importIndex(args []string, index *fileIndex, formats types.Types) error { func importIndex(args []string, index *fileIndex, formats types.Types) error {
if IndexFile != "" { if IndexFile != "" {
err := index.Import(IndexFile) err := index.Import(IndexFile)
if err == nil { if err != nil {
return nil _, err := fileList(args, &filters{}, "", index, formats)
if err != nil {
return err
}
} }
} }
_, err := fileList(args, &filters{}, "", index, formats)
if err != nil {
return err
}
return nil return nil
} }

View File

@ -19,7 +19,7 @@ import (
"seedno.de/seednode/roulette/types" "seedno.de/seednode/roulette/types"
) )
func paginateIndex(page int, fileCount int, ending bool) string { func paginate(page int, fileCount int, ending bool) string {
var html strings.Builder var html strings.Builder
var firstPage int = 1 var firstPage int = 1
@ -120,8 +120,8 @@ func serveIndexHtml(args []string, index *fileIndex, shouldPaginate bool) httpro
htmlBody.WriteString(`table,td,tr{border:none;}td{border-bottom:1px solid black;}td{white-space:nowrap;padding:.5em}</style>`) htmlBody.WriteString(`table,td,tr{border:none;}td{border-bottom:1px solid black;}td{white-space:nowrap;padding:.5em}</style>`)
htmlBody.WriteString(fmt.Sprintf("<title>Index contains %d files</title></head><body><table>", fileCount)) htmlBody.WriteString(fmt.Sprintf("<title>Index contains %d files</title></head><body><table>", fileCount))
if shouldPaginate && !DisableButtons { if shouldPaginate {
htmlBody.WriteString(paginateIndex(page, fileCount, false)) htmlBody.WriteString(paginate(page, fileCount, false))
} }
if len(indexDump) > 0 { if len(indexDump) > 0 {
@ -135,8 +135,8 @@ func serveIndexHtml(args []string, index *fileIndex, shouldPaginate bool) httpro
} }
} }
if shouldPaginate && !DisableButtons { if shouldPaginate {
htmlBody.WriteString(paginateIndex(page, fileCount, true)) htmlBody.WriteString(paginate(page, fileCount, true))
} }
htmlBody.WriteString(`</table></body></html>`) htmlBody.WriteString(`</table></body></html>`)

View File

@ -12,41 +12,40 @@ import (
) )
const ( const (
ReleaseVersion string = "3.1.0" ReleaseVersion string = "3.0.2"
) )
var ( var (
All bool All bool
Audio bool Audio bool
Bind string Bind string
CaseSensitive bool CaseSensitive bool
Code bool Code bool
CodeTheme string CodeTheme string
DisableButtons bool ExitOnError bool
ExitOnError bool Fallback bool
Fallback bool Filtering bool
Filtering bool Flash bool
Flash bool Fun bool
Fun bool Handlers bool
Handlers bool Images bool
Images bool Index bool
Index bool IndexFile string
IndexFile string Info bool
Info bool MaxFileCount int
MaxFileCount int MinFileCount int
MinFileCount int PageLength int
PageLength int Port int
Port int Prefix string
Prefix string Profile bool
Profile bool Recursive bool
Recursive bool Refresh bool
Refresh bool Russian bool
Russian bool Sorting bool
Sorting bool Text bool
Text bool Verbose bool
Verbose bool Version bool
Version bool Videos bool
Videos bool
rootCmd = &cobra.Command{ rootCmd = &cobra.Command{
Use: "roulette <path> [path]...", Use: "roulette <path> [path]...",
@ -89,7 +88,6 @@ func init() {
rootCmd.Flags().BoolVar(&CaseSensitive, "case-sensitive", false, "use case-sensitive matching for filters") rootCmd.Flags().BoolVar(&CaseSensitive, "case-sensitive", false, "use case-sensitive matching for filters")
rootCmd.Flags().BoolVar(&Code, "code", false, "enable support for source code files") rootCmd.Flags().BoolVar(&Code, "code", false, "enable support for source code files")
rootCmd.Flags().StringVar(&CodeTheme, "code-theme", "solarized-dark256", "theme for source code syntax highlighting") rootCmd.Flags().StringVar(&CodeTheme, "code-theme", "solarized-dark256", "theme for source code syntax highlighting")
rootCmd.Flags().BoolVar(&DisableButtons, "disable-buttons", false, "disable first/prev/next/last buttons")
rootCmd.Flags().BoolVar(&ExitOnError, "exit-on-error", false, "shut down webserver on error, instead of just printing the error") rootCmd.Flags().BoolVar(&ExitOnError, "exit-on-error", false, "shut down webserver on error, instead of just printing the error")
rootCmd.Flags().BoolVar(&Fallback, "fallback", false, "serve files as application/octet-stream if no matching format is registered") rootCmd.Flags().BoolVar(&Fallback, "fallback", false, "serve files as application/octet-stream if no matching format is registered")
rootCmd.Flags().BoolVarP(&Filtering, "filter", "f", false, "enable filtering") rootCmd.Flags().BoolVarP(&Filtering, "filter", "f", false, "enable filtering")

View File

@ -6,12 +6,8 @@ package cmd
import ( import (
"fmt" "fmt"
"sort"
"strings"
"strconv" "strconv"
"seedno.de/seednode/roulette/types"
) )
type splitPath struct { type splitPath struct {
@ -20,22 +16,22 @@ type splitPath struct {
extension string extension string
} }
func (splitPath *splitPath) increment() string { func (splitPath *splitPath) increment() {
asInt, err := strconv.Atoi(splitPath.number) asInt, err := strconv.Atoi(splitPath.number)
if err != nil { if err != nil {
return "" return
} }
return fmt.Sprintf("%0*d", len(splitPath.number), asInt+1) splitPath.number = fmt.Sprintf("%0*d", len(splitPath.number), asInt+1)
} }
func (splitPath *splitPath) decrement() string { func (splitPath *splitPath) decrement() {
asInt, err := strconv.Atoi(splitPath.number) asInt, err := strconv.Atoi(splitPath.number)
if err != nil { if err != nil {
return "" return
} }
return fmt.Sprintf("%0*d", len(splitPath.number), asInt-1) splitPath.number = fmt.Sprintf("%0*d", len(splitPath.number), asInt-1)
} }
func split(path string, regexes *regexes) (*splitPath, error) { func split(path string, regexes *regexes) (*splitPath, error) {
@ -53,126 +49,3 @@ func split(path string, regexes *regexes) (*splitPath, error) {
return p, nil return p, nil
} }
func getRange(path string, regexes *regexes, index *fileIndex) (string, string, error) {
splitPath, err := split(path, regexes)
if err != nil {
return "", "", err
}
list := index.List()
sort.Slice(list, func(i, j int) bool {
return list[i] <= list[j]
})
var first, last, previous string
Loop:
for _, val := range list {
splitVal, err := split(val, regexes)
if err != nil {
return "", "", err
}
switch {
case splitVal.base == splitPath.base && first == "":
first = val
case splitVal.base != splitPath.base && first != "":
last = previous
break Loop
}
previous = val
}
return first, last, nil
}
func paginateSorted(path, first, last, queryParams string, regexes *regexes, formats types.Types) (string, error) {
split, err := split(path, regexes)
if err != nil {
return "", err
}
var firstStatus, prevStatus, nextStatus, lastStatus string = "", "", "", ""
if path <= first {
firstStatus = " disabled"
prevStatus = " disabled"
}
if path >= last {
nextStatus = " disabled"
lastStatus = " disabled"
}
prevPath := &splitPath{
base: split.base,
number: split.decrement(),
extension: split.extension,
}
prevPage, err := tryExtensions(prevPath, formats)
switch {
case err != nil:
return "", err
case prevPage == "":
prevStatus = " disabled"
case prevPage < first:
prevPage = first
}
nextPath := &splitPath{
base: split.base,
number: split.increment(),
extension: split.extension,
}
nextPage, err := tryExtensions(nextPath, formats)
switch {
case err != nil:
return "", err
case nextPage == "":
nextStatus = " disabled"
case nextPage > last:
nextPage = last
}
var html strings.Builder
html.WriteString(`<table style="margin-left:auto;margin-right:auto;"><tr><td>`)
html.WriteString(fmt.Sprintf(`<button onclick="window.location.href = '%s%s%s%s';"%s>First</button>`,
Prefix,
mediaPrefix,
first,
queryParams,
firstStatus))
html.WriteString(fmt.Sprintf(`<button onclick="window.location.href = '%s%s%s%s';"%s>Prev</button>`,
Prefix,
mediaPrefix,
prevPage,
queryParams,
prevStatus))
html.WriteString(fmt.Sprintf(`<button onclick="window.location.href = '%s%s%s%s';"%s>Next</button>`,
Prefix,
mediaPrefix,
nextPage,
queryParams,
nextStatus))
html.WriteString(fmt.Sprintf(`<button onclick="window.location.href = '%s%s%s%s';"%s>Last</button>`,
Prefix,
mediaPrefix,
last,
queryParams,
lastStatus))
html.WriteString("</td></tr></table>")
return html.String(), nil
}

View File

@ -307,9 +307,7 @@ func serveMedia(paths []string, regexes *regexes, index *fileIndex, formats type
refreshTimer, refreshInterval := refreshInterval(r) refreshTimer, refreshInterval := refreshInterval(r)
queryParams := generateQueryParams(filters, sortOrder, refreshInterval) rootUrl := Prefix + "/" + generateQueryParams(filters, sortOrder, refreshInterval)
rootUrl := Prefix + "/" + queryParams
var htmlBody strings.Builder var htmlBody strings.Builder
htmlBody.WriteString(`<!DOCTYPE html><html class="bg" lang="en"><head>`) htmlBody.WriteString(`<!DOCTYPE html><html class="bg" lang="en"><head>`)
@ -326,33 +324,6 @@ func serveMedia(paths []string, regexes *regexes, index *fileIndex, formats type
} }
htmlBody.WriteString(title) htmlBody.WriteString(title)
htmlBody.WriteString(`</head><body>`) htmlBody.WriteString(`</head><body>`)
var first, last string
if Index && sortOrder != "" {
first, last, err = getRange(path, regexes, index)
if err != nil {
errorChannel <- err
serverError(w, r, nil)
return
}
}
if Index && !DisableButtons && sortOrder != "" {
paginate, err := paginateSorted(path, first, last, queryParams, regexes, formats)
if err != nil {
errorChannel <- err
serverError(w, r, nil)
return
}
htmlBody.WriteString(paginate)
}
if refreshInterval != "0ms" { if refreshInterval != "0ms" {
htmlBody.WriteString(refreshFunction(rootUrl, refreshTimer)) htmlBody.WriteString(refreshFunction(rootUrl, refreshTimer))
} }
@ -366,7 +337,6 @@ func serveMedia(paths []string, regexes *regexes, index *fileIndex, formats type
return return
} }
htmlBody.WriteString(body) htmlBody.WriteString(body)
htmlBody.WriteString(`</body></html>`) htmlBody.WriteString(`</body></html>`)
startTime := time.Now() startTime := time.Now()
@ -486,7 +456,7 @@ func ServePage(args []string) error {
// enable image support if no other flags are passed, to retain backwards compatibility // enable image support if no other flags are passed, to retain backwards compatibility
// to be replaced with rootCmd.MarkFlagsOneRequired on next spf13/cobra update // to be replaced with rootCmd.MarkFlagsOneRequired on next spf13/cobra update
if Images || All || len(formats) == 0 { if Images || All || len(formats) == 0 {
formats.Add(images.Format{DisableButtons: DisableButtons, Fun: Fun}) formats.Add(images.Format{Fun: Fun})
} }
paths, err := validatePaths(args, formats) paths, err := validatePaths(args, formats)

View File

@ -26,21 +26,14 @@ type dimensions struct {
} }
type Format struct { type Format struct {
DisableButtons bool Fun bool
Fun bool
} }
func (t Format) Css() string { func (t Format) Css() string {
var css strings.Builder var css strings.Builder
css.WriteString(`html,body{margin:0;padding:0;height:100%;}`) css.WriteString(`html,body{margin:0;padding:0;height:100%;}`)
css.WriteString(`a{color:inherit;display:block;height:100%;width:100%;text-decoration:none;}`)
if t.DisableButtons {
css.WriteString(`a{color:inherit;display:block;height:100%;width:100%;text-decoration:none;}`)
} else {
css.WriteString(`a{color:inherit;display:block;height:97%;width:100%;text-decoration:none;}`)
}
css.WriteString(`img{margin:auto;display:block;max-width:97%;max-height:97%;`) css.WriteString(`img{margin:auto;display:block;max-width:97%;max-height:97%;`)
css.WriteString(`object-fit:scale-down;position:absolute;top:50%;left:50%;transform:translate(-50%,-50%)`) css.WriteString(`object-fit:scale-down;position:absolute;top:50%;left:50%;transform:translate(-50%,-50%)`)
if t.Fun { if t.Fun {