mirror of
https://github.com/taigrr/wails.git
synced 2026-04-17 04:05:12 -07:00
Compare commits
15 Commits
Improve-bu
...
fix-lintin
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
5ef130a4a6 | ||
|
|
ea94c2de1f | ||
|
|
b323c3db20 | ||
|
|
1670ac6567 | ||
|
|
c941176018 | ||
|
|
a060d9dcc0 | ||
|
|
9bbac46b3f | ||
|
|
d8c591e64c | ||
|
|
2c28a8f550 | ||
|
|
d6c5586159 | ||
|
|
fe2a20f92a | ||
|
|
243d738d64 | ||
|
|
f0d8ce99a1 | ||
|
|
a51e127309 | ||
|
|
9393b08c3f |
@@ -163,8 +163,71 @@ func (b *bindingManager) bind(object interface{}) {
|
|||||||
b.objectsToBind = append(b.objectsToBind, object)
|
b.objectsToBind = append(b.objectsToBind, object)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (b *bindingManager) processFunctionCall(callData *callData) (interface{}, error) {
|
||||||
|
// Return values
|
||||||
|
var result []reflect.Value
|
||||||
|
var err error
|
||||||
|
|
||||||
|
function := b.functions[callData.BindingName]
|
||||||
|
if function == nil {
|
||||||
|
return nil, fmt.Errorf("Invalid function name '%s'", callData.BindingName)
|
||||||
|
}
|
||||||
|
result, err = function.call(callData.Data)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
// Do we have an error return type?
|
||||||
|
if function.hasErrorReturnType {
|
||||||
|
// We do - last result is an error type
|
||||||
|
// Check if the last result was nil
|
||||||
|
b.log.Debugf("# of return types: %d", len(function.returnTypes))
|
||||||
|
b.log.Debugf("# of results: %d", len(result))
|
||||||
|
errorResult := result[len(function.returnTypes)-1]
|
||||||
|
if !errorResult.IsNil() {
|
||||||
|
// It wasn't - we have an error
|
||||||
|
return nil, errorResult.Interface().(error)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result[0].Interface(), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (b *bindingManager) processMethodCall(callData *callData) (interface{}, error) {
|
||||||
|
// Return values
|
||||||
|
var result []reflect.Value
|
||||||
|
var err error
|
||||||
|
|
||||||
|
// do we have this method?
|
||||||
|
method := b.methods[callData.BindingName]
|
||||||
|
if method == nil {
|
||||||
|
return nil, fmt.Errorf("Invalid method name '%s'", callData.BindingName)
|
||||||
|
}
|
||||||
|
|
||||||
|
result, err = method.call(callData.Data)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
// Do we have an error return type?
|
||||||
|
if method.hasErrorReturnType {
|
||||||
|
// We do - last result is an error type
|
||||||
|
// Check if the last result was nil
|
||||||
|
b.log.Debugf("# of return types: %d", len(method.returnTypes))
|
||||||
|
b.log.Debugf("# of results: %d", len(result))
|
||||||
|
errorResult := result[len(method.returnTypes)-1]
|
||||||
|
if !errorResult.IsNil() {
|
||||||
|
// It wasn't - we have an error
|
||||||
|
return nil, errorResult.Interface().(error)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if result != nil {
|
||||||
|
return result[0].Interface(), nil
|
||||||
|
}
|
||||||
|
return nil, nil
|
||||||
|
}
|
||||||
|
|
||||||
// process an incoming call request
|
// process an incoming call request
|
||||||
func (b *bindingManager) processCall(callData *callData) (interface{}, error) {
|
func (b *bindingManager) processCall(callData *callData) (result interface{}, err error) {
|
||||||
b.log.Debugf("Wanting to call %s", callData.BindingName)
|
b.log.Debugf("Wanting to call %s", callData.BindingName)
|
||||||
|
|
||||||
// Determine if this is function call or method call by the number of
|
// Determine if this is function call or method call by the number of
|
||||||
@@ -176,13 +239,10 @@ func (b *bindingManager) processCall(callData *callData) (interface{}, error) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Return values
|
|
||||||
var result []reflect.Value
|
|
||||||
var err error
|
|
||||||
|
|
||||||
// We need to catch reflect related panics and return
|
// We need to catch reflect related panics and return
|
||||||
// a decent error message
|
// a decent error message
|
||||||
// TODO: DEBUG THIS!
|
// TODO: DEBUG THIS!
|
||||||
|
|
||||||
defer func() {
|
defer func() {
|
||||||
if r := recover(); r != nil {
|
if r := recover(); r != nil {
|
||||||
err = fmt.Errorf("%s", r.(string))
|
err = fmt.Errorf("%s", r.(string))
|
||||||
@@ -191,59 +251,14 @@ func (b *bindingManager) processCall(callData *callData) (interface{}, error) {
|
|||||||
|
|
||||||
switch dotCount {
|
switch dotCount {
|
||||||
case 1:
|
case 1:
|
||||||
function := b.functions[callData.BindingName]
|
result, err = b.processFunctionCall(callData)
|
||||||
if function == nil {
|
|
||||||
return nil, fmt.Errorf("Invalid function name '%s'", callData.BindingName)
|
|
||||||
}
|
|
||||||
result, err = function.call(callData.Data)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
|
|
||||||
// Do we have an error return type?
|
|
||||||
if function.hasErrorReturnType {
|
|
||||||
// We do - last result is an error type
|
|
||||||
// Check if the last result was nil
|
|
||||||
b.log.Debugf("# of return types: %d", len(function.returnTypes))
|
|
||||||
b.log.Debugf("# of results: %d", len(result))
|
|
||||||
errorResult := result[len(function.returnTypes)-1]
|
|
||||||
if !errorResult.IsNil() {
|
|
||||||
// It wasn't - we have an error
|
|
||||||
return nil, errorResult.Interface().(error)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return result[0].Interface(), nil
|
|
||||||
case 2:
|
case 2:
|
||||||
// do we have this method?
|
result, err = b.processMethodCall(callData)
|
||||||
method := b.methods[callData.BindingName]
|
|
||||||
if method == nil {
|
|
||||||
return nil, fmt.Errorf("Invalid method name '%s'", callData.BindingName)
|
|
||||||
}
|
|
||||||
result, err = method.call(callData.Data)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
|
|
||||||
// Do we have an error return type?
|
|
||||||
if method.hasErrorReturnType {
|
|
||||||
// We do - last result is an error type
|
|
||||||
// Check if the last result was nil
|
|
||||||
b.log.Debugf("# of return types: %d", len(method.returnTypes))
|
|
||||||
b.log.Debugf("# of results: %d", len(result))
|
|
||||||
errorResult := result[len(method.returnTypes)-1]
|
|
||||||
if !errorResult.IsNil() {
|
|
||||||
// It wasn't - we have an error
|
|
||||||
return nil, errorResult.Interface().(error)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if result != nil {
|
|
||||||
return result[0].Interface(), nil
|
|
||||||
}
|
|
||||||
return nil, nil
|
|
||||||
|
|
||||||
default:
|
default:
|
||||||
return nil, fmt.Errorf("Invalid binding name '%s'", callData.BindingName)
|
result = nil
|
||||||
|
err = fmt.Errorf("Invalid binding name '%s'", callData.BindingName)
|
||||||
}
|
}
|
||||||
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
// callWailsInitMethods calls all of the WailsInit methods that were
|
// callWailsInitMethods calls all of the WailsInit methods that were
|
||||||
|
|||||||
171
cmd/frontend.go
171
cmd/frontend.go
@@ -1,171 +0,0 @@
|
|||||||
package cmd
|
|
||||||
|
|
||||||
import (
|
|
||||||
"fmt"
|
|
||||||
|
|
||||||
"github.com/leaanthony/slicer"
|
|
||||||
"github.com/leaanthony/spinner"
|
|
||||||
)
|
|
||||||
|
|
||||||
// ValidateFrontendConfig checks if the frontend config is valid
|
|
||||||
func ValidateFrontendConfig(projectOptions *ProjectOptions) error {
|
|
||||||
if projectOptions.FrontEnd.Dir == "" {
|
|
||||||
return fmt.Errorf("Frontend directory not set in project.json")
|
|
||||||
}
|
|
||||||
if projectOptions.FrontEnd.Build == "" {
|
|
||||||
return fmt.Errorf("Frontend build command not set in project.json")
|
|
||||||
}
|
|
||||||
if projectOptions.FrontEnd.Install == "" {
|
|
||||||
return fmt.Errorf("Frontend install command not set in project.json")
|
|
||||||
}
|
|
||||||
if projectOptions.FrontEnd.Bridge == "" {
|
|
||||||
return fmt.Errorf("Frontend bridge config not set in project.json")
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func InstallGoDependencies() error {
|
|
||||||
depSpinner := spinner.New("Installing Dependencies...")
|
|
||||||
depSpinner.SetSpinSpeed(50)
|
|
||||||
depSpinner.Start()
|
|
||||||
err := NewProgramHelper().RunCommand("go get")
|
|
||||||
if err != nil {
|
|
||||||
depSpinner.Error()
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
depSpinner.Success()
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func BuildApplication(binaryName string, forceRebuild bool, buildMode string) error {
|
|
||||||
compileMessage := "Packing + Compiling project"
|
|
||||||
if buildMode == "debug" {
|
|
||||||
compileMessage += " (Debug Mode)"
|
|
||||||
}
|
|
||||||
|
|
||||||
packSpinner := spinner.New(compileMessage + "...")
|
|
||||||
packSpinner.SetSpinSpeed(50)
|
|
||||||
packSpinner.Start()
|
|
||||||
|
|
||||||
buildCommand := slicer.String()
|
|
||||||
buildCommand.AddSlice([]string{"packr", "build"})
|
|
||||||
|
|
||||||
if binaryName != "" {
|
|
||||||
buildCommand.Add("-o")
|
|
||||||
buildCommand.Add(binaryName)
|
|
||||||
}
|
|
||||||
|
|
||||||
// If we are forcing a rebuild
|
|
||||||
if forceRebuild {
|
|
||||||
buildCommand.Add("-a")
|
|
||||||
}
|
|
||||||
|
|
||||||
buildCommand.AddSlice([]string{"-ldflags", "-X github.com/wailsapp/wails.BuildMode=" + buildMode})
|
|
||||||
err := NewProgramHelper().RunCommandArray(buildCommand.AsSlice())
|
|
||||||
if err != nil {
|
|
||||||
packSpinner.Error()
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
packSpinner.Success()
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func PackageApplication(projectOptions *ProjectOptions) error {
|
|
||||||
// Package app
|
|
||||||
packageSpinner := spinner.New("Packaging Application")
|
|
||||||
packageSpinner.SetSpinSpeed(50)
|
|
||||||
packageSpinner.Start()
|
|
||||||
err := NewPackageHelper().Package(projectOptions)
|
|
||||||
if err != nil {
|
|
||||||
packageSpinner.Error()
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
packageSpinner.Success()
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func BuildFrontend(buildCommand string) error {
|
|
||||||
buildFESpinner := spinner.New("Building frontend...")
|
|
||||||
buildFESpinner.SetSpinSpeed(50)
|
|
||||||
buildFESpinner.Start()
|
|
||||||
err := NewProgramHelper().RunCommand(buildCommand)
|
|
||||||
if err != nil {
|
|
||||||
buildFESpinner.Error()
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
buildFESpinner.Success()
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// func CopyBridgeFile(projectDir string, projectOptions ProjectOptions, bridgeMode bool) error {
|
|
||||||
// // Copy bridge to project
|
|
||||||
// fs := NewFSHelper()
|
|
||||||
// var bridgeFile = "wailsbridge.prod.js"
|
|
||||||
// if bridgeMode {
|
|
||||||
// bridgeFile = "wailsbridge.js"
|
|
||||||
// }
|
|
||||||
// _, filename, _, _ := runtime.Caller(1)
|
|
||||||
// bridgeFileSource := filepath.Join(path.Dir(filename), "..", "assets", "default", bridgeFile)
|
|
||||||
// bridgeFileTarget := filepath.Join(projectDir, projectOptions.FrontEnd.Dir, projectOptions.FrontEnd.Bridge, bridgeFile)
|
|
||||||
// err := fs.CopyFile(bridgeFileSource, bridgeFileTarget)
|
|
||||||
// if err != nil {
|
|
||||||
// return err
|
|
||||||
// }
|
|
||||||
// return nil
|
|
||||||
// }
|
|
||||||
|
|
||||||
// func InstallFrontend(projectOptions *ProjectOptions) error {
|
|
||||||
// // Install frontend deps
|
|
||||||
// err := os.Chdir(projectOptions.FrontEnd.Dir)
|
|
||||||
// if err != nil {
|
|
||||||
// return err
|
|
||||||
// }
|
|
||||||
|
|
||||||
// // Check if frontend deps have been updated
|
|
||||||
// feSpinner := spinner.New("Installing frontend dependencies (This may take a while)...")
|
|
||||||
// feSpinner.SetSpinSpeed(50)
|
|
||||||
// feSpinner.Start()
|
|
||||||
|
|
||||||
// requiresNPMInstall := true
|
|
||||||
|
|
||||||
// // Read in package.json MD5
|
|
||||||
// fs := NewFSHelper()
|
|
||||||
// packageJSONMD5, err := fs.FileMD5("package.json")
|
|
||||||
// if err != nil {
|
|
||||||
// return err
|
|
||||||
// }
|
|
||||||
|
|
||||||
// const md5sumFile = "package.json.md5"
|
|
||||||
|
|
||||||
// // If we aren't forcing the install and the md5sum file exists
|
|
||||||
// if !forceRebuild && fs.FileExists(md5sumFile) {
|
|
||||||
// // Yes - read contents
|
|
||||||
// savedMD5sum, err := fs.LoadAsString(md5sumFile)
|
|
||||||
// // File exists
|
|
||||||
// if err == nil {
|
|
||||||
// // Compare md5
|
|
||||||
// if savedMD5sum == packageJSONMD5 {
|
|
||||||
// // Same - no need for reinstall
|
|
||||||
// requiresNPMInstall = false
|
|
||||||
// feSpinner.Success("Skipped frontend dependencies (-f to force rebuild)")
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
|
|
||||||
// // Md5 sum package.json
|
|
||||||
// // Different? Build
|
|
||||||
// if requiresNPMInstall || forceRebuild {
|
|
||||||
// // Install dependencies
|
|
||||||
// err = program.RunCommand(projectOptions.FrontEnd.Install)
|
|
||||||
// if err != nil {
|
|
||||||
// feSpinner.Error()
|
|
||||||
// return err
|
|
||||||
// }
|
|
||||||
// feSpinner.Success()
|
|
||||||
|
|
||||||
// // Update md5sum file
|
|
||||||
// ioutil.WriteFile(md5sumFile, []byte(packageJSONMD5), 0644)
|
|
||||||
// }
|
|
||||||
// return nil
|
|
||||||
// }
|
|
||||||
225
cmd/helpers.go
Normal file
225
cmd/helpers.go
Normal file
@@ -0,0 +1,225 @@
|
|||||||
|
package cmd
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"io/ioutil"
|
||||||
|
"os"
|
||||||
|
"os/exec"
|
||||||
|
"path"
|
||||||
|
"path/filepath"
|
||||||
|
"runtime"
|
||||||
|
"time"
|
||||||
|
|
||||||
|
"github.com/leaanthony/slicer"
|
||||||
|
"github.com/leaanthony/spinner"
|
||||||
|
)
|
||||||
|
|
||||||
|
// ValidateFrontendConfig checks if the frontend config is valid
|
||||||
|
func ValidateFrontendConfig(projectOptions *ProjectOptions) error {
|
||||||
|
if projectOptions.FrontEnd.Dir == "" {
|
||||||
|
return fmt.Errorf("Frontend directory not set in project.json")
|
||||||
|
}
|
||||||
|
if projectOptions.FrontEnd.Build == "" {
|
||||||
|
return fmt.Errorf("Frontend build command not set in project.json")
|
||||||
|
}
|
||||||
|
if projectOptions.FrontEnd.Install == "" {
|
||||||
|
return fmt.Errorf("Frontend install command not set in project.json")
|
||||||
|
}
|
||||||
|
if projectOptions.FrontEnd.Bridge == "" {
|
||||||
|
return fmt.Errorf("Frontend bridge config not set in project.json")
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// InstallGoDependencies will run go get in the current directory
|
||||||
|
func InstallGoDependencies() error {
|
||||||
|
depSpinner := spinner.New("Installing Dependencies...")
|
||||||
|
depSpinner.SetSpinSpeed(50)
|
||||||
|
depSpinner.Start()
|
||||||
|
err := NewProgramHelper().RunCommand("go get")
|
||||||
|
if err != nil {
|
||||||
|
depSpinner.Error()
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
depSpinner.Success()
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// BuildApplication will attempt to build the project based on the given inputs
|
||||||
|
func BuildApplication(binaryName string, forceRebuild bool, buildMode string) error {
|
||||||
|
compileMessage := "Packing + Compiling project"
|
||||||
|
if buildMode == "debug" {
|
||||||
|
compileMessage += " (Debug Mode)"
|
||||||
|
}
|
||||||
|
|
||||||
|
packSpinner := spinner.New(compileMessage + "...")
|
||||||
|
packSpinner.SetSpinSpeed(50)
|
||||||
|
packSpinner.Start()
|
||||||
|
|
||||||
|
buildCommand := slicer.String()
|
||||||
|
buildCommand.AddSlice([]string{"packr", "build"})
|
||||||
|
|
||||||
|
if binaryName != "" {
|
||||||
|
buildCommand.Add("-o")
|
||||||
|
buildCommand.Add(binaryName)
|
||||||
|
}
|
||||||
|
|
||||||
|
// If we are forcing a rebuild
|
||||||
|
if forceRebuild {
|
||||||
|
buildCommand.Add("-a")
|
||||||
|
}
|
||||||
|
|
||||||
|
buildCommand.AddSlice([]string{"-ldflags", "-X github.com/wailsapp/wails.BuildMode=" + buildMode})
|
||||||
|
err := NewProgramHelper().RunCommandArray(buildCommand.AsSlice())
|
||||||
|
if err != nil {
|
||||||
|
packSpinner.Error()
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
packSpinner.Success()
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// PackageApplication will attempt to package the application in a pltform dependent way
|
||||||
|
func PackageApplication(projectOptions *ProjectOptions) error {
|
||||||
|
// Package app
|
||||||
|
packageSpinner := spinner.New("Packaging Application")
|
||||||
|
packageSpinner.SetSpinSpeed(50)
|
||||||
|
packageSpinner.Start()
|
||||||
|
err := NewPackageHelper().Package(projectOptions)
|
||||||
|
if err != nil {
|
||||||
|
packageSpinner.Error()
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
packageSpinner.Success()
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// BuildFrontend runs the given build command
|
||||||
|
func BuildFrontend(buildCommand string) error {
|
||||||
|
buildFESpinner := spinner.New("Building frontend...")
|
||||||
|
buildFESpinner.SetSpinSpeed(50)
|
||||||
|
buildFESpinner.Start()
|
||||||
|
err := NewProgramHelper().RunCommand(buildCommand)
|
||||||
|
if err != nil {
|
||||||
|
buildFESpinner.Error()
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
buildFESpinner.Success()
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// CheckPackr checks if packr is installed and if not, attempts to fetch it
|
||||||
|
func CheckPackr() (err error) {
|
||||||
|
programHelper := NewProgramHelper()
|
||||||
|
if !programHelper.IsInstalled("packr") {
|
||||||
|
buildSpinner := spinner.New()
|
||||||
|
buildSpinner.SetSpinSpeed(50)
|
||||||
|
buildSpinner.Start("Installing packr...")
|
||||||
|
err := programHelper.InstallGoPackage("github.com/gobuffalo/packr/...")
|
||||||
|
if err != nil {
|
||||||
|
buildSpinner.Error()
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
buildSpinner.Success()
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// InstallFrontendDeps attempts to install the frontend dependencies based on the given options
|
||||||
|
func InstallFrontendDeps(projectDir string, projectOptions *ProjectOptions, forceRebuild bool) error {
|
||||||
|
|
||||||
|
// Install frontend deps
|
||||||
|
err := os.Chdir(projectOptions.FrontEnd.Dir)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check if frontend deps have been updated
|
||||||
|
feSpinner := spinner.New("Installing frontend dependencies (This may take a while)...")
|
||||||
|
feSpinner.SetSpinSpeed(50)
|
||||||
|
feSpinner.Start()
|
||||||
|
|
||||||
|
requiresNPMInstall := true
|
||||||
|
|
||||||
|
// Read in package.json MD5
|
||||||
|
fs := NewFSHelper()
|
||||||
|
packageJSONMD5, err := fs.FileMD5("package.json")
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
const md5sumFile = "package.json.md5"
|
||||||
|
|
||||||
|
// If we aren't forcing the install and the md5sum file exists
|
||||||
|
if !forceRebuild && fs.FileExists(md5sumFile) {
|
||||||
|
// Yes - read contents
|
||||||
|
savedMD5sum, err := fs.LoadAsString(md5sumFile)
|
||||||
|
// File exists
|
||||||
|
if err == nil {
|
||||||
|
// Compare md5
|
||||||
|
if savedMD5sum == packageJSONMD5 {
|
||||||
|
// Same - no need for reinstall
|
||||||
|
requiresNPMInstall = false
|
||||||
|
feSpinner.Success("Skipped frontend dependencies (-f to force rebuild)")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Md5 sum package.json
|
||||||
|
// Different? Build
|
||||||
|
if requiresNPMInstall || forceRebuild {
|
||||||
|
// Install dependencies
|
||||||
|
err = NewProgramHelper().RunCommand(projectOptions.FrontEnd.Install)
|
||||||
|
if err != nil {
|
||||||
|
feSpinner.Error()
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
feSpinner.Success()
|
||||||
|
|
||||||
|
// Update md5sum file
|
||||||
|
ioutil.WriteFile(md5sumFile, []byte(packageJSONMD5), 0644)
|
||||||
|
}
|
||||||
|
|
||||||
|
bridgeFile := "wailsbridge.prod.js"
|
||||||
|
|
||||||
|
// Copy bridge to project
|
||||||
|
_, filename, _, _ := runtime.Caller(1)
|
||||||
|
bridgeFileSource := filepath.Join(path.Dir(filename), "..", "..", "assets", "default", bridgeFile)
|
||||||
|
bridgeFileTarget := filepath.Join(projectDir, projectOptions.FrontEnd.Dir, projectOptions.FrontEnd.Bridge, "wailsbridge.js")
|
||||||
|
err = fs.CopyFile(bridgeFileSource, bridgeFileTarget)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
// Build frontend
|
||||||
|
err = BuildFrontend(projectOptions.FrontEnd.Build)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// ServeProject attempts to serve up the current project so that it may be connected to
|
||||||
|
// via the Wails bridge
|
||||||
|
func ServeProject(projectOptions *ProjectOptions, logger *Logger) error {
|
||||||
|
go func() {
|
||||||
|
time.Sleep(2 * time.Second)
|
||||||
|
logger.Green(">>>>> To connect, you will need to run '" + projectOptions.FrontEnd.Serve + "' in the '" + projectOptions.FrontEnd.Dir + "' directory <<<<<")
|
||||||
|
}()
|
||||||
|
location, err := filepath.Abs(projectOptions.BinaryName)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
logger.Yellow("Serving Application: " + location)
|
||||||
|
cmd := exec.Command(location)
|
||||||
|
cmd.Stdout = os.Stdout
|
||||||
|
cmd.Stderr = os.Stderr
|
||||||
|
err = cmd.Run()
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
@@ -17,6 +17,7 @@ func NewLogger() *Logger {
|
|||||||
return &Logger{errorOnly: false}
|
return &Logger{errorOnly: false}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SetErrorOnly onyl outputs messages if they are an error
|
||||||
func (l *Logger) SetErrorOnly(errorOnly bool) {
|
func (l *Logger) SetErrorOnly(errorOnly bool) {
|
||||||
l.errorOnly = errorOnly
|
l.errorOnly = errorOnly
|
||||||
}
|
}
|
||||||
|
|||||||
148
cmd/project.go
148
cmd/project.go
@@ -178,40 +178,14 @@ func (po *ProjectOptions) Defaults() {
|
|||||||
func (po *ProjectOptions) PromptForInputs() error {
|
func (po *ProjectOptions) PromptForInputs() error {
|
||||||
|
|
||||||
var questions []*survey.Question
|
var questions []*survey.Question
|
||||||
fs := NewFSHelper()
|
|
||||||
|
|
||||||
if po.Name == "" {
|
processProjectName(po.Name, &questions)
|
||||||
questions = append(questions, InputQuestion("Name", "The name of the project", "My Project", true))
|
|
||||||
} else {
|
|
||||||
fmt.Println("Project Name: " + po.Name)
|
|
||||||
}
|
|
||||||
|
|
||||||
if po.BinaryName == "" {
|
processBinaryName(po.BinaryName, po.Name, &questions)
|
||||||
var binaryNameComputed string
|
|
||||||
if po.Name != "" {
|
|
||||||
binaryNameComputed = strings.ToLower(po.Name)
|
|
||||||
binaryNameComputed = strings.Replace(binaryNameComputed, " ", "-", -1)
|
|
||||||
binaryNameComputed = strings.Replace(binaryNameComputed, string(filepath.Separator), "-", -1)
|
|
||||||
binaryNameComputed = strings.Replace(binaryNameComputed, ":", "-", -1)
|
|
||||||
}
|
|
||||||
questions = append(questions, InputQuestion("BinaryName", "The output binary name", binaryNameComputed, true))
|
|
||||||
} else {
|
|
||||||
fmt.Println("Output binary Name: " + po.BinaryName)
|
|
||||||
}
|
|
||||||
|
|
||||||
if po.OutputDirectory != "" {
|
err := processOutputDirectory(po.OutputDirectory, &questions)
|
||||||
projectPath, err := filepath.Abs(po.OutputDirectory)
|
if err != nil {
|
||||||
if err != nil {
|
return err
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
if fs.DirExists(projectPath) {
|
|
||||||
return fmt.Errorf("directory '%s' already exists", projectPath)
|
|
||||||
}
|
|
||||||
|
|
||||||
fmt.Println("Project Directory: " + po.OutputDirectory)
|
|
||||||
} else {
|
|
||||||
questions = append(questions, InputQuestion("OutputDirectory", "Project directory name", "", true))
|
|
||||||
}
|
}
|
||||||
|
|
||||||
templateDetails, err := po.templates.GetTemplateDetails()
|
templateDetails, err := po.templates.GetTemplateDetails()
|
||||||
@@ -259,35 +233,10 @@ func (po *ProjectOptions) PromptForInputs() error {
|
|||||||
|
|
||||||
// Populate template details
|
// Populate template details
|
||||||
templateMetadata := templateDetails[po.Template].Metadata
|
templateMetadata := templateDetails[po.Template].Metadata
|
||||||
if templateMetadata["frontenddir"] != nil {
|
|
||||||
po.FrontEnd = &frontend{}
|
|
||||||
po.FrontEnd.Dir = templateMetadata["frontenddir"].(string)
|
|
||||||
}
|
|
||||||
if templateMetadata["install"] != nil {
|
|
||||||
if po.FrontEnd == nil {
|
|
||||||
return fmt.Errorf("install set in template metadata but not frontenddir")
|
|
||||||
}
|
|
||||||
po.FrontEnd.Install = templateMetadata["install"].(string)
|
|
||||||
}
|
|
||||||
if templateMetadata["build"] != nil {
|
|
||||||
if po.FrontEnd == nil {
|
|
||||||
return fmt.Errorf("build set in template metadata but not frontenddir")
|
|
||||||
}
|
|
||||||
po.FrontEnd.Build = templateMetadata["build"].(string)
|
|
||||||
}
|
|
||||||
|
|
||||||
if templateMetadata["bridge"] != nil {
|
err = processTemplateMetadata(templateMetadata, po)
|
||||||
if po.FrontEnd == nil {
|
if err != nil {
|
||||||
return fmt.Errorf("bridge set in template metadata but not frontenddir")
|
return err
|
||||||
}
|
|
||||||
po.FrontEnd.Bridge = templateMetadata["bridge"].(string)
|
|
||||||
}
|
|
||||||
|
|
||||||
if templateMetadata["serve"] != nil {
|
|
||||||
if po.FrontEnd == nil {
|
|
||||||
return fmt.Errorf("serve set in template metadata but not frontenddir")
|
|
||||||
}
|
|
||||||
po.FrontEnd.Serve = templateMetadata["serve"].(string)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
@@ -320,3 +269,84 @@ func (po *ProjectOptions) LoadConfig(projectDir string) error {
|
|||||||
}
|
}
|
||||||
return json.Unmarshal(rawBytes, po)
|
return json.Unmarshal(rawBytes, po)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func computeBinaryName(projectName string) string {
|
||||||
|
if projectName == "" {
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
var binaryNameComputed = strings.ToLower(projectName)
|
||||||
|
binaryNameComputed = strings.Replace(binaryNameComputed, " ", "-", -1)
|
||||||
|
binaryNameComputed = strings.Replace(binaryNameComputed, string(filepath.Separator), "-", -1)
|
||||||
|
binaryNameComputed = strings.Replace(binaryNameComputed, ":", "-", -1)
|
||||||
|
return binaryNameComputed
|
||||||
|
}
|
||||||
|
|
||||||
|
func processOutputDirectory(outputDirectory string, questions *[]*survey.Question) error {
|
||||||
|
|
||||||
|
if outputDirectory != "" {
|
||||||
|
projectPath, err := filepath.Abs(outputDirectory)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
if NewFSHelper().DirExists(projectPath) {
|
||||||
|
return fmt.Errorf("directory '%s' already exists", projectPath)
|
||||||
|
}
|
||||||
|
|
||||||
|
fmt.Println("Project Directory: " + outputDirectory)
|
||||||
|
} else {
|
||||||
|
*questions = append(*questions, InputQuestion("OutputDirectory", "Project directory name", "", true))
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func processProjectName(name string, questions *[]*survey.Question) {
|
||||||
|
if name == "" {
|
||||||
|
*questions = append(*questions, InputQuestion("Name", "The name of the project", "My Project", true))
|
||||||
|
} else {
|
||||||
|
fmt.Println("Project Name: " + name)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func processBinaryName(binaryName string, name string, questions *[]*survey.Question) {
|
||||||
|
if binaryName == "" {
|
||||||
|
var binaryNameComputed = computeBinaryName(name)
|
||||||
|
*questions = append(*questions, InputQuestion("BinaryName", "The output binary name", binaryNameComputed, true))
|
||||||
|
} else {
|
||||||
|
fmt.Println("Output binary Name: " + binaryName)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func processTemplateMetadata(templateMetadata map[string]interface{}, po *ProjectOptions) error {
|
||||||
|
if templateMetadata["frontenddir"] != nil {
|
||||||
|
po.FrontEnd = &frontend{}
|
||||||
|
po.FrontEnd.Dir = templateMetadata["frontenddir"].(string)
|
||||||
|
}
|
||||||
|
if templateMetadata["install"] != nil {
|
||||||
|
if po.FrontEnd == nil {
|
||||||
|
return fmt.Errorf("install set in template metadata but not frontenddir")
|
||||||
|
}
|
||||||
|
po.FrontEnd.Install = templateMetadata["install"].(string)
|
||||||
|
}
|
||||||
|
if templateMetadata["build"] != nil {
|
||||||
|
if po.FrontEnd == nil {
|
||||||
|
return fmt.Errorf("build set in template metadata but not frontenddir")
|
||||||
|
}
|
||||||
|
po.FrontEnd.Build = templateMetadata["build"].(string)
|
||||||
|
}
|
||||||
|
|
||||||
|
if templateMetadata["bridge"] != nil {
|
||||||
|
if po.FrontEnd == nil {
|
||||||
|
return fmt.Errorf("bridge set in template metadata but not frontenddir")
|
||||||
|
}
|
||||||
|
po.FrontEnd.Bridge = templateMetadata["bridge"].(string)
|
||||||
|
}
|
||||||
|
|
||||||
|
if templateMetadata["serve"] != nil {
|
||||||
|
if po.FrontEnd == nil {
|
||||||
|
return fmt.Errorf("serve set in template metadata but not frontenddir")
|
||||||
|
}
|
||||||
|
po.FrontEnd.Serve = templateMetadata["serve"].(string)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|||||||
@@ -12,8 +12,8 @@ html {
|
|||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
/* https://leaverou.github.io/css3patterns/#carbon */
|
/* https://leaverou.github.io/css3patterns/#carbon */
|
||||||
background: linear-gradient(27deg, #151515 5px, transparent 5px) 0 5px,
|
background: linear-gradient(27deg, #151515 5px, transparent 5px) 0 5px,
|
||||||
linear-gradient(207deg, #151515 5px, transparent 5px) 10px 0px,
|
linear-gradient(207deg, #151515 5px, transparent 5px) 10px 0,
|
||||||
linear-gradient(27deg, #222 5px, transparent 5px) 0px 10px,
|
linear-gradient(27deg, #222 5px, transparent 5px) 0 10px,
|
||||||
linear-gradient(207deg, #222 5px, transparent 5px) 10px 5px,
|
linear-gradient(207deg, #222 5px, transparent 5px) 10px 5px,
|
||||||
linear-gradient(90deg, #1b1b1b 10px, transparent 10px),
|
linear-gradient(90deg, #1b1b1b 10px, transparent 10px),
|
||||||
linear-gradient(
|
linear-gradient(
|
||||||
@@ -46,10 +46,8 @@ html {
|
|||||||
format("woff2"),
|
format("woff2"),
|
||||||
/* Super Modern Browsers */
|
/* Super Modern Browsers */
|
||||||
url("../fonts/roboto/roboto-v18-latin-regular.woff") format("woff"),
|
url("../fonts/roboto/roboto-v18-latin-regular.woff") format("woff"),
|
||||||
/* Modern Browsers */
|
/* Modern Browsers */ url("../fonts/roboto/roboto-v18-latin-regular.ttf")
|
||||||
url("../fonts/roboto/roboto-v18-latin-regular.ttf")
|
|
||||||
format("truetype"),
|
format("truetype"),
|
||||||
/* Safari, Android, iOS */
|
/* Safari, Android, iOS */
|
||||||
url("../fonts/roboto/roboto-v18-latin-regular.svg#Roboto")
|
url("../fonts/roboto/roboto-v18-latin-regular.svg#Roboto") format("svg"); /* Legacy iOS */
|
||||||
format("svg"); /* Legacy iOS */
|
}
|
||||||
}
|
|
||||||
|
|||||||
@@ -18,8 +18,12 @@ body {
|
|||||||
border-color: #117;
|
border-color: #117;
|
||||||
}
|
}
|
||||||
|
|
||||||
p { margin-bottom: 1.5em; }
|
p {
|
||||||
p:last-child { margin-bottom: 0; }
|
margin-bottom: 1.5em;
|
||||||
|
}
|
||||||
|
p:last-child {
|
||||||
|
margin-bottom: 0;
|
||||||
|
}
|
||||||
|
|
||||||
blockquote {
|
blockquote {
|
||||||
display: block;
|
display: block;
|
||||||
@@ -32,9 +36,9 @@ blockquote {
|
|||||||
color: #117;
|
color: #117;
|
||||||
}
|
}
|
||||||
blockquote:before {
|
blockquote:before {
|
||||||
content: '\201C';
|
content: "\201C";
|
||||||
position: absolute;
|
position: absolute;
|
||||||
top: 0em;
|
top: 0;
|
||||||
left: 50%;
|
left: 50%;
|
||||||
transform: translate(-50%, -50%);
|
transform: translate(-50%, -50%);
|
||||||
background: #fff;
|
background: #fff;
|
||||||
@@ -54,22 +58,22 @@ blockquote:after {
|
|||||||
|
|
||||||
/* https://fdossena.com/?p=html5cool/buttons/i.frag */
|
/* https://fdossena.com/?p=html5cool/buttons/i.frag */
|
||||||
button {
|
button {
|
||||||
display:inline-block;
|
display: inline-block;
|
||||||
padding:0.35em 1.2em;
|
padding: 0.35em 1.2em;
|
||||||
border:0.1em solid #000;
|
border: 0.1em solid #000;
|
||||||
margin:0 0.3em 0.3em 0;
|
margin: 0 0.3em 0.3em 0;
|
||||||
border-radius:0.12em;
|
border-radius: 0.12em;
|
||||||
box-sizing: border-box;
|
box-sizing: border-box;
|
||||||
text-decoration:none;
|
text-decoration: none;
|
||||||
font-family:'Roboto',sans-serif;
|
font-family: "Roboto", sans-serif;
|
||||||
font-weight:300;
|
font-weight: 300;
|
||||||
font-size: 1em;
|
font-size: 1em;
|
||||||
color:#000;
|
color: #000;
|
||||||
text-align:center;
|
text-align: center;
|
||||||
transition: all 0.2s;
|
transition: all 0.2s;
|
||||||
}
|
}
|
||||||
button:hover{
|
button:hover {
|
||||||
color:#FFF;
|
color: #fff;
|
||||||
background-color:#000;
|
background-color: #000;
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,7 +5,6 @@ import (
|
|||||||
"runtime"
|
"runtime"
|
||||||
|
|
||||||
"github.com/leaanthony/spinner"
|
"github.com/leaanthony/spinner"
|
||||||
|
|
||||||
"github.com/wailsapp/wails/cmd"
|
"github.com/wailsapp/wails/cmd"
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -31,64 +30,29 @@ Create your first project by running 'wails init'.`
|
|||||||
if runtime.GOOS != "windows" {
|
if runtime.GOOS != "windows" {
|
||||||
successMessage = "🚀 " + successMessage
|
successMessage = "🚀 " + successMessage
|
||||||
}
|
}
|
||||||
switch runtime.GOOS {
|
// Platform check
|
||||||
case "darwin":
|
err = platformCheck()
|
||||||
logger.Yellow("Detected Platform: OSX")
|
|
||||||
case "windows":
|
|
||||||
logger.Yellow("Detected Platform: Windows")
|
|
||||||
case "linux":
|
|
||||||
logger.Yellow("Detected Platform: Linux")
|
|
||||||
default:
|
|
||||||
return fmt.Errorf("Platform %s is currently not supported", runtime.GOOS)
|
|
||||||
}
|
|
||||||
|
|
||||||
logger.Yellow("Checking for prerequisites...")
|
|
||||||
// Check we have a cgo capable environment
|
|
||||||
|
|
||||||
requiredPrograms, err := cmd.GetRequiredPrograms()
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
errors := false
|
|
||||||
programHelper := cmd.NewProgramHelper()
|
// Check we have a cgo capable environment
|
||||||
for _, program := range *requiredPrograms {
|
logger.Yellow("Checking for prerequisites...")
|
||||||
bin := programHelper.FindProgram(program.Name)
|
errors, err := checkRequiredPrograms()
|
||||||
if bin == nil {
|
if err != nil {
|
||||||
errors = true
|
return err
|
||||||
logger.Red("Program '%s' not found. %s", program.Name, program.Help)
|
|
||||||
} else {
|
|
||||||
logger.Green("Program '%s' found: %s", program.Name, bin.Path)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Linux has library deps
|
// Linux has library deps
|
||||||
if runtime.GOOS == "linux" {
|
errors, err = checkLibraries()
|
||||||
// Check library prerequisites
|
if err != nil {
|
||||||
requiredLibraries, err := cmd.GetRequiredLibraries()
|
return err
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
distroInfo := cmd.GetLinuxDistroInfo()
|
|
||||||
for _, library := range *requiredLibraries {
|
|
||||||
switch distroInfo.Distribution {
|
|
||||||
case cmd.Ubuntu:
|
|
||||||
installed, err := cmd.DpkgInstalled(library.Name)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
if !installed {
|
|
||||||
errors = true
|
|
||||||
logger.Red("Library '%s' not found. %s", library.Name, library.Help)
|
|
||||||
} else {
|
|
||||||
logger.Green("Library '%s' installed.", library.Name)
|
|
||||||
}
|
|
||||||
default:
|
|
||||||
return fmt.Errorf("unable to check libraries on distribution '%s'. Please ensure that the '%s' equivalent is installed", distroInfo.DistributorID, library.Name)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// packr
|
// packr
|
||||||
|
err = cmd.CheckPackr()
|
||||||
|
|
||||||
|
programHelper := cmd.NewProgramHelper()
|
||||||
if !programHelper.IsInstalled("packr") {
|
if !programHelper.IsInstalled("packr") {
|
||||||
buildSpinner := spinner.New()
|
buildSpinner := spinner.New()
|
||||||
buildSpinner.SetSpinSpeed(50)
|
buildSpinner.SetSpinSpeed(50)
|
||||||
@@ -110,3 +74,65 @@ Create your first project by running 'wails init'.`
|
|||||||
return err
|
return err
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func platformCheck() error {
|
||||||
|
switch runtime.GOOS {
|
||||||
|
case "darwin":
|
||||||
|
logger.Yellow("Detected Platform: OSX")
|
||||||
|
case "windows":
|
||||||
|
logger.Yellow("Detected Platform: Windows")
|
||||||
|
case "linux":
|
||||||
|
logger.Yellow("Detected Platform: Linux")
|
||||||
|
default:
|
||||||
|
return fmt.Errorf("Platform %s is currently not supported", runtime.GOOS)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func checkLibraries() (errors bool, err error) {
|
||||||
|
if runtime.GOOS == "linux" {
|
||||||
|
// Check library prerequisites
|
||||||
|
requiredLibraries, err := cmd.GetRequiredLibraries()
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
distroInfo := cmd.GetLinuxDistroInfo()
|
||||||
|
for _, library := range *requiredLibraries {
|
||||||
|
switch distroInfo.Distribution {
|
||||||
|
case cmd.Ubuntu:
|
||||||
|
installed, err := cmd.DpkgInstalled(library.Name)
|
||||||
|
if err != nil {
|
||||||
|
return false, err
|
||||||
|
}
|
||||||
|
if !installed {
|
||||||
|
errors = true
|
||||||
|
logger.Red("Library '%s' not found. %s", library.Name, library.Help)
|
||||||
|
} else {
|
||||||
|
logger.Green("Library '%s' installed.", library.Name)
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
return false, fmt.Errorf("unable to check libraries on distribution '%s'. Please ensure that the '%s' equivalent is installed", distroInfo.DistributorID, library.Name)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func checkRequiredPrograms() (errors bool, err error) {
|
||||||
|
requiredPrograms, err := cmd.GetRequiredPrograms()
|
||||||
|
if err != nil {
|
||||||
|
return true, err
|
||||||
|
}
|
||||||
|
errors = false
|
||||||
|
programHelper := cmd.NewProgramHelper()
|
||||||
|
for _, program := range *requiredPrograms {
|
||||||
|
bin := programHelper.FindProgram(program.Name)
|
||||||
|
if bin == nil {
|
||||||
|
errors = true
|
||||||
|
logger.Red("Program '%s' not found. %s", program.Name, program.Help)
|
||||||
|
} else {
|
||||||
|
logger.Green("Program '%s' found: %s", program.Name, bin.Path)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|||||||
@@ -2,11 +2,7 @@ package main
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"io/ioutil"
|
|
||||||
"os"
|
"os"
|
||||||
"path"
|
|
||||||
"path/filepath"
|
|
||||||
"runtime"
|
|
||||||
|
|
||||||
"github.com/leaanthony/spinner"
|
"github.com/leaanthony/spinner"
|
||||||
"github.com/wailsapp/wails/cmd"
|
"github.com/wailsapp/wails/cmd"
|
||||||
@@ -53,8 +49,6 @@ func init() {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check pre-requisites are installed
|
|
||||||
|
|
||||||
// Program checker
|
// Program checker
|
||||||
program := cmd.NewProgramHelper()
|
program := cmd.NewProgramHelper()
|
||||||
|
|
||||||
@@ -65,15 +59,10 @@ func init() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// packr
|
// Check Packr is installed
|
||||||
if !program.IsInstalled("packr") {
|
err = cmd.CheckPackr()
|
||||||
buildSpinner.Start("Installing packr...")
|
if err != nil {
|
||||||
err := program.InstallGoPackage("github.com/gobuffalo/packr/...")
|
return err
|
||||||
if err != nil {
|
|
||||||
buildSpinner.Error()
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
buildSpinner.Success()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Save project directory
|
// Save project directory
|
||||||
@@ -81,71 +70,7 @@ func init() {
|
|||||||
|
|
||||||
// Install deps
|
// Install deps
|
||||||
if projectOptions.FrontEnd != nil {
|
if projectOptions.FrontEnd != nil {
|
||||||
|
err = cmd.InstallFrontendDeps(projectDir, projectOptions, forceRebuild)
|
||||||
// Install frontend deps
|
|
||||||
err = os.Chdir(projectOptions.FrontEnd.Dir)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check if frontend deps have been updated
|
|
||||||
feSpinner := spinner.New("Installing frontend dependencies (This may take a while)...")
|
|
||||||
feSpinner.SetSpinSpeed(50)
|
|
||||||
feSpinner.Start()
|
|
||||||
|
|
||||||
requiresNPMInstall := true
|
|
||||||
|
|
||||||
// Read in package.json MD5
|
|
||||||
packageJSONMD5, err := fs.FileMD5("package.json")
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
const md5sumFile = "package.json.md5"
|
|
||||||
|
|
||||||
// If we aren't forcing the install and the md5sum file exists
|
|
||||||
if !forceRebuild && fs.FileExists(md5sumFile) {
|
|
||||||
// Yes - read contents
|
|
||||||
savedMD5sum, err := fs.LoadAsString(md5sumFile)
|
|
||||||
// File exists
|
|
||||||
if err == nil {
|
|
||||||
// Compare md5
|
|
||||||
if savedMD5sum == packageJSONMD5 {
|
|
||||||
// Same - no need for reinstall
|
|
||||||
requiresNPMInstall = false
|
|
||||||
feSpinner.Success("Skipped frontend dependencies (-f to force rebuild)")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Md5 sum package.json
|
|
||||||
// Different? Build
|
|
||||||
if requiresNPMInstall || forceRebuild {
|
|
||||||
// Install dependencies
|
|
||||||
err = program.RunCommand(projectOptions.FrontEnd.Install)
|
|
||||||
if err != nil {
|
|
||||||
feSpinner.Error()
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
feSpinner.Success()
|
|
||||||
|
|
||||||
// Update md5sum file
|
|
||||||
ioutil.WriteFile(md5sumFile, []byte(packageJSONMD5), 0644)
|
|
||||||
}
|
|
||||||
|
|
||||||
bridgeFile := "wailsbridge.prod.js"
|
|
||||||
|
|
||||||
// Copy bridge to project
|
|
||||||
_, filename, _, _ := runtime.Caller(1)
|
|
||||||
bridgeFileSource := filepath.Join(path.Dir(filename), "..", "assets", "default", bridgeFile)
|
|
||||||
bridgeFileTarget := filepath.Join(projectDir, projectOptions.FrontEnd.Dir, projectOptions.FrontEnd.Bridge, "wailsbridge.js")
|
|
||||||
err = fs.CopyFile(bridgeFileSource, bridgeFileTarget)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
// Build frontend
|
|
||||||
err = cmd.BuildFrontend(projectOptions.FrontEnd.Build)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,13 +2,7 @@ package main
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"io/ioutil"
|
|
||||||
"os"
|
"os"
|
||||||
"os/exec"
|
|
||||||
"path"
|
|
||||||
"path/filepath"
|
|
||||||
"runtime"
|
|
||||||
"time"
|
|
||||||
|
|
||||||
"github.com/leaanthony/spinner"
|
"github.com/leaanthony/spinner"
|
||||||
"github.com/wailsapp/wails/cmd"
|
"github.com/wailsapp/wails/cmd"
|
||||||
@@ -51,8 +45,6 @@ func init() {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check pre-requisites are installed
|
|
||||||
|
|
||||||
// Program checker
|
// Program checker
|
||||||
program := cmd.NewProgramHelper()
|
program := cmd.NewProgramHelper()
|
||||||
|
|
||||||
@@ -63,15 +55,10 @@ func init() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// packr
|
// Check Packr is installed
|
||||||
if !program.IsInstalled("packr") {
|
err = cmd.CheckPackr()
|
||||||
buildSpinner.Start("Installing packr...")
|
if err != nil {
|
||||||
err := program.InstallGoPackage("github.com/gobuffalo/packr/...")
|
return err
|
||||||
if err != nil {
|
|
||||||
buildSpinner.Error()
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
buildSpinner.Success()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Save project directory
|
// Save project directory
|
||||||
@@ -79,70 +66,7 @@ func init() {
|
|||||||
|
|
||||||
// Install deps
|
// Install deps
|
||||||
if projectOptions.FrontEnd != nil {
|
if projectOptions.FrontEnd != nil {
|
||||||
// Install frontend deps
|
err = cmd.InstallFrontendDeps(projectDir, projectOptions, forceRebuild)
|
||||||
err = os.Chdir(projectOptions.FrontEnd.Dir)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check if frontend deps have been updated
|
|
||||||
feSpinner := spinner.New("Installing frontend dependencies (This may take a while)...")
|
|
||||||
feSpinner.SetSpinSpeed(50)
|
|
||||||
feSpinner.Start()
|
|
||||||
|
|
||||||
requiresNPMInstall := true
|
|
||||||
|
|
||||||
// Read in package.json MD5
|
|
||||||
packageJSONMD5, err := fs.FileMD5("package.json")
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
const md5sumFile = "package.json.md5"
|
|
||||||
|
|
||||||
// If we aren't forcing the install and the md5sum file exists
|
|
||||||
if !forceRebuild && fs.FileExists(md5sumFile) {
|
|
||||||
// Yes - read contents
|
|
||||||
savedMD5sum, err := fs.LoadAsString(md5sumFile)
|
|
||||||
// File exists
|
|
||||||
if err == nil {
|
|
||||||
// Compare md5
|
|
||||||
if savedMD5sum == packageJSONMD5 {
|
|
||||||
// Same - no need for reinstall
|
|
||||||
requiresNPMInstall = false
|
|
||||||
feSpinner.Success("Skipped frontend dependencies (-f to force rebuild)")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Md5 sum package.json
|
|
||||||
// Different? Build
|
|
||||||
if requiresNPMInstall || forceRebuild {
|
|
||||||
// Install dependencies
|
|
||||||
err = program.RunCommand(projectOptions.FrontEnd.Install)
|
|
||||||
if err != nil {
|
|
||||||
feSpinner.Error()
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
feSpinner.Success()
|
|
||||||
|
|
||||||
// Update md5sum file
|
|
||||||
ioutil.WriteFile(md5sumFile, []byte(packageJSONMD5), 0644)
|
|
||||||
}
|
|
||||||
|
|
||||||
bridgeFile := "wailsbridge.prod.js"
|
|
||||||
|
|
||||||
// Copy bridge to project
|
|
||||||
_, filename, _, _ := runtime.Caller(1)
|
|
||||||
bridgeFileSource := filepath.Join(path.Dir(filename), "..", "assets", "default", bridgeFile)
|
|
||||||
bridgeFileTarget := filepath.Join(projectDir, projectOptions.FrontEnd.Dir, projectOptions.FrontEnd.Bridge, "wailsbridge.js")
|
|
||||||
err = fs.CopyFile(bridgeFileSource, bridgeFileTarget)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
// Build frontend
|
|
||||||
err = cmd.BuildFrontend(projectOptions.FrontEnd.Build)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@@ -167,25 +91,6 @@ func init() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
logger.Yellow("Awesome! Project '%s' built!", projectOptions.Name)
|
logger.Yellow("Awesome! Project '%s' built!", projectOptions.Name)
|
||||||
|
return cmd.ServeProject(projectOptions, logger)
|
||||||
go func() {
|
|
||||||
time.Sleep(2 * time.Second)
|
|
||||||
logger.Green(">>>>> To connect, you will need to run '" + projectOptions.FrontEnd.Serve + "' in the '" + projectOptions.FrontEnd.Dir + "' directory <<<<<")
|
|
||||||
}()
|
|
||||||
location, err := filepath.Abs(projectOptions.BinaryName)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
logger.Yellow("Serving Application: " + location)
|
|
||||||
cmd := exec.Command(location)
|
|
||||||
cmd.Stdout = os.Stdout
|
|
||||||
cmd.Stderr = os.Stderr
|
|
||||||
err = cmd.Run()
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user