117 lines
3.1 KiB
Go
117 lines
3.1 KiB
Go
package main
|
|
|
|
import (
|
|
"Moonshark/modules"
|
|
"fmt"
|
|
"os"
|
|
"os/signal"
|
|
"path/filepath"
|
|
"syscall"
|
|
|
|
luajit "git.sharkk.net/Sky/LuaJIT-to-Go"
|
|
)
|
|
|
|
func main() {
|
|
if len(os.Args) < 2 {
|
|
fmt.Fprintf(os.Stderr, "Usage: %s <script.lua>\n", filepath.Base(os.Args[0]))
|
|
os.Exit(1)
|
|
}
|
|
|
|
scriptPath := os.Args[1]
|
|
|
|
// Check if file exists
|
|
if _, err := os.Stat(scriptPath); os.IsNotExist(err) {
|
|
fmt.Fprintf(os.Stderr, "Error: script file '%s' not found\n", scriptPath)
|
|
os.Exit(1)
|
|
}
|
|
|
|
// Create new Lua state with standard libraries
|
|
state := luajit.New()
|
|
if state == nil {
|
|
fmt.Fprintf(os.Stderr, "Error: failed to create Lua state\n")
|
|
os.Exit(1)
|
|
}
|
|
defer state.Close()
|
|
|
|
// Set up module system
|
|
registry := modules.NewModuleRegistry()
|
|
if err := registry.LoadEmbeddedModules(); err != nil {
|
|
fmt.Fprintf(os.Stderr, "Warning: failed to load built-in modules: %v\n", err)
|
|
}
|
|
|
|
// Backup original require and install module system
|
|
modules.BackupOriginalRequire(state)
|
|
if err := registry.InstallModules(state); err != nil {
|
|
fmt.Fprintf(os.Stderr, "Error: failed to install module system: %v\n", err)
|
|
os.Exit(1)
|
|
}
|
|
|
|
// Get the absolute path to the script directory
|
|
scriptDir := filepath.Dir(scriptPath)
|
|
absScriptDir, err := filepath.Abs(scriptDir)
|
|
if err != nil {
|
|
fmt.Fprintf(os.Stderr, "Error: failed to get absolute path: %v\n", err)
|
|
os.Exit(1)
|
|
}
|
|
|
|
// Add script directory to Lua's package.path
|
|
packagePath := filepath.Join(absScriptDir, "?.lua")
|
|
if err := state.AddPackagePath(packagePath); err != nil {
|
|
fmt.Fprintf(os.Stderr, "Warning: failed to add script directory to package.path: %v\n", err)
|
|
}
|
|
|
|
// Read script file
|
|
scriptContent, err := os.ReadFile(scriptPath)
|
|
if err != nil {
|
|
fmt.Fprintf(os.Stderr, "Error reading script file '%s': %v\n", scriptPath, err)
|
|
os.Exit(1)
|
|
}
|
|
|
|
// Compile script to bytecode
|
|
bytecode, err := state.CompileBytecode(string(scriptContent), scriptPath)
|
|
if err != nil {
|
|
fmt.Fprintf(os.Stderr, "Error compiling '%s': %v\n", scriptPath, err)
|
|
os.Exit(1)
|
|
}
|
|
|
|
// Execute the compiled bytecode
|
|
if err := state.LoadAndRunBytecode(bytecode, scriptPath); err != nil {
|
|
fmt.Fprintf(os.Stderr, "Error executing '%s': %v\n", scriptPath, err)
|
|
os.Exit(1)
|
|
}
|
|
|
|
// Check if any servers are running to determine if we need to wait
|
|
hasRunningServers := false
|
|
if result, err := state.ExecuteWithResult(`
|
|
for i = 1, 100 do
|
|
if moonshark.http_server_is_running(i) then
|
|
return true
|
|
end
|
|
end
|
|
return false
|
|
`); err == nil {
|
|
if running, ok := result.(bool); ok && running {
|
|
hasRunningServers = true
|
|
}
|
|
}
|
|
|
|
// Only set up signal handling if there are long-running services
|
|
if hasRunningServers {
|
|
sigChan := make(chan os.Signal, 1)
|
|
signal.Notify(sigChan, syscall.SIGINT, syscall.SIGTERM)
|
|
|
|
fmt.Printf("Script executed successfully. Press Ctrl+C to stop...\n")
|
|
|
|
// Wait for signal
|
|
<-sigChan
|
|
fmt.Printf("\nReceived shutdown signal. Cleaning up...\n")
|
|
|
|
// Cleanup HTTP servers through Lua
|
|
if err := state.DoString("moonshark.http_cleanup_servers()"); err != nil {
|
|
fmt.Printf("Warning: failed to cleanup servers: %v\n", err)
|
|
}
|
|
|
|
fmt.Printf("Shutdown complete.\n")
|
|
}
|
|
}
|