Initial commit

This commit is contained in:
2018-11-26 15:53:01 -06:00
commit 9891169704
3 changed files with 150 additions and 0 deletions

119
compile.go Normal file
View File

@ -0,0 +1,119 @@
package precompiler
import (
"bytes"
"crypto/sha256"
"encoding/hex"
"fmt"
"io/ioutil"
"os"
"path/filepath"
"github.com/tdewolff/minify"
"github.com/tdewolff/minify/css"
"github.com/tdewolff/minify/js"
)
// FileType represents a supported file extension (without the .)
type FileType string
// supported file types
const (
CSS FileType = "css"
JS FileType = "js"
)
func initMinify() *minify.M {
minifier := minify.New()
minifier.AddFunc("text/css", css.Minify)
minifier.AddFunc("text/js", js.Minify)
return minifier
}
func getBytes(config Config, minifier *minify.M) (map[FileType]*bytes.Buffer, error) {
buf := make(map[FileType]*bytes.Buffer)
for _, file := range config.Files {
if file, err := os.Open(file); err == nil {
ext := FileType(filepath.Ext(file.Name())[1:])
if !supportedFileType(ext) {
fmt.Println("Unsupported file type:", file.Name())
continue
}
if buf[ext] == nil {
buf[ext] = &bytes.Buffer{}
}
if config.Minify {
if err = minifier.Minify("text/"+string(ext), buf[ext], file); err != nil {
return nil, err
}
} else {
if _, err = buf[ext].ReadFrom(file); err != nil {
return nil, err
}
}
} else {
return nil, err
}
}
return buf, nil
}
// CompileResult holds the results of compilation
type CompileResult struct {
Bytes []byte
Hash string
OutputPath string
}
func finalize(config Config, buf map[FileType]*bytes.Buffer) (map[FileType]*CompileResult, error) {
ret := make(map[FileType]*CompileResult, len(buf))
for key, b := range buf {
if b.Len() > 0 {
bytes := b.Bytes()
hash := sha256.Sum256(bytes)
ret[key] = &CompileResult{
Bytes: bytes,
Hash: hex.EncodeToString(hash[:]),
}
if len(config.OutputDir) > 0 {
ext := "." + string(key)
if config.Minify {
ext = ".min" + ext
}
dir := filepath.Join(config.OutputDir, string(key))
os.MkdirAll(dir, os.ModeDir)
destFile := filepath.Join(dir, "app-"+ret[key].Hash+ext)
ret[key].OutputPath = destFile
ioutil.WriteFile(destFile, bytes, 0644)
}
}
}
return ret, nil
}
// Compile compiles files indicated by the config into a single file per type
func Compile(config Config) (map[FileType]*CompileResult, error) {
var buf map[FileType]*bytes.Buffer
var err error
if buf, err = getBytes(config, initMinify()); err != nil {
return nil, err
}
return finalize(config, buf)
}
func supportedFileType(t FileType) bool {
switch t {
case CSS, JS:
return true
}
return false
}

8
config.go Normal file
View File

@ -0,0 +1,8 @@
package precompiler
// Config holds information on how to run the compiler
type Config struct {
Files []string
Minify bool
OutputDir string
}

23
main.go Normal file
View File

@ -0,0 +1,23 @@
package precompiler
func main() {
Compile(Config{
Files: []string{
"assets/css/bootstrap.min.default.css",
"assets/css/font-awesome.min.css",
"assets/css/tempusdominus-bootstrap-4.min.css",
"assets/css/roboto.css",
"assets/css/application.css",
"assets/js/jquery.min.js",
"assets/js/popper.min.js",
"assets/js/bootstrap.min.js",
"assets/js/linkify.min.js",
"assets/js/linkify-jquery.min.js",
"assets/js/moment.min.js",
"assets/js/tempusdominus-bootstrap-4.min.js",
"assets/js/application.js",
},
Minify: true,
OutputDir: "assets/",
})
}