You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
186 lines
4.2 KiB
Go
186 lines
4.2 KiB
Go
package main
|
|
|
|
import (
|
|
"fmt"
|
|
"log"
|
|
"os"
|
|
"strings"
|
|
|
|
"github.com/alecthomas/repr"
|
|
"github.com/aziis98/cabret/config"
|
|
"github.com/aziis98/cabret/runner"
|
|
"github.com/spf13/pflag"
|
|
)
|
|
|
|
const HelpMessage = `usage: cabret <SUBCOMMAND> [OPTIONS...]
|
|
subcommands:
|
|
build [OPTIONS...] Builds the current project
|
|
serve [OPTIONS...] Starts an http server and watches files for changes
|
|
|
|
`
|
|
|
|
func main() {
|
|
flagSet := pflag.FlagSet{
|
|
Usage: func() {
|
|
fmt.Print(HelpMessage)
|
|
},
|
|
}
|
|
if err := flagSet.Parse(os.Args[1:]); err != nil {
|
|
if err != pflag.ErrHelp {
|
|
log.Fatal(err)
|
|
}
|
|
return
|
|
}
|
|
|
|
switch flagSet.Arg(0) {
|
|
case "serve":
|
|
if err := serveSubcommand(os.Args[2:]); err != nil {
|
|
if err != pflag.ErrHelp {
|
|
log.Fatal(err)
|
|
}
|
|
return
|
|
}
|
|
|
|
case "build":
|
|
if err := buildSubcommand(os.Args[2:]); err != nil {
|
|
if err != pflag.ErrHelp {
|
|
log.Fatal(err)
|
|
}
|
|
return
|
|
}
|
|
|
|
default:
|
|
fmt.Print(HelpMessage)
|
|
|
|
}
|
|
}
|
|
|
|
const BuildHelpMessage = `usage: cabret build [OPTIONS...]
|
|
options:
|
|
|
|
-c, --config <path> Path to configuration file (default is "Cabretfile.yaml")
|
|
-v, --verbose Be more verbose
|
|
|
|
`
|
|
|
|
func buildSubcommand(args []string) error {
|
|
flagSet := pflag.FlagSet{
|
|
Usage: func() { fmt.Print(BuildHelpMessage) },
|
|
}
|
|
|
|
var configFile string
|
|
flagSet.StringVarP(&configFile, "config", "c",
|
|
"Cabretfile.yaml",
|
|
`path to configuration file`,
|
|
)
|
|
|
|
var verbose bool
|
|
flagSet.BoolVarP(&verbose, "verbose", "v",
|
|
false,
|
|
`verbose output`,
|
|
)
|
|
|
|
if err := flagSet.Parse(args); err != nil {
|
|
return err
|
|
}
|
|
|
|
cabretfile, err := config.ReadCabretfile(configFile)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
if err := runner.RunConfig(cabretfile); err != nil {
|
|
return err
|
|
}
|
|
|
|
return nil
|
|
}
|
|
|
|
const ServeHelpMessage = `usage: cabret serve [OPTIONS...]
|
|
options:
|
|
|
|
-c, --config <path> Path to configuration file (default is "Cabretfile.yaml")
|
|
-v, --verbose Be more verbose
|
|
-w, --watch <pattern> List of paths to watch for rebuild
|
|
-m, --mount <path> Mount a file or folder on the default static file
|
|
server, this will mount file or folder at "<path>"
|
|
on route "<path>".
|
|
-m, --mount <from>:<to> Mount a file or folder on the default static file
|
|
server, this will mount file or folder at "<from>"
|
|
on route "<to>".
|
|
|
|
By default the mount list is "public/:/", "dist/:/", "out/:/".
|
|
|
|
The server will also serve a special js script on "/cabret/live-reload.js" that
|
|
will add live reload on file change for development, this can be included with
|
|
the following tag
|
|
|
|
<script type="module" src="/__cabret__/live-reload.js" async></script>
|
|
|
|
`
|
|
|
|
func serveSubcommand(args []string) error {
|
|
flagSet := pflag.FlagSet{
|
|
Usage: func() { fmt.Print(ServeHelpMessage) },
|
|
}
|
|
|
|
var configFile string
|
|
flagSet.StringVarP(&configFile, "config", "c",
|
|
"Cabretfile.yaml",
|
|
`path to configuration file`,
|
|
)
|
|
|
|
var verbose bool
|
|
flagSet.BoolVarP(&verbose, "verbose", "v",
|
|
false,
|
|
`verbose output`,
|
|
)
|
|
|
|
var watchedPatterns []string
|
|
flagSet.StringArrayVarP(&watchedPatterns, "watch", "w",
|
|
[]string{"src/**/"},
|
|
`list of paths to watch for rebuild`,
|
|
)
|
|
|
|
var mounts []string
|
|
flagSet.StringArrayVarP(&mounts, "mount", "m",
|
|
[]string{"public/:/", "out/:/", "dist/:/"},
|
|
`list of paths to mount for the static file server`,
|
|
)
|
|
|
|
err := flagSet.Parse(args)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
serveMounts := make([]serveMount, len(mounts))
|
|
for i, m := range mounts {
|
|
path, route, found := strings.Cut(m, ":")
|
|
if !found {
|
|
if strings.HasPrefix(path, "/") {
|
|
return fmt.Errorf(`cannot mount an absolute path without a route: "%s"`, path)
|
|
}
|
|
|
|
route = "/" + path
|
|
}
|
|
|
|
if !strings.HasPrefix(route, "/") {
|
|
return fmt.Errorf(`route must start with a slash: "%s"`, route)
|
|
}
|
|
|
|
serveMounts[i] = serveMount{path, route}
|
|
}
|
|
|
|
log.Printf(`configFile = %v`, repr.String(configFile))
|
|
log.Printf(`verbose = %v`, repr.String(verbose))
|
|
log.Printf(`watchedPatterns = %v`, repr.String(watchedPatterns))
|
|
log.Printf(`serveMounts = %v`, repr.String(serveMounts))
|
|
|
|
return serve(serveConfig{
|
|
configFile,
|
|
verbose,
|
|
watchedPatterns,
|
|
serveMounts,
|
|
})
|
|
}
|