JSch中断命令正在执行

问题描述 投票:2回答:2

我有一个带有两个按钮的swing应用程序,用于运行和停止执行JSch命令。因此,当单击开始按钮时,我将调用下一个方法:

public String executeSSHCommand(String pattern, String listFiles) {             
    searchRez = new StringBuilder();        
    BufferedReader br = null;
    String line, cmd = null;
    // adding ' symbol to pattern
    pattern = "'"+pattern+"'";       
    //
    try {
        Channel channel = session.openChannel("exec");            
        cmd = "zgrep " + pattern + " " + listFiles;
        log.debug("Executing next ssh command: " + cmd);                        
        ((ChannelExec)channel).setCommand(cmd);                        
        channel.setInputStream(null);
        ((ChannelExec)channel).setErrStream(System.err);             
        InputStream in=channel.getInputStream();
        channel.connect();
        // read server output
        br = new BufferedReader(new InputStreamReader(in));
        while(true && !isCancel){               
          while ((line = br.readLine()) != null && !isCancel) {                        
            searchRez.append(line+"\n");                        
          }                         
          if(channel.isClosed()){
              log.debug("Exit status for execute ssh command is " + channel.getExitStatus());                
            break;
          }
          try{Thread.sleep(1000);}catch(Exception ee){log.error(ee);}
        }

        if (isCancel) {
            log.debug("Search was canceled by user... ");                

            channel.setInputStream(null);                
            if (in != null) {
                in.close();
                in = null;
            }
            if (br != null) {
                br.close();
                br = null;
            }
            try{Thread.sleep(1000);}catch(Exception ee){log.error(ee);}
        }
        //
        channel.disconnect();   
        session.disconnect();         
        log.debug("Search pattern in log file is complete.");
    } catch (Exception ex) {
        log.error(ex);
    }               
    log.debug("Rezult string has next value: " + searchRez.toString());
    return searchRez.toString();
}

正如您在上面看到的,我们有isCancel变量,它是布尔型volatile变量,单击停止按钮时我们将其设置为false。所以我的问题是,当用户单击停止按钮并且会话通道断开时,zgrep表达式继续在服务器上工作。我认为channel.disconnect()应该停止我在服务器上所有正在运行的命令,有人可以建议如何解决此问题。谢谢。

java swing jsch
2个回答
3
投票

[@dic19给我一个主意,将Ctrl+C命令发送到服务器之前断开通道和会话的连接,以中断服务器端zgrep命令的执行。

我在JSch邮件列表中找到了this post,这有助于我解决问题。

因此,要发送Ctrl+C命令,应为通道对象((ChannelExec)channel).setPty(true);启用腻子模式,并将3值写入通道OutputStream:

        ((ChannelExec)channel).setPty(true);
        ((ChannelExec)channel).setCommand(cmd);                        
        channel.setInputStream(null);
        ((ChannelExec)channel).setErrStream(System.err);             
        InputStream in=channel.getInputStream();
        OutputStream out = channel.getOutputStream();
        channel.connect();
        ...........
        if (isCancel) {
            log.debug("Search was canceled by user... ");                

            channel.setInputStream(null);                
            if (in != null) {
                in.close();
                in = null;
            }
            if (br != null) {
                br.close();
                br = null;
            }
            out.write(3);
            out.flush();
            try{Thread.sleep(1000);}catch(Exception ee){log.error(ee);}
        }

0
投票

代替将pty设置为true,您也可以简单地使用:

((ChannelExec) channel).sendSignal("INT"); // may throw Exception

即使您已经调用了out.close();(与正在运行的命令的stdin相关,该功能仍然有效。

© www.soinside.com 2019 - 2024. All rights reserved.