当前位置: 首页 > 知识库问答 >
问题:

Java Messenger套接字

弓泰
2023-03-14

我正在尝试制作一个“messenger”(只是为了真正学习),我对Socket/ServerSocket还很陌生,目前正在制作网络部分。而且,我知道客户网络还不完善。我曾试图完成它,但我被难倒了。

ServerMain:

public class ServerMain extends JFrame {

int WIDTH = 480;
int HEIGHT = 320;

String writeToConsole;

JPanel mainPanel, userPanel, consolePanel;
JTabbedPane tabbedPane;
JButton launchButton;
JTextArea console;
JTextField consoleInput;
JScrollPane consoleScroll;

public ServerMain() {
    super("Messenger Server");

    mainPanel = new JPanel();
    mainPanel.setLayout(null);

    Networking();
    createConsolePanel();

    userPanel = new JPanel();
    userPanel.setLayout(null);

    tabbedPane = new JTabbedPane();

    tabbedPane.add(mainPanel, "Main");
    tabbedPane.add(userPanel, "Users");
    tabbedPane.add(consolePanel, "Console");

    add(tabbedPane);
}

public static void main(String[] args) {
    try {
        UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());

    } catch(UnsupportedLookAndFeelException e) {
        e.printStackTrace();

    } catch (ClassNotFoundException e) {
        e.printStackTrace();

    } catch (InstantiationException e) {
        e.printStackTrace();

    } catch (IllegalAccessException e) {
        e.printStackTrace();
    }

    ServerMain frame = new ServerMain();
    frame.setDefaultCloseOperation(EXIT_ON_CLOSE);
    frame.setSize(frame.WIDTH, frame.HEIGHT);
    frame.setLocationRelativeTo(null);
    frame.setVisible(true);
    frame.setResizable(false);
}

public void Networking() {
    ServerNetworking net;
    try {
        net = new ServerNetworking();
        net.start();
    } catch(Exception e) {
        e.printStackTrace();
    }
}

public void createConsolePanel() {
    consolePanel = new JPanel();
    consolePanel.setLayout(null);

    console = new JTextArea();
    console.setFont(new Font("", Font.PLAIN, 13 + 1/2));
    console.setBounds(0, 0, WIDTH, HEIGHT - 100);
    console.setEditable(false);
    console.setLineWrap(true);


    consoleInput = new JTextField(20);
    consoleInput.setBounds(0, 0, WIDTH, 25);
    consoleInput.setLocation(0, 240);
    consoleInput.addActionListener(new ActionListener(){
        public void actionPerformed(ActionEvent event) {
            String input = consoleInput.getText();

            if(input.equalsIgnoreCase("/sendmessage")) {
                //console.append(input);
                console.append("Input who you would like to send the message to:");
                consoleInput.setText("");

            } if (input.equalsIgnoreCase("/ban")) {
                console.append("Who you would like to ban");
                consoleInput.setText("");
            } 
        }
    });

    consolePanel.add(console);
    consolePanel.add(consoleInput);
}

public void consoleWrite(String write) {
    console.append(write);
}
}

服务器网络(线程):

public class ServerNetworking extends Thread {
private static ServerSocket servSock;
private static final int PORT = 1234;

private static void handleClient() {
    Socket link = null;                                 
    try {
        link = servSock.accept();                       

        Scanner input = new Scanner(link.getInputStream());     
        PrintWriter output =
        new PrintWriter(link.getOutputStream(),true);

        int numMessages = 0;
        String message = input.nextLine();
        while (!message.equals("***CLOSE***")) {
            System.out.println("Message received.");
            numMessages++;
            output.println("Message " +
            numMessages + ": " + message);
            message = input.nextLine();
        }
        output.println(numMessages + " messages received.");
    } catch(IOException ioEx)  {
        ioEx.printStackTrace();
    } finally {
        try {
            System.out.println( "\n* Closing connection... *");
            link.close();
        } catch(IOException ioEx) {
            System.out.println("Unable to disconnect!");
            System.exit(1);
        }
    }
}

public void run() {
     System.out.println("Opening port...\n");
     try {
         servSock = new ServerSocket(PORT);
     } catch(IOException ioEx) {
         System.out.println("Unable to attach to port!");
         System.exit(1);
     } do {
         handleClient();
     } while (true);
}

}

ClientMain:

public class ClientMain extends JFrame {

int WIDTH = 640;
int HEIGHT = 480;

JTabbedPane tabbedPane;
JMenuBar topMenuBar;
JMenu userMenu, helpMenu, settingsMenu;
JRadioButtonMenuItem menuItem;
JPanel mainPanel, friendsPanel, groupsPanel, testPanel;
JLabel title;
JScrollPane consoleScrollPane;
JSplitPane friendsPane;
JTextArea messageArea, testArea;
JTextField testField;
Box box;

public ClientMain() {
    super("Messenger Client");

    Networking();

    title = new JLabel("Client!");
    title.setFont(new Font("Impact", Font.PLAIN, 32));

    mainPanel = new JPanel();
    mainPanel.setLayout(null);
    mainPanel.add(title);

    groupsPanel = new JPanel();
    groupsPanel.setLayout(null);

    friendsPanel = new JPanel();
    friendsPanel.setLayout(null);

    testPanel = new JPanel();
    testPanel.setLayout(null);

    testArea = new JTextArea();
    testArea.setFont(new Font("", Font.PLAIN, 13 + 1/2));
    testArea.setBounds(0, 0, WIDTH, HEIGHT - 100);
    testArea.setEditable(false);
    testArea.setLineWrap(true);

    testField = new JTextField(20);
    testField.setBounds(0, 380, 640, 25);
    //testField.setLocation(0, HEIGHT - 50);
    testField.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent e) {
            ClientNet net = new ClientNet();
            String input = null;
            input = testField.getText();
            testArea.append(input);
            testField.setText("");

            if(input.equalsIgnoreCase("/sendmessage")) {
                testArea.append("\n Input who you would like to send the message to:");
                input = null;

                if(input.equalsIgnoreCase("Hello")) {
                    net.userEntry = input;
                }
            }
        }
    });

    testPanel.add(testArea);
    testPanel.add(testField);

    tabbedPane = new JTabbedPane();

    tabbedPane.add(mainPanel, "Main");
    tabbedPane.add(friendsPanel, "Friends");
    tabbedPane.add(groupsPanel, "Groups");
    tabbedPane.add(testPanel, "Test");

    topMenuBar = new JMenuBar();

    userMenu = new JMenu("User");

    settingsMenu = new JMenu("Settings");

    helpMenu = new JMenu("Help");

    menuItem = new JRadioButtonMenuItem("Something here");

    userMenu.add(menuItem);

    topMenuBar.add(userMenu, "User");
    topMenuBar.add(settingsMenu, "Settings");
    topMenuBar.add(helpMenu, "Help");

    add(topMenuBar);
    add(tabbedPane);
}

public static void main(String[] args) {
    try {
        UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());

    } catch(UnsupportedLookAndFeelException e) {
        e.printStackTrace();

    } catch (ClassNotFoundException e) {
        e.printStackTrace();

    } catch (InstantiationException e) {
        e.printStackTrace();

    } catch (IllegalAccessException e) {
        e.printStackTrace();

    }

    ClientMain frame = new ClientMain();
    Insets insets = frame.getInsets();
    frame.setDefaultCloseOperation(EXIT_ON_CLOSE);
    frame.setSize(frame.WIDTH, frame.HEIGHT);
    frame.setLocationRelativeTo(null);
    frame.setVisible(true);
    frame.setResizable(false);
    frame.setJMenuBar(frame.topMenuBar);

}

public void Networking() {
    ClientNet net;
    try {
        net = new ClientNet();
        net.start();

    } catch(Exception e) {
        e.printStackTrace();
    }
}

public void createMenuBar() {
    topMenuBar = new JMenuBar();

    userMenu = new JMenu("User");
    settingsMenu = new JMenu("Settings");
    helpMenu = new JMenu("Help");

    menuItem = new JRadioButtonMenuItem("MenuItem");
    menuItem.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent arg0) {

        }
    });

    topMenuBar.add(userMenu, "User");
    topMenuBar.add(settingsMenu, "Settings");
    topMenuBar.add(helpMenu, "Help");
}

public void getFriends(String username) {

}

}

客户端网络(线程):

public class ClientMain extends JFrame {

int WIDTH = 640;
int HEIGHT = 480;

JTabbedPane tabbedPane;
JMenuBar topMenuBar;
JMenu userMenu, helpMenu, settingsMenu;
JRadioButtonMenuItem menuItem;
JPanel mainPanel, friendsPanel, groupsPanel, testPanel;
JLabel title;
JScrollPane consoleScrollPane;
JSplitPane friendsPane;
JTextArea messageArea, testArea;
JTextField testField;
Box box;

public ClientMain() {
    super("Messenger Client");

    Networking();

    title = new JLabel("Client!");
    title.setFont(new Font("Impact", Font.PLAIN, 32));

    mainPanel = new JPanel();
    mainPanel.setLayout(null);
    mainPanel.add(title);

    groupsPanel = new JPanel();
    groupsPanel.setLayout(null);

    friendsPanel = new JPanel();
    friendsPanel.setLayout(null);

    testPanel = new JPanel();
    testPanel.setLayout(null);

    testArea = new JTextArea();
    testArea.setFont(new Font("", Font.PLAIN, 13 + 1/2));
    testArea.setBounds(0, 0, WIDTH, HEIGHT - 100);
    testArea.setEditable(false);
    testArea.setLineWrap(true);

    testField = new JTextField(20);
    testField.setBounds(0, 380, 640, 25);
    //testField.setLocation(0, HEIGHT - 50);
    testField.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent e) {
            ClientNet net = new ClientNet();
            String input = null;
            input = testField.getText();
            testArea.append(input);
            testField.setText("");

            if(input.equalsIgnoreCase("/sendmessage")) {
                testArea.append("\n Input who you would like to send the message to:");
                input = null;

                if(input.equalsIgnoreCase("Hello")) {
                    net.userEntry = input;
                }
            }
        }
    });

    testPanel.add(testArea);
    testPanel.add(testField);

    tabbedPane = new JTabbedPane();

    tabbedPane.add(mainPanel, "Main");
    tabbedPane.add(friendsPanel, "Friends");
    tabbedPane.add(groupsPanel, "Groups");
    tabbedPane.add(testPanel, "Test");

    topMenuBar = new JMenuBar();

    userMenu = new JMenu("User");

    settingsMenu = new JMenu("Settings");

    helpMenu = new JMenu("Help");

    menuItem = new JRadioButtonMenuItem("Something here");

    userMenu.add(menuItem);

    topMenuBar.add(userMenu, "User");
    topMenuBar.add(settingsMenu, "Settings");
    topMenuBar.add(helpMenu, "Help");

    add(topMenuBar);
    add(tabbedPane);
}

public static void main(String[] args) {
    try {
        UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());

    } catch(UnsupportedLookAndFeelException e) {
        e.printStackTrace();

    } catch (ClassNotFoundException e) {
        e.printStackTrace();

    } catch (InstantiationException e) {
        e.printStackTrace();

    } catch (IllegalAccessException e) {
        e.printStackTrace();

    }

    ClientMain frame = new ClientMain();
    Insets insets = frame.getInsets();
    frame.setDefaultCloseOperation(EXIT_ON_CLOSE);
    frame.setSize(frame.WIDTH, frame.HEIGHT);
    frame.setLocationRelativeTo(null);
    frame.setVisible(true);
    frame.setResizable(false);
    frame.setJMenuBar(frame.topMenuBar);

}

public void Networking() {
    ClientNet net;
    try {
        net = new ClientNet();
        net.start();

    } catch(Exception e) {
        e.printStackTrace();
    }
}

public void createMenuBar() {
    topMenuBar = new JMenuBar();

    userMenu = new JMenu("User");
    settingsMenu = new JMenu("Settings");
    helpMenu = new JMenu("Help");

    menuItem = new JRadioButtonMenuItem("MenuItem");
    menuItem.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent arg0) {

        }
    });

    topMenuBar.add(userMenu, "User");
    topMenuBar.add(settingsMenu, "Settings");
    topMenuBar.add(helpMenu, "Help");
}

public void getFriends(String username) {

}
}

这是我得到的错误,当我启动服务器,然后客户端:它不应该说"消息收到",因为我实际上没有发送消息

Opening port...

Message received.

* Closing connection... *
Exception in thread "Thread-1" java.util.NoSuchElementException: No line found
at java.util.Scanner.nextLine(Unknown Source)
at Server.ServerNetworking.handleClient(ServerNetworking.java:29)
at Server.ServerNetworking.run(ServerNetworking.java:53)

共有1个答案

陶树
2023-03-14

我认为问题在于ServerNetworking类中的以下循环:

while (!message.equals("***CLOSE***")) {
    System.out.println("Message received.");
    numMessages++;
    output.println("Message " +
    numMessages + ": " + message);
    message = input.nextLine();
}

这段代码的问题是,在收到来自客户端的完整消息后,最后一行代码

message = input.nextLine();

查找消息的下一行,但由于消息已被使用,它引发以下异常:

NoSuchElementException - if no line was found 

所以在阅读下一行之前,你需要确保有下一行要读。您可以使用

hasNextLine()

方法,如果有下一行,则返回true,否则返回false。

if(input.hasNextLine()) {
    message = input.nextLine();  // read the next line
} else {
   break;  // exit the loop because, nothing to read left
}
 类似资料:
  • socket_read和socket_recv之间有什么区别?我正在尝试使用PHP套接字,但使用socket_read时收到了以下警告: 请帮帮我!

  • 问题内容: 我试图理解SocketChannels和NIO。我知道如何使用常规套接字,以及如何制作一个简单的每客户端线程服务器(使用常规阻塞套接字)。 所以我的问题是: 什么是SocketChannel? 当使用SocketChannel而不是Socket时,我还能得到什么呢? 通道和缓冲区之间是什么关系? 什么是选择器? 文档中的第一句话是。那是什么意思? 我也阅读了本文档,但是不知何故…… 问

  • 线程“main”java.net.ConnectException:连接超时:在java.net.dualStackplainsockeTimpl.Connect0(本机方法)在java.net.dualStackplainsockeTimpl.socketConnect(DualStackplainsockeTimpl.java:69)在java.net.abstractplainsockeTi

  • 我最近一直在玩套接字,但是我遇到了一个问题…当我从服务器接收数据时,我得到一个“java.net.套接字异常:套接字关闭”异常。我没有在任何地方关闭套接字,事实上,我唯一使用关闭()的地方是扫描仪上从System.in读取文本; 以下是我的代码: 客户: 服务器: 数据包发送者: 客户端接收器: 数据包接收器:

  • 问题内容: 如何创建SSL套接字连接? 我真的需要创建密钥库吗?该密钥库应该与我所有的客户端应用程序共享吗? 我用以下代码创建了一个服务器: 我用以下代码在android上创建了一个客户端: 但是当我尝试连接时,会引发以下错误: 问题答案: 您需要一个证书来建立ssl连接,您可以在密钥库中加载证书,也可以加载证书本身。我将显示一些有关keystore选项的示例。 您的代码需要一些参数才能运行: 您

  • 我有一个UDP服务器,它必须同时为IPV4和IPV6地址上的客户端提供服务。我创建了一个IPV6套接字来同时为IPV4和IPV6客户端服务。 服务器在第一次通信时存储客户端的IPAddress。如果是IPV4客户端,则存储为IPV4地址;如果是IPV6客户端,则服务器存储为IPV6地址。对于以后的所有通信,它检查存储是否已知(存储)该客户端,然后相应地执行操作。为了将客户端地址与存储的地址进行比较

  • 问题内容: 是否可以在IP协议下使用ICMP套接字?也许像: 我应该在 字段中输入什么?我看到了一些使用SOCK_RAW的示例,但是这是否会阻止OS处理IP协议呢? 还有一件事。由于该协议不涉及任何端口,操作系统如何知道他应该向哪个进程发送ICMP数据报? 问题答案: 是的,这是可能的,因为该命令执行ICMP。 要找出所涉及的系统调用,您可以使用该命令(在根目录下)。 您也可以浏览该命令的源代码,