Rename monitor to master

This commit is contained in:
Michael Wolf
2026-01-01 12:30:58 -06:00
parent 3bece46638
commit a178536472
9 changed files with 2 additions and 2 deletions

1
master/.gitignore vendored Normal file
View File

@@ -0,0 +1 @@
master

84
master/devrunner.go Normal file
View File

@@ -0,0 +1,84 @@
// a vibe coded el cheapo: https://claude.ai/chat/328ca558-1019-49b9-9f08-e85cfcea2ceb
package main
import (
"context"
"fmt"
"io"
"os"
"os/exec"
"sync"
"time"
)
func runProcess(ctx context.Context, wg *sync.WaitGroup, name, command string) {
defer wg.Done()
for {
select {
case <-ctx.Done():
fmt.Printf("[%s] Stopping\n", name)
return
default:
fmt.Printf("[%s] Starting: %s\n", name, command)
// Create command with context for cancellation
cmd := exec.CommandContext(ctx, "sh", "-c", command)
// Setup stdout pipe
stdout, err := cmd.StdoutPipe()
if err != nil {
fmt.Fprintf(os.Stderr, "[%s] Error creating stdout pipe: %v\n", name, err)
return
}
// Setup stderr pipe
stderr, err := cmd.StderrPipe()
if err != nil {
fmt.Fprintf(os.Stderr, "[%s] Error creating stderr pipe: %v\n", name, err)
return
}
// Start the command
if err := cmd.Start(); err != nil {
fmt.Fprintf(os.Stderr, "[%s] Error starting command: %v\n", name, err)
time.Sleep(time.Second)
continue
}
// Copy output in separate goroutines
var ioWg sync.WaitGroup
ioWg.Add(2)
go func() {
defer ioWg.Done()
io.Copy(os.Stdout, stdout)
}()
go func() {
defer ioWg.Done()
io.Copy(os.Stderr, stderr)
}()
// Wait for command to finish
err = cmd.Wait()
ioWg.Wait() // Ensure all output is copied
// Check if we should restart
select {
case <-ctx.Done():
fmt.Printf("[%s] Stopped\n", name)
return
default:
if err != nil {
fmt.Fprintf(os.Stderr, "[%s] Process exited with error: %v\n", name, err)
} else {
fmt.Printf("[%s] Process exited normally\n", name)
}
fmt.Printf("[%s] Restarting in 1 second...\n", name)
time.Sleep(time.Second)
}
}
}
}

6
master/filechange.go Normal file
View File

@@ -0,0 +1,6 @@
package main
type FileChange struct {
Path string
Operation string
}

8
master/go.mod Normal file
View File

@@ -0,0 +1,8 @@
module philologue.net/diachron/master
go 1.23.3
require (
github.com/fsnotify/fsnotify v1.9.0 // indirect
golang.org/x/sys v0.13.0 // indirect
)

4
master/go.sum Normal file
View File

@@ -0,0 +1,4 @@
github.com/fsnotify/fsnotify v1.9.0 h1:2Ml+OJNzbYCTzsxtv8vKSFD9PbJjmhYF14k/jKC7S9k=
github.com/fsnotify/fsnotify v1.9.0/go.mod h1:8jBTzvmWwFyi3Pb8djgCCO5IBqzKJ/Jwo8TRcHyHii0=
golang.org/x/sys v0.13.0 h1:Af8nKPmuFypiUBjVoU9V20FiaFXOcuZI21p0ycVYYGE=
golang.org/x/sys v0.13.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=

50
master/main.go Normal file
View File

@@ -0,0 +1,50 @@
package main
import (
// "context"
"fmt"
"os"
"os/signal"
// "sync"
"syscall"
)
func main() {
// var program1 = os.Getenv("BUILD_COMMAND")
//var program2 = os.Getenv("RUN_COMMAND")
var watchedDir = os.Getenv("WATCHED_DIR")
// Create context for graceful shutdown
// ctx, cancel := context.WithCancel(context.Background())
//defer cancel()
// Setup signal handling
sigCh := make(chan os.Signal, 1)
signal.Notify(sigCh, os.Interrupt, syscall.SIGTERM)
fileChanges := make(chan FileChange, 10)
go watchFiles(watchedDir, fileChanges)
go printChanges(fileChanges)
// WaitGroup to track both processes
// var wg sync.WaitGroup
// Start both processes
//wg.Add(2)
// go runProcess(ctx, &wg, "builder", program1)
// go runProcess(ctx, &wg, "runner", program2)
// Wait for interrupt signal
<-sigCh
fmt.Println("\nReceived interrupt signal, shutting down...")
// Cancel context to signal goroutines to stop
/// cancel()
// Wait for both processes to finish
// wg.Wait()
fmt.Println("All processes terminated cleanly")
}

11
master/printchanges.go Normal file
View File

@@ -0,0 +1,11 @@
package main
import (
"fmt"
)
func printChanges(changes <-chan FileChange) {
for change := range changes {
fmt.Printf("[%s] %s\n", change.Operation, change.Path)
}
}

74
master/watchfiles.go Normal file
View File

@@ -0,0 +1,74 @@
package main
import (
"github.com/fsnotify/fsnotify"
"log"
"os"
"path/filepath"
)
func watchFiles(dir string, changes chan<- FileChange) {
watcher, err := fsnotify.NewWatcher()
if err != nil {
log.Fatal(err)
}
defer watcher.Close()
// Add all directories recursively
err = filepath.Walk(dir, func(path string, info os.FileInfo, err error) error {
if err != nil {
return err
}
if info.IsDir() {
err = watcher.Add(path)
if err != nil {
log.Printf("Error watching %s: %v\n", path, err)
}
}
return nil
})
if err != nil {
log.Fatal(err)
}
for {
select {
case event, ok := <-watcher.Events:
if !ok {
return
}
// Handle different types of events
var operation string
switch {
case event.Op&fsnotify.Write == fsnotify.Write:
operation = "MODIFIED"
case event.Op&fsnotify.Create == fsnotify.Create:
operation = "CREATED"
// If a new directory is created, start watching it
if info, err := os.Stat(event.Name); err == nil && info.IsDir() {
watcher.Add(event.Name)
}
case event.Op&fsnotify.Remove == fsnotify.Remove:
operation = "REMOVED"
case event.Op&fsnotify.Rename == fsnotify.Rename:
operation = "RENAMED"
case event.Op&fsnotify.Chmod == fsnotify.Chmod:
operation = "CHMOD"
default:
operation = "UNKNOWN"
}
changes <- FileChange{
Path: event.Name,
Operation: operation,
}
case err, ok := <-watcher.Errors:
if !ok {
return
}
log.Printf("Watcher error: %v\n", err)
}
}
}