From e10f21f57481bd0f7810934f823c9cc14cffc670 Mon Sep 17 00:00:00 2001 From: Matthias Blaser Date: Thu, 18 Apr 2019 19:06:15 +0200 Subject: [PATCH] Serve default favicon, allow disabling logs --- README.md | 9 +++++ cmd/root.go | 71 ++++++++++++++++++++++++++------- helper/dump.go | 23 +++++++++++ helper/favicon.ico | Bin 0 -> 15086 bytes internal/lib/static/favicon.go | 3 ++ 5 files changed, 91 insertions(+), 15 deletions(-) create mode 100644 helper/dump.go create mode 100644 helper/favicon.ico create mode 100644 internal/lib/static/favicon.go diff --git a/README.md b/README.md index 6786173..e20e4a0 100644 --- a/README.md +++ b/README.md @@ -44,6 +44,8 @@ Flags: -k, --key string Key file (default "/home/maetthu/.config/dirhttps/key.pem") -l, --listen string Listen address (default ":8443") --no-cors Disable CORS handling + --no-favicon Disable default favicon delivered when no favicon.ico is present in current directory + -q, --quiet Don't log requests to STDOUT --version version for dirhttps ``` @@ -64,3 +66,10 @@ $ dirhttps $ dirhttps -l :1234 $ dirhttps -l 127.0.0.2:8443 ``` + + +## License + +The default favicon served by dirhttps is generated from the [Font Awesome "code" icon](https://fontawesome.com/icons/code?style=solid) by [FontIcon](https://github.com/devgg/FontIcon) and is [licensed under the CC BY 4.0 License](https://fontawesome.com/license/free). + +dirhttps is licensed under the MIT License. \ No newline at end of file diff --git a/cmd/root.go b/cmd/root.go index c988ae0..5a340ec 100644 --- a/cmd/root.go +++ b/cmd/root.go @@ -2,15 +2,17 @@ package cmd import ( "fmt" - "github.com/maetthu/dirhttps/internal/lib/version" - "github.com/mitchellh/go-homedir" - "github.com/rs/cors" - "github.com/spf13/cobra" "log" "net/http" "net/http/httputil" "os" "path/filepath" + + "github.com/maetthu/dirhttps/internal/lib/static" + "github.com/maetthu/dirhttps/internal/lib/version" + "github.com/mitchellh/go-homedir" + "github.com/rs/cors" + "github.com/spf13/cobra" ) const ( @@ -19,9 +21,9 @@ const ( ) var rootCmd = &cobra.Command{ - Use: "dirhttps", - Short: "Serving contents of current directory by HTTPS.", - Args: cobra.NoArgs, + Use: "dirhttps", + Short: "Serving contents of current directory by HTTPS.", + Args: cobra.NoArgs, Version: fmt.Sprintf("%s -- %s", version.Version, version.Commit), Run: func(cmd *cobra.Command, args []string) { @@ -39,11 +41,11 @@ var rootCmd = &cobra.Command{ certAvailable := true - if _, err := os.Stat(certFile); err != nil { + if _, err := os.Stat(certFile); err != nil { certAvailable = false } - if _, err := os.Stat(keyFile); err != nil { + if _, err := os.Stat(keyFile); err != nil { certAvailable = false } @@ -53,7 +55,7 @@ var rootCmd = &cobra.Command{ "Store a certificate to \"%s\" and a key file to \"%s\" or provide the --cert and --key flags", certFile, keyFile, - ) + ) } dir, err := os.Getwd() @@ -71,13 +73,23 @@ var rootCmd = &cobra.Command{ log.Printf("Listening for HTTPS connections on %s", addr) log.Printf("Serving from directory %s", dir) - handler := logger(http.FileServer(http.Dir(dir))) + handler := http.FileServer(http.Dir(dir)) + + // favicon + if disableFavicon, _ := cmd.Flags().GetBool("no-favicon"); !disableFavicon { + handler = favicon(handler) + } + + // logger + if quiet, _ := cmd.Flags().GetBool("quiet"); !quiet { + handler = logger(handler) + } // permit some CORS stuff if disableCORS, _ := cmd.Flags().GetBool("no-cors"); !disableCORS { handler = cors.New(cors.Options{ AllowCredentials: true, - AllowOriginFunc: func(origin string) bool {return true}, + AllowOriginFunc: func(origin string) bool { return true }, }).Handler(handler) } @@ -103,7 +115,7 @@ func Execute() { } } -func init(){ +func init() { home, err := homedir.Dir() if err != nil { @@ -120,13 +132,42 @@ func init(){ rootCmd.Flags().StringP("listen", "l", ":8443", "Listen address") rootCmd.Flags().Bool("cache", false, "Enable client side caching") - rootCmd.Flags().BoolP("dump", "d",false, "Dump client request headers to STDOUT") + rootCmd.Flags().BoolP("dump", "d", false, "Dump client request headers to STDOUT") + rootCmd.Flags().BoolP("quiet", "q", false, "Don't log requests to STDOUT") rootCmd.Flags().Bool("no-cors", false, "Disable CORS handling") + rootCmd.Flags().Bool( + "no-favicon", + false, + "Disable default favicon delivered when no favicon.ico is present in current directory", + ) +} + +func favicon(handler http.Handler) http.Handler { + return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { + if r.RequestURI != "/favicon.ico" { + handler.ServeHTTP(w, r) + return + } + + i, err := os.Stat("favicon.ico") + + if !os.IsNotExist(err) && !i.IsDir() { + handler.ServeHTTP(w, r) + return + } + + w.Header().Add("Content-Type", "image/vnd.microsoft.icon") + _, err = w.Write(static.Favicon) + + if err != nil { + log.Print(err) + } + }) } func logger(handler http.Handler) http.Handler { return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - log.Printf( "%s \"%s %s %s\"\n", r.RemoteAddr, r.Method, r.URL, r.Proto) + log.Printf("%s \"%s %s %s\"\n", r.RemoteAddr, r.Method, r.URL, r.Proto) handler.ServeHTTP(w, r) }) } diff --git a/helper/dump.go b/helper/dump.go new file mode 100644 index 0000000..3d2d2e2 --- /dev/null +++ b/helper/dump.go @@ -0,0 +1,23 @@ +package main + +import ( + "fmt" + "io/ioutil" + "log" + "os" +) + +func main() { + f, err := os.Open("favicon.ico") + + if err != nil { + log.Fatal(err) + } + + b, err := ioutil.ReadAll(f) + if err != nil { + log.Fatal(err) + } + + fmt.Printf("%#v", b) +} diff --git a/helper/favicon.ico b/helper/favicon.ico new file mode 100644 index 0000000000000000000000000000000000000000..552e208cbb84cf5b557d1e815977bcc67803fc69 GIT binary patch literal 15086 zcmeI23v3ic7{|91Deps2sDiXjz()W96COd+BS?bJM8ptHL=o`;BuZ2WDz-%fm|&vB zM2!y!5Ct_v@tpv%ATf#v8i`7bP(ekkk*gqW;pqAMZ}%h1vUjw-UhO6KCBJ_2_-5vt z+1Z)dxjIgslkbce;h>A1b%PyewBtC%#a_IZ6MebX`0#s%!cqUz&t(7TjL$)obAZ~)$cLNK|OKrNW>rXMkbB)TW*FT)|2 z4VmggK6OtA|2%)4cps2l2tR`PZTdaZ3Ls3nk@y_MLH0*r9wf6Tt3{%9d=4B2^Go_9 zXzVnGnpbPUpRe$K2>Wu9kBi|r_{$t4UIAU8HAL;q2aS!t9Shfx9tFuv@b6)=(b(P! zLD4((D_A{#T~GQl(7KS0bfxej(3tq^x3K!O5M(DA2Aao~Z~8@L21L(v7W@Tf=hr7l ze*s#$eyQ)zfX2dKuZ62gzZc|(NjCzU!E8+LBJDgg@@dVvDew!JtzTU`ee|06cjx#voo#dR2nq&#m5u=4$R)KH6PywooSmQeKA@M>bt)l3x7*` zDqkj&|8Gdy$4E;hTK~6#wG-4Il2?+d0`m0y-+*9Qi+@4hP)H@(6Ly1@G5s-VI;*CV zA~HV$D-+Zk$CPY3aVG@lpW@S$nM7J+{#e!N zyuYgBGWZ>W&)`+k!ruAuq_@`lOI5D4Wc{?V+B-jip#So*pBbSuwSHO?P1(Pmz}WUL zD<}Op1pU{#bhR>(Oz&Tftu&sc<`dBx9`r}?8i+zrlonQ|+%p`4&h+`ge9~CWfw1%2 zE2QiE78LE7-+=n)XA^NfueLhB(UdD;=V$E|eZ2fI^%9AG-xdA?Y!A_Ty&QDLQ=XpJ zJZSCnGgZ2xwPPwA0NwLk0IB3QGR-&Zht2~te1#%}wJ!Y$v!NqoQnY4h?rNVsn+(Q4 zeKp@ruOdzLm}tG$`k!gvt-Ypd&4c&B{5JhPY5HEv2GQDOew#i<+N5l79v`m+t+D32 z>BU*%e{cNU5#s+A(z<6!AD$2Rf0XzJP~WmaZotW(Kxd)_a251|Y>`elIskO8%Smno zawCu%f!qkRgAqu$!r`RF`UoXeeo;Vg@#2-?y1pv0QsrV*1FxSm2=DTq@7q) zC#HtHShS*?kBIzOv@+^Abp>_Nsv^gUMe2%Td^wn|D~J~g+{y@&1s+foM6 z*nVI|a?y7~rqABGgVPybqVv9f_qFzQ7p*(#Fwq@Sy7QwCb-V^&!AOwkcXMlBclUQF zF(8)^-wJO*OYcME|5{KRYVS+97{)*h%m?}Be;131Z}#PXKv-$bk%1U*0Bb|K7H$VU zkL_T2`c27ycYY)Be|-6}lRp}hrikvwHiFeJt^Pg)ok6l3EMIru6P4(R?sV?~-TRr1 z^yhFnq>`azZUcWg&9P~qdsdU13HX1XudobH>v`M+`@mn!bIcqHTdoIu1yLt zE+K8N&sO8BJKLb>dwvi2>->TE6+uJd$=bgr#8zXx9<1I&golOLHK%YhTY*@1gE=(s}DD6I^STVQKBx64qSRTCMqL=`C4*DDH}_zdMM9%~`EA^