forked from codegangsta/gin
-
Notifications
You must be signed in to change notification settings - Fork 0
/
main.go
108 lines (90 loc) · 2.12 KB
/
main.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
package main
import (
"errors"
"fmt"
"github.com/codegangsta/cli"
"github.com/codegangsta/gin/lib"
"log"
"os"
"path/filepath"
"strconv"
"time"
)
var (
startTime = time.Now()
logger = log.New(os.Stdout, "[gin] ", 0)
buildError error
)
func main() {
app := cli.NewApp()
app.Name = "gin"
app.Usage = "A live reload utility for Go web applications."
app.Action = MainAction
app.Flags = []cli.Flag{
cli.IntFlag{"port,p", 3000, "port for the proxy server"},
cli.IntFlag{"appPort,a", 3001, "port for the Go web server"},
cli.StringFlag{"bin,b", "gin-bin", "name of generated binary file"},
}
app.Run(os.Args)
}
func MainAction(c *cli.Context) {
port := c.Int("port")
appPort := strconv.Itoa(c.Int("appPort"))
os.Setenv("PORT", appPort)
wd, err := os.Getwd()
if err != nil {
logger.Fatal(err)
}
builder := gin.NewBuilder(".", c.String("bin"))
runner := gin.NewRunner(filepath.Join(wd, builder.Binary()))
runner.SetWriter(os.Stdout)
proxy := gin.NewProxy(builder, runner)
config := &gin.Config{
Port: port,
ProxyTo: "http://localhost:" + appPort,
}
err = proxy.Run(config)
if err != nil {
logger.Fatal(err)
}
logger.Printf("listening on port %d\n", port)
// build right now
build(builder, logger)
// scan for changes
scanChanges(func(path string) {
runner.Kill()
build(builder, logger)
})
}
func build(builder gin.Builder, logger *log.Logger) {
err := builder.Build()
if err != nil {
buildError = err
logger.Println("ERROR! Build failed.")
fmt.Println(builder.Errors())
} else {
// print success only if there were errors before
if buildError != nil {
logger.Println("Build Successful")
}
buildError = nil
}
time.Sleep(100 * time.Millisecond)
}
type scanCallback func(path string)
func scanChanges(cb scanCallback) {
for {
filepath.Walk(".", func(path string, info os.FileInfo, err error) error {
if path == ".git" {
return filepath.SkipDir
}
if filepath.Ext(path) == ".go" && info.ModTime().After(startTime) {
cb(path)
startTime = time.Now()
return errors.New("done")
}
return nil
})
time.Sleep(500 * time.Millisecond)
}
}