From e58c9b797b503ecfb8628f7f65d58e886b5256e2 Mon Sep 17 00:00:00 2001 From: dudaodong Date: Fri, 13 Sep 2024 15:09:44 +0800 Subject: [PATCH] feat: add StartProcess, StopProcess, KillProcess for system package --- docs/api/packages/system.md | 98 ++++++++++++++++++++++++++++++- docs/en/api/packages/system.md | 103 ++++++++++++++++++++++++++++++++- system/os.go | 34 +++++++++++ system/os_example_test.go | 44 +++++++++++++- system/os_test.go | 52 +++++++++++++---- 5 files changed, 316 insertions(+), 15 deletions(-) diff --git a/docs/api/packages/system.md b/docs/api/packages/system.md index e9b673b..c1bfc04 100644 --- a/docs/api/packages/system.md +++ b/docs/api/packages/system.md @@ -1,6 +1,6 @@ # System -system 包含 os, runtime, shell command 相关函数。 +system 包含 os, 运行time, shell command 相关函数。
@@ -308,3 +308,99 @@ func main() { fmt.Println(osBit) // 32 or 64 } ``` + +### StartProcess + +

创建进程。

+ +函数签名: + +```go +func StartProcess(command string, args ...string) (int, error) +``` + +示例:[运行](todo) + +```go +import ( + "fmt" + "github.com/duke-git/lancet/v2/system" +) + +func main() { + pid, err := system.StartProcess("sleep", "2") + if err != nil { + return + } + + fmt.Println(pid) +} +``` + +### StopProcess + +

停止进程。

+ +函数签名: + +```go +func StopProcess(pid int) error +``` + +示例:[运行](todo) + +```go +import ( + "fmt" + "github.com/duke-git/lancet/v2/system" +) + +func main() { + pid, err := system.StartProcess("sleep", "10") + if err != nil { + return + } + time.Sleep(1 * time.Second) + + err = system.StopProcess(pid) + + fmt.Println(err) + + // Output: + // +} +``` + +### KillProcess + +

杀掉进程。

+ +函数签名: + +```go +func KillProcess(pid int) error +``` + +示例:[运行](todo) + +```go +import ( + "fmt" + "github.com/duke-git/lancet/v2/system" +) + +func main() { + pid, err := system.StartProcess("sleep", "10") + if err != nil { + return + } + time.Sleep(1 * time.Second) + + err = system.KillProcess(pid) + + fmt.Println(err) + + // Output: + // +} +``` \ No newline at end of file diff --git a/docs/en/api/packages/system.md b/docs/en/api/packages/system.md index 1fd130e..964f5fe 100644 --- a/docs/en/api/packages/system.md +++ b/docs/en/api/packages/system.md @@ -31,6 +31,9 @@ import ( - [CompareOsEnv](#CompareOsEnv) - [ExecCommand](#ExecCommand) - [GetOsBits](#GetOsBits) +- [StartProcess](#StartProcess) +- [StopProcess](#StopProcess) +- [KillProcess](#KillProcess)
@@ -249,7 +252,7 @@ The second parameter of the function is the cmd option control parameter. The ty ```go type ( - Option func(*exec.Cmd) + Option func(*exec.Cmd) ) func ExecCommand(command string, opts ...Option) (stdout, stderr string, err error) ``` @@ -288,7 +291,7 @@ func main() { ### GetOsBits -

Get current os bits, 32bit or 64bit. return 32 or 64

+

Get current os bits, 32bit or 64bit. return 32 or 64.

Signature: @@ -309,3 +312,99 @@ func main() { fmt.Println(osBit) // 32 or 64 } ``` + +### StartProcess + +

Start a new process with the specified name and arguments.

+ +Signature: + +```go +func StartProcess(command string, args ...string) (int, error) +``` + +Example:[Run](todo) + +```go +import ( + "fmt" + "github.com/duke-git/lancet/v2/system" +) + +func main() { + pid, err := system.StartProcess("sleep", "2") + if err != nil { + return + } + + fmt.Println(pid) +} +``` + +### StopProcess + +

Stop a process by pid.

+ +Signature: + +```go +func StopProcess(pid int) error +``` + +Example:[Run](todo) + +```go +import ( + "fmt" + "github.com/duke-git/lancet/v2/system" +) + +func main() { + pid, err := system.StartProcess("sleep", "10") + if err != nil { + return + } + time.Sleep(1 * time.Second) + + err = system.StopProcess(pid) + + fmt.Println(err) + + // Output: + // +} +``` + +### KillProcess + +

Kill a process by pid.

+ +Signature: + +```go +func KillProcess(pid int) error +``` + +Example:[Run](todo) + +```go +import ( + "fmt" + "github.com/duke-git/lancet/v2/system" +) + +func main() { + pid, err := system.StartProcess("sleep", "10") + if err != nil { + return + } + time.Sleep(1 * time.Second) + + err = system.KillProcess(pid) + + fmt.Println(err) + + // Output: + // +} +``` \ No newline at end of file diff --git a/system/os.go b/system/os.go index 2924b33..f7dcdb0 100644 --- a/system/os.go +++ b/system/os.go @@ -132,3 +132,37 @@ func byteToString(data []byte, charset string) string { func GetOsBits() int { return 32 << (^uint(0) >> 63) } + +// StartProcess start a new process with the specified name and arguments. +// Play: todo +func StartProcess(command string, args ...string) (int, error) { + cmd := exec.Command(command, args...) + + if err := cmd.Start(); err != nil { + return 0, err + } + + return cmd.Process.Pid, nil +} + +// StopProcess stop a process by pid. +// Play: todo +func StopProcess(pid int) error { + process, err := os.FindProcess(pid) + if err != nil { + return err + } + + return process.Signal(os.Kill) +} + +// KillProcess kill a process by pid. +// Play: todo +func KillProcess(pid int) error { + process, err := os.FindProcess(pid) + if err != nil { + return err + } + + return process.Kill() +} diff --git a/system/os_example_test.go b/system/os_example_test.go index 8ab3a65..ccdd317 100644 --- a/system/os_example_test.go +++ b/system/os_example_test.go @@ -1,6 +1,9 @@ package system -import "fmt" +import ( + "fmt" + "time" +) func ExampleSetOsEnv() { err := SetOsEnv("foo", "abc") @@ -75,3 +78,42 @@ func ExampleGetOsBits() { // Output: // 64 } + +func ExampleStartProcess() { + pid, err := StartProcess("sleep", "2") + if err != nil { + return + } + + fmt.Println(pid) +} + +func ExampleStopProcess() { + pid, err := StartProcess("sleep", "10") + if err != nil { + return + } + time.Sleep(1 * time.Second) + + err = StopProcess(pid) + + fmt.Println(err) + + // Output: + // +} + +func ExampleKillProcess() { + pid, err := StartProcess("sleep", "3") + if err != nil { + return + } + time.Sleep(1 * time.Second) + + err = KillProcess(pid) + + fmt.Println(err) + + // Output: + // +} diff --git a/system/os_test.go b/system/os_test.go index 28a7478..4dc5d49 100644 --- a/system/os_test.go +++ b/system/os_test.go @@ -1,6 +1,7 @@ package system import ( + "os/exec" "strings" "testing" @@ -53,7 +54,9 @@ func TestExecCommand(t *testing.T) { assert := internal.NewAssert(t, "TestExecCommand") // linux or mac - stdout, stderr, err := ExecCommand("ls") + stdout, stderr, err := ExecCommand("ls", func(cmd *exec.Cmd) { + cmd.Dir = "/" + }) t.Log("std out: ", stdout) t.Log("std err: ", stderr) assert.Equal("", stderr) @@ -74,16 +77,6 @@ func TestExecCommand(t *testing.T) { assert.IsNotNil(err) } -// func TestExecCommandWithOption(t *testing.T) { -// assert := internal.NewAssert(t, "TestExecCommandWithOption") - -// stdout, stderr, err := ExecCommand("ls", WithForeground()) -// t.Log("std out: ", stdout) -// t.Log("std err: ", stderr) -// assert.Equal("", stderr) -// assert.IsNil(err) -// } - func TestGetOsBits(t *testing.T) { t.Parallel() @@ -95,3 +88,40 @@ func TestGetOsBits(t *testing.T) { t.Error("os is not 32 or 64 bits") } } + +func TestStartProcess(t *testing.T) { + t.Parallel() + + assert := internal.NewAssert(t, "TestStartProcess") + + pid, err := StartProcess("ls", "-a") + + assert.IsNil(err) + assert.Equal(true, pid > 0) +} + +func TestKillProcess(t *testing.T) { + t.Parallel() + + assert := internal.NewAssert(t, "TestKillProcess") + + pid, err := StartProcess("ls") + assert.IsNil(err) + assert.Equal(true, pid > 0) + + err = KillProcess(pid) + assert.IsNil(err) +} + +func TestStopProcess(t *testing.T) { + t.Parallel() + + assert := internal.NewAssert(t, "TestStopProcess") + + pid, err := StartProcess("ls") + assert.IsNil(err) + assert.Equal(true, pid > 0) + + err = StopProcess(pid) + assert.IsNil(err) +}