mirror of
https://github.com/nabbar/golib.git
synced 2025-12-24 11:51:02 +08:00
Refactor package errors + packages names :
- Refactor ErrorType, list errors managment, codeError - Add interface Error with error interface implement - Add type CodeError assign typiclly to const that represent code of error - Add func to registry func to retrieve message from an uint16 codeError (typicaly a switch of each codeError const) - Add default errorCode with default errorMessage if no one code or message is found - Add modeError to manage how to manage compatibility between Error interface and error interface - Add Error interface that allow parent link (parent as error or Error interface), code and trace management - Add trace finder to allow find func/file/line caller when Error is call - Add http 2 transport in httpcli - Add http 2 transport in httpserver - Add function to get client http with timeout management in httpcli - Add function to get Error if occurs of http client in httpcli - Add test for smtp package - Chg return error by returning Error in all packages - Chg package njs-archive by archive - Chg package njs-certif by certificates - Chg package njs-console by console - Chg package njs-crypt by crypt - Chg package njs-errors by errors - Chg package njs-httpcli by httpcli - Chg package njs-httpserver by httpserver - Chg package njs-ioutils by ioutils - Chg package njs-ldap by ldap - Chg package njs-logger by logger - Chg package njs-password by password - Chg package njs-progress by progress - Chg package njs-router by router - Chg package njs-semaphore by semaphore - Chg package njs-smtp by smtp - Chg package njs-static by static - Chg package njs-status by status - Chg package njs-version by version - Fix dependancies gopkg by github/go-ldap for go module compatibility - Fix gin Abort call by gin Abort with Error in static package - Fix issue #18 in status package : replace partner by component - Fix go vet error - Del deprecated function - Del useless function & files - Bump dependancies - Apply CHG in README.md
This commit is contained in:
0
static/README.md
Normal file
0
static/README.md
Normal file
58
static/error.go
Normal file
58
static/error.go
Normal file
@@ -0,0 +1,58 @@
|
||||
/*
|
||||
* MIT License
|
||||
*
|
||||
* Copyright (c) 2020 Nicolas JUHEL
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
* in the Software without restriction, including without limitation the rights
|
||||
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
* copies of the Software, and to permit persons to whom the Software is
|
||||
* furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in all
|
||||
* copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
package static
|
||||
|
||||
import errors "github.com/nabbar/golib/errors"
|
||||
|
||||
const (
|
||||
EMPTY_PARAMS errors.CodeError = iota + errors.MIN_PKG_Static
|
||||
EMPTY_PACKED
|
||||
INDEX_NOT_FOUND
|
||||
INDEX_REQUESTED_NOT_SET
|
||||
FILE_NOT_FOUND
|
||||
)
|
||||
|
||||
func init() {
|
||||
errors.RegisterFctMessage(getMessage)
|
||||
}
|
||||
|
||||
func getMessage(code errors.CodeError) (message string) {
|
||||
switch code {
|
||||
case EMPTY_PARAMS:
|
||||
return "given parameters is empty"
|
||||
case EMPTY_PACKED:
|
||||
return "packed file is empty"
|
||||
case INDEX_NOT_FOUND:
|
||||
return "mode index is defined but index.(html|htm) is not found"
|
||||
case INDEX_REQUESTED_NOT_SET:
|
||||
return "request call index but mode index is false"
|
||||
case FILE_NOT_FOUND:
|
||||
return "requested packed file is not found"
|
||||
}
|
||||
|
||||
return ""
|
||||
}
|
||||
202
static/static.go
Normal file
202
static/static.go
Normal file
@@ -0,0 +1,202 @@
|
||||
/*
|
||||
* MIT License
|
||||
*
|
||||
* Copyright (c) 2019 Nicolas JUHEL
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
* in the Software without restriction, including without limitation the rights
|
||||
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
* copies of the Software, and to permit persons to whom the Software is
|
||||
* furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in all
|
||||
* copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*
|
||||
*/
|
||||
|
||||
package static
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
"mime"
|
||||
"net/http"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
"github.com/gin-gonic/gin/render"
|
||||
"github.com/gobuffalo/packr"
|
||||
|
||||
. "github.com/nabbar/golib/errors"
|
||||
. "github.com/nabbar/golib/logger"
|
||||
|
||||
njs_router "github.com/nabbar/golib/router"
|
||||
)
|
||||
|
||||
const (
|
||||
FileIndex = "index.html"
|
||||
)
|
||||
|
||||
type staticHandler struct {
|
||||
box packr.Box
|
||||
debug bool
|
||||
index bool
|
||||
prefix string
|
||||
download []string
|
||||
allDwnld bool
|
||||
head func() map[string]string
|
||||
}
|
||||
|
||||
type Static interface {
|
||||
Register(register njs_router.RegisterRouter)
|
||||
RegisterInGroup(group string, register njs_router.RegisterRouterInGroup)
|
||||
|
||||
SetDownloadAll()
|
||||
SetDownload(file string)
|
||||
IsDownload(file string) bool
|
||||
|
||||
Has(file string) bool
|
||||
Find(file string) ([]byte, error)
|
||||
|
||||
Health() Error
|
||||
Get(c *gin.Context)
|
||||
}
|
||||
|
||||
func cleanPath(p string) string {
|
||||
return filepath.Clean(filepath.Join("/", strings.TrimLeft(p, "/")))
|
||||
}
|
||||
|
||||
func cleanJoinPath(p, e string) string {
|
||||
return cleanPath(filepath.Join(strings.TrimLeft(p, "/"), e))
|
||||
}
|
||||
|
||||
func NewStatic(hasIndex bool, prefix string, box packr.Box, Header func() map[string]string) Static {
|
||||
return &staticHandler{
|
||||
box: box,
|
||||
debug: false,
|
||||
index: hasIndex,
|
||||
prefix: cleanPath(prefix),
|
||||
head: Header,
|
||||
download: make([]string, 0),
|
||||
}
|
||||
}
|
||||
|
||||
func (s staticHandler) Register(register njs_router.RegisterRouter) {
|
||||
if s.prefix == "/" {
|
||||
for _, f := range s.box.List() {
|
||||
register(http.MethodGet, cleanJoinPath(s.prefix, f), s.Get)
|
||||
}
|
||||
} else {
|
||||
register(http.MethodGet, s.prefix, s.Get)
|
||||
register(http.MethodGet, cleanJoinPath(s.prefix, "/*file"), s.Get)
|
||||
}
|
||||
}
|
||||
|
||||
func (s staticHandler) RegisterInGroup(group string, register njs_router.RegisterRouterInGroup) {
|
||||
if s.prefix == "/" {
|
||||
for _, f := range s.box.List() {
|
||||
register(group, http.MethodGet, cleanJoinPath(s.prefix, f), s.Get)
|
||||
}
|
||||
} else {
|
||||
register(group, http.MethodGet, s.prefix, s.Get)
|
||||
register(group, http.MethodGet, cleanJoinPath(s.prefix, "/*file"), s.Get)
|
||||
}
|
||||
}
|
||||
|
||||
func (s staticHandler) print() {
|
||||
if s.debug {
|
||||
return
|
||||
}
|
||||
|
||||
for _, f := range s.box.List() {
|
||||
DebugLevel.Logf("Embedded file : %s", f)
|
||||
}
|
||||
|
||||
s.debug = true
|
||||
}
|
||||
|
||||
func (s staticHandler) Health() Error {
|
||||
s.print()
|
||||
|
||||
if len(s.box.List()) < 1 {
|
||||
return EMPTY_PACKED.Error(nil)
|
||||
}
|
||||
|
||||
if s.index && !s.box.Has("index.html") && !s.box.Has("index.htm") {
|
||||
return INDEX_NOT_FOUND.Error(nil)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s staticHandler) Has(file string) bool {
|
||||
return s.box.Has(file)
|
||||
}
|
||||
|
||||
func (s staticHandler) Find(file string) ([]byte, error) {
|
||||
return s.box.Find(file)
|
||||
}
|
||||
|
||||
func (s staticHandler) Get(c *gin.Context) {
|
||||
partPath := strings.SplitN(c.Request.URL.Path, s.prefix, 2)
|
||||
requestPath := partPath[1]
|
||||
|
||||
requestPath = strings.TrimLeft(requestPath, "./")
|
||||
requestPath = strings.Trim(requestPath, "/")
|
||||
calledFile := filepath.Base(requestPath)
|
||||
|
||||
if requestPath == "" || requestPath == "/" {
|
||||
if s.index {
|
||||
calledFile = FileIndex
|
||||
requestPath = FileIndex
|
||||
} else {
|
||||
_ = c.AbortWithError(http.StatusNotFound, INDEX_REQUESTED_NOT_SET.Error(nil))
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
if obj, err := s.box.Find(requestPath); !ErrorLevel.LogErrorCtxf(DebugLevel, "find file '%s' error for request '%s%s' :", err, calledFile, s.prefix, requestPath) {
|
||||
head := s.head()
|
||||
|
||||
if s.allDwnld || s.IsDownload(requestPath) {
|
||||
head["Content-Disposition"] = fmt.Sprintf("attachment; filename=\"%s\"", calledFile)
|
||||
}
|
||||
|
||||
c.Render(http.StatusOK, render.Reader{
|
||||
ContentLength: int64(len(obj)),
|
||||
ContentType: mime.TypeByExtension(filepath.Ext(calledFile)),
|
||||
Headers: head,
|
||||
Reader: bytes.NewReader(obj),
|
||||
})
|
||||
} else {
|
||||
_ = c.AbortWithError(http.StatusNotFound, FILE_NOT_FOUND.Error(nil))
|
||||
}
|
||||
}
|
||||
|
||||
func (s *staticHandler) SetDownload(file string) {
|
||||
s.download = append(s.download, file)
|
||||
}
|
||||
|
||||
func (s *staticHandler) SetDownloadAll() {
|
||||
s.allDwnld = true
|
||||
}
|
||||
|
||||
func (s staticHandler) IsDownload(file string) bool {
|
||||
for _, f := range s.download {
|
||||
if f == file {
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
||||
return false
|
||||
}
|
||||
Reference in New Issue
Block a user