-
Notifications
You must be signed in to change notification settings - Fork 13
/
static.go
110 lines (92 loc) · 2.44 KB
/
static.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
package handler
import (
"io/ioutil"
"net/http"
"os"
"path/filepath"
"strings"
gopi "github.com/djthorpe/gopi/v3"
)
/////////////////////////////////////////////////////////////////////
// TYPES
type Static struct {
gopi.Unit
gopi.Server
gopi.Logger
folder *string
}
type static struct {
http.Handler
}
/////////////////////////////////////////////////////////////////////
// LIFECYCLE
func (this *Static) Define(cfg gopi.Config) error {
this.folder = cfg.FlagString("http.static", "", "Path to static folder")
return nil
}
func (this *Static) New(gopi.Config) error {
// Where there is no static argument, use current working
// directory
if *this.folder == "" {
if wd, err := os.Getwd(); err != nil {
return err
} else {
*this.folder = wd
}
}
// Check static folder
if stat, err := os.Stat(*this.folder); os.IsNotExist(err) {
return gopi.ErrNotFound.WithPrefix(*this.folder)
} else if err != nil {
return gopi.ErrBadParameter.WithPrefix(*this.folder)
} else if stat.IsDir() == false {
return gopi.ErrBadParameter.WithPrefix(*this.folder)
}
// Return success
return nil
}
/////////////////////////////////////////////////////////////////////
// METHODS
// Register a service to serve static files with root of path
func (this *Static) ServeStatic(path string) error {
if this.Server == nil {
return gopi.ErrInternalAppError.WithPrefix("ServeStatic")
} else if *this.folder == "" {
return gopi.ErrBadParameter.WithPrefix("ServeStatic")
}
files, err := ioutil.ReadDir(*this.folder)
if err != nil {
return err
}
for _, file := range files {
if strings.HasPrefix(file.Name(), ".") {
continue
}
if file.IsDir() == false {
continue
}
child := filepath.Join(path, file.Name())
if strings.HasSuffix(child, "/") == false {
child = child + "/"
}
folder := filepath.Join(*this.folder, child)
if err := this.Server.RegisterService(child, NewStaticHandler(child, folder)); err != nil {
return err
} else {
this.Debugf("Register Static %q => %v", child, folder)
}
}
// Return success
return nil
}
/////////////////////////////////////////////////////////////////////
// HANDLER
func NewStaticHandler(root, folder string) http.Handler {
this := new(static)
this.Handler = http.StripPrefix(root, http.FileServer(http.Dir(folder)))
return this
}
func (this *static) ServeHTTP(w http.ResponseWriter, req *http.Request) {
// TODO: Prevent listing of directories
this.Handler.ServeHTTP(w, req)
}