我如何发送命令并从Java中的Telnet服务器读取响应?

问题描述 投票:0回答:1

我很难用我最初用Python编写的Java重写应用程序。我需要连接到Telnet服务器并提交命令(我假设它需要为Ascii字节),然后检索响应。然后,我将解析响应,但这与此处无关。每个响应的末尾应包含“ &&”,但在套接字实例的任何地方都看不到这种类型的方法。我也尝试过Apache Telnet库。也许我只是不了解这些东西是如何工作的。

这是我到目前为止拥有的Java代码:

import org.apache.commons.net.telnet.TelnetClient;
import java.io.*;
import java.net.*;
import java.nio.charset.StandardCharsets;


public class Telnet
{

    public Telnet()
    {

    }

    public void initiateTelnetSession()
    {

            Socket sock = new Socket(IP, Integer.parseInt("10".concat(Port)));

            DataInputStream dataInput = new DataInputStream(sock.getInputStream());

            DataOutputStream dataOutput = new DataOutputStream(sock.getOutputStream());

            BufferedReader buff = new BufferedReader(new InputStreamReader(System.in));

            System.out.println("Connecting to stuff.");

            dataOutput.write("\\x01".getBytes(StandardCharsets.US_ASCII));
            dataOutput.write("i20700".getBytes(StandardCharsets.US_ASCII));
            dataOutput.write("\\n".getBytes(StandardCharsets.US_ASCII));

            System.out.println(buff.readLine());

            sock.close();
            dataInput.close();
            dataOutput.close();
            buff.close();
            System.exit(0);

这真的很基础,我假设我需要缓冲区读取器更多的逻辑,但是我是新手,所以我不知道。这是我在原始应用程序中编写的Python代码:

# Letting you know we're attempting a connection :)
        print(colored("Connecting to..." + Host + " " + Port + " for command " + command, 'green'))

        # Allow up to 3 retries to execute the telnet connection
        for i in range(0, 3):
            while True:
                try:
                    # Set variable to the Telnet class, passing in the host and port defined above
                    tn = telnetlib.Telnet(Host, Port)
                    tn.set_debuglevel(0)
                    # Each sleep is to allow time for the stream to complete
                    time.sleep(1)
                    # \x01 is the ^A command you would enter if running commands manually.
                    # Encoding to ascii is necessary to combine byte and ascii values. Streams are in bytes.
                    tn.write("\x01".encode("ascii"))
                    time.sleep(1)
                    # Write the supplied command, press enter
                    tn.write(str(command + "\n").encode("ascii"))
                    # Read until the end of the stream, denoted by && per documentation
                    stream = tn.read_until("&&".encode("ascii"))
                    # Print it to look at it if you want to. You don't have to. It's just nice to see that it's working, you know?
                    #print(str(stream) + "\n")
                    tn.close()
                    #print(str(command).encode("ascii") + " stream is ".encode("ascii") + str(stream).encode("ascii"))
                except (socket.error, WindowsError, OSError) as err:
                    print(colored("There was an error and we're trying again.", "yellow"))
                    time.sleep(3)
                    if i == 2:
                        print(colored("We couldn't make a successful connection on port " + str(portnumber) +
                                      " for the " + str(command) + " command. We tried three times. Moving on.", "red"))
                        return
                else:
                    print(colored("We pulled the readings successfully. Let us continue.", "green"))
                    return stream
                break

任何帮助将不胜感激。我觉得我要接近了……谢谢!

java python sockets stream telnet
1个回答
0
投票

BufferedReader.readLine()只会读取,直到找到下一个换行为止,直到您需要的&&为止,都无法使用它进行读取。您需要自己实现。我猜是这样的:

public class TelnetReader extends FilterReader {

    private static final int AMPERSAND = "&".getBytes(StandardCharsets.US_ASCII)[0] & 0xFF;

    public TelnetReader(Reader in) {
        super(in);
    }

    public String readResponse() throws IOException {
        StringBuilder sb = new StringBuilder();
        int current = -1;
        while ((current = read()) > -1) {
            if (current != AMPERSAND) {
                sb.append(new String(new byte[] { (byte) current }, StandardCharsets.US_ASCII));
            } else {
                int next = read();
                if (next != AMPERSAND) {
                    sb.append(new String(new byte[] { (byte) current, (byte) next }, StandardCharsets.US_ASCII));
                } else {
                    return sb.toString();
                }
            }
        }
        return sb.toString();
    }
}

有更有效的方法,但这是一个很好的起点。获得Reader并将其读到“ &&”后,就可以像这样使用它了:

DataInputStream dataInput = new DataInputStream(sock.getInputStream());
TelnetReader dataInputReader = new TelnetReader(new BufferedReader(new InputStreamReader(dataInput)));

这将使您能够使用dataInputReader.readResponse()读取响应。

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