From d7c08295f811ebf04ce469d192839ff204fc8487 Mon Sep 17 00:00:00 2001 From: ssongliu <73214554+ssongliu@users.noreply.github.com> Date: Wed, 24 May 2023 15:45:12 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E8=A7=A3=E5=86=B3=E5=AE=B9=E5=99=A8?= =?UTF-8?q?=E8=BF=9B=E7=A8=8B=E5=BC=82=E5=B8=B8=E9=80=80=E5=87=BA=E7=9A=84?= =?UTF-8?q?=E9=97=AE=E9=A2=98=20(#1124)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- backend/app/api/v1/terminal.go | 47 +++++++++++++++++++++++++++------- 1 file changed, 38 insertions(+), 9 deletions(-) diff --git a/backend/app/api/v1/terminal.go b/backend/app/api/v1/terminal.go index e3ec524dc..6082d0d4b 100644 --- a/backend/app/api/v1/terminal.go +++ b/backend/app/api/v1/terminal.go @@ -5,8 +5,8 @@ import ( "encoding/json" "fmt" "net/http" - "os/exec" "strconv" + "strings" "time" "github.com/1Panel-dev/1Panel/backend/app/api/v1/helper" @@ -112,11 +112,12 @@ func (b *BaseApi) RedisWsSsh(c *gin.Context) { if len(redisConf.Requirepass) != 0 { commands = fmt.Sprintf("redis-cli -a %s --no-auth-warning", redisConf.Requirepass) } + pidMap := loadMapFromDockerTop(redisConf.ContainerName) slave, err := terminal.NewCommand(fmt.Sprintf("docker exec -it %s %s", redisConf.ContainerName, commands)) if wshandleError(wsConn, err) { return } - defer killBash(redisConf.ContainerName, commands) + defer killBash(redisConf.ContainerName, commands, pidMap) defer slave.Close() tty, err := terminal.NewLocalWsSession(cols, rows, wsConn, slave) @@ -175,11 +176,12 @@ func (b *BaseApi) ContainerWsSsh(c *gin.Context) { if len(user) != 0 { commands = fmt.Sprintf("docker exec -it -u %s %s %s", user, containerID, command) } + pidMap := loadMapFromDockerTop(containerID) slave, err := terminal.NewCommand(commands) if wshandleError(wsConn, err) { return } - defer killBash(containerID, command) + defer killBash(containerID, command, pidMap) defer slave.Close() tty, err := terminal.NewLocalWsSession(cols, rows, wsConn, slave) @@ -219,13 +221,40 @@ func wshandleError(ws *websocket.Conn, err error) bool { return false } -func killBash(containerID, comm string) { - sudo := "" - if cmd.HasNoPasswordSudo() { - sudo = "sudo" +func loadMapFromDockerTop(containerID string) map[string]string { + pidMap := make(map[string]string) + sudo := cmd.SudoHandleCmd() + + stdout, err := cmd.Execf("%s docker top %s -eo pid,command ", sudo, containerID) + if err != nil { + return pidMap + } + lines := strings.Split(stdout, "\n") + for _, line := range lines { + parts := strings.Fields(line) + if len(parts) != 2 { + continue + } + pidMap[parts[0]] = parts[1] + } + return pidMap +} + +func killBash(containerID, comm string, pidMap map[string]string) { + sudo := cmd.SudoHandleCmd() + newPidMap := loadMapFromDockerTop(containerID) + for pid, command := range newPidMap { + isOld := false + for pid2 := range pidMap { + if pid == pid2 { + isOld = true + break + } + } + if !isOld && command == comm { + _, _ = cmd.Execf("%s kill -9 %s", sudo, pid) + } } - command := exec.Command("sh", "-c", fmt.Sprintf("%s kill -9 $(docker top %s -eo pid,command | grep '%s' | awk '{print $1}')", sudo, containerID, comm)) - _, _ = command.CombinedOutput() } var upGrader = websocket.Upgrader{