1
0
mirror of https://github.com/hrfee/jfa-go.git synced 2025-04-19 09:32:53 +00:00

Compare commits

...

3 Commits

Author SHA1 Message Date
9875458b01
rewrite time unmarshaler for mediabrowser
Last ditch effort for #69, removes quotes and trailing Z's manually and
also removes nanoseconds since they're useless.
2021-03-23 21:59:41 +00:00
f0dccc58aa
separate pprof from debug mode
enabled with -pprof now.
2021-03-23 21:59:04 +00:00
636bc22d52
reimplement Lshortfile for log wrapper
Fixes all debug messages having "logger:<line>:" instead of the actual
caller.
2021-03-23 21:57:53 +00:00
4 changed files with 101 additions and 47 deletions

View File

@ -3,6 +3,8 @@ package main
import (
"io"
"log"
"runtime"
"strconv"
c "github.com/fatih/color"
)
@ -16,24 +18,84 @@ type Logger interface {
}
type logger struct {
logger *log.Logger
printer *c.Color
logger *log.Logger
shortfile bool
printer *c.Color
}
func Lshortfile() string {
_, file, line, ok := runtime.Caller(2)
lineString := strconv.Itoa(line)
if !ok {
return ""
}
if file == "" {
return lineString
}
for i := len(file) - 1; i > 0; i-- {
if file[i] == '/' || file[i] == '\\' {
file = file[i+1:]
break
}
}
return file + ":" + lineString + ":"
}
func NewLogger(out io.Writer, prefix string, flag int, color c.Attribute) (l logger) {
// Use reimplemented Lshortfile since wrapping the log functions messes them up
if flag&log.Lshortfile != 0 {
flag -= log.Lshortfile
l.shortfile = true
}
l.logger = log.New(out, prefix, flag)
l.printer = c.New(color)
return l
}
func (l logger) Printf(format string, v ...interface{}) {
l.logger.Print(l.printer.Sprintf(format, v...))
var out string
if l.shortfile {
out = Lshortfile()
}
out += " " + l.printer.Sprintf(format, v...)
l.logger.Print(out)
}
func (l logger) Print(v ...interface{}) { l.logger.Print(l.printer.Sprint(v...)) }
func (l logger) Println(v ...interface{}) { l.logger.Print(l.printer.Sprintln(v...)) }
func (l logger) Fatal(v ...interface{}) { l.logger.Fatal(l.printer.Sprint(v...)) }
func (l logger) Print(v ...interface{}) {
var out string
if l.shortfile {
out = Lshortfile()
}
out += " " + l.printer.Sprint(v...)
l.logger.Print(out)
}
func (l logger) Println(v ...interface{}) {
var out string
if l.shortfile {
out = Lshortfile()
}
out += " " + l.printer.Sprintln(v...)
l.logger.Print(out)
}
func (l logger) Fatal(v ...interface{}) {
var out string
if l.shortfile {
out = Lshortfile()
}
out += " " + l.printer.Sprint(v...)
l.logger.Fatal(out)
}
func (l logger) Fatalf(format string, v ...interface{}) {
l.logger.Fatal(l.printer.Sprintf(format, v...))
var out string
if l.shortfile {
out = Lshortfile()
}
out += " " + l.printer.Sprintf(format, v...)
l.logger.Fatal(out)
}
type emptyLogger bool

14
main.go
View File

@ -38,6 +38,7 @@ var (
DATA, CONFIG, HOST *string
PORT *int
DEBUG *bool
PPROF *bool
TEST bool
SWAGGER *bool
warning = color.New(color.FgYellow).SprintfFunc()
@ -172,7 +173,8 @@ func start(asDaemon, firstCall bool) {
CONFIG = flag.String("config", app.configPath, "alternate path to config file.")
HOST = flag.String("host", "", "alternate address to host web ui on.")
PORT = flag.Int("port", 0, "alternate port to host web ui on.")
DEBUG = flag.Bool("debug", false, "Enables debug logging and exposes pprof.")
DEBUG = flag.Bool("debug", false, "Enables debug logging.")
PPROF = flag.Bool("pprof", false, "Exposes pprof profiler on /debug/pprof.")
SWAGGER = flag.Bool("swagger", false, "Enable swagger at /swagger/index.html")
flag.Parse()
@ -182,6 +184,9 @@ func start(asDaemon, firstCall bool) {
if *DEBUG {
os.Setenv("DEBUG", "1")
}
if *PPROF {
os.Setenv("PPROF", "1")
}
}
if os.Getenv("SWAGGER") == "1" {
@ -190,6 +195,9 @@ func start(asDaemon, firstCall bool) {
if os.Getenv("DEBUG") == "1" {
*DEBUG = true
}
if os.Getenv("PPROF") == "1" {
*PPROF = true
}
// attempt to apply command line flags correctly
if app.configPath == *CONFIG && app.dataPath != *DATA {
app.dataPath = *DATA
@ -248,11 +256,13 @@ func start(asDaemon, firstCall bool) {
debugMode = true
}
if debugMode {
app.info.Print(warning("\n\nWARNING: Don't use debug mode in production, as it exposes pprof on the network.\n\n"))
app.debug = NewLogger(os.Stdout, "[DEBUG] ", log.Ltime|log.Lshortfile, color.FgYellow)
} else {
app.debug = emptyLogger(false)
}
if *PPROF {
app.info.Print(warning("\n\nWARNING: Don't use pprof in production.\n\n"))
}
// Starts listener to receive commands over a unix socket. Use with 'jfa-go start/stop'
if asDaemon {

View File

@ -1,9 +1,6 @@
package mediabrowser
import (
"encoding/json"
"fmt"
"strings"
"time"
)
@ -17,44 +14,29 @@ type Time struct {
}
func (t *Time) UnmarshalJSON(b []byte) (err error) {
str := strings.TrimSuffix(strings.TrimPrefix(string(b), "\""), "\"")
// Trim nanoseconds to always have 6 digits, so overall length is always the same.
if str[len(str)-1] == 'Z' {
if str[len(str)-2] == 'Z' {
/* From #69, "ZZ" is sometimes used, meaning UTC-8:00.
TZ doesn't really matter to us, so we'll pretend it's UTC. */
str = str[:25] + "0Z"
} else {
str = str[:26] + "Z"
}
} else {
str = str[:26]
// str := strings.TrimSuffix(strings.TrimPrefix(string(b), "\""), "\"")
// Trim quotes from beginning and end, and any number of Zs (indicates UTC).
for b[0] == '"' {
b = b[1:]
}
// decent method
t.Time, err = time.Parse("2006-01-02T15:04:05.000000Z", str)
if err == nil {
return
for b[len(b)-1] == '"' || b[len(b)-1] == 'Z' {
b = b[:len(b)-1]
}
t.Time, err = time.Parse("2006-01-02T15:04:05.000000", str)
if err == nil {
return
// Trim nanoseconds and anything after, we don't care
i := len(b) - 1
for b[i] != '.' && i > 0 {
i--
}
// emby method
t.Time, err = time.Parse("2006-01-02T15:04:05.0000000+00:00", str)
if err == nil {
return
if i != 0 {
b = b[:i]
}
fmt.Println("THIRDERR", err)
// if all else fails, just do whatever would usually be done.
// some stored dates from jellyfin have no timezone at the end, if not we assume UTC
if str[len(str)-1] != 'Z' {
str += "Z"
}
timeJSON := []byte("{ \"parseme\": \"" + str + "\" }")
var parsed magicParse
// Magically turn it into a time.Time
err = json.Unmarshal(timeJSON, &parsed)
t.Time = parsed.Parsed
t.Time, err = time.Parse("2006-01-02T15:04:05", string(b))
// str := string(b) + "Z"
// timeJSON := []byte("{ \"parseme\": \"" + str + "\" }")
// var parsed magicParse
// // Magically turn it into a time.Time
// err = json.Unmarshal(timeJSON, &parsed)
// t.Time = parsed.Parsed
return
}

View File

@ -85,7 +85,7 @@ func (app *appContext) loadRouter(address string, debug bool) *gin.Engine {
app.loadHTML(router)
router.Use(static.Serve("/", app.webFS))
router.NoRoute(app.NoRouteHandler)
if debug {
if *PPROF {
app.debug.Println("Loading pprof")
pprof.Register(router)
}