From fc61af4b6634a1b15fae720d951c202916b8aaf6 Mon Sep 17 00:00:00 2001 From: Xircon Date: Sat, 21 Feb 2026 21:18:29 -0500 Subject: [PATCH] Rework almost Everything! YAY --- .gitignore | 3 + .../java/net/xircon/xenon/client/Xenon.java | 19 +++--- .../xenon/client/networking/Networking.java | 27 ++------ .../networking/textclient/TextClient.java | 62 +++++++++++++++---- .../java/net/xircon/xenon/server/Xenon.java | 11 ++-- .../xenon/server/io/database/Database.java | 54 ++++++++++++++++ .../xenon/server/networking/Networking.java | 20 +----- .../networking/textserver/ClientHandler.java | 11 ++-- .../networking/textserver/TextServer.java | 38 ++++++++---- server/src/main/resources/server.properties | 3 +- 10 files changed, 161 insertions(+), 87 deletions(-) create mode 100644 server/src/main/java/net/xircon/xenon/server/io/database/Database.java diff --git a/.gitignore b/.gitignore index 0890712..cc0beef 100644 --- a/.gitignore +++ b/.gitignore @@ -45,3 +45,6 @@ bin/ ## Logs ## /server/logs/ /client/logs/ + +## Server Database ## +/server/server.db diff --git a/client/src/main/java/net/xircon/xenon/client/Xenon.java b/client/src/main/java/net/xircon/xenon/client/Xenon.java index dd4c678..937a380 100644 --- a/client/src/main/java/net/xircon/xenon/client/Xenon.java +++ b/client/src/main/java/net/xircon/xenon/client/Xenon.java @@ -18,14 +18,11 @@ import java.util.Objects; public class Xenon implements Runnable { public static void main(String[] args) {new Xenon().start();} - private static Socket mainSocket; public Color buttonColour = new Color(55, 90, 129); public Image xenonIcon; static final String propertiesFile = "client.properties"; // Properties - public static int PortVoIP = 49190; - public static int PortText = 49180; public static int Width = 800; public static int Height = 600; @@ -64,11 +61,10 @@ public class Xenon implements Runnable { System.setOut(systemOutput); System.setErr(systemOutput); - Log.info("Starting Xenon Client!"); // Get Property Values - PortVoIP = Objects.requireNonNull(Util.GetProperties(propertiesFile, "PortVoIP", Util.PROPERTY_TYPE_INT)).intValue; - PortText = Objects.requireNonNull(Util.GetProperties(propertiesFile, "PortText", Util.PROPERTY_TYPE_INT)).intValue; + Networking.PortVoIP = Objects.requireNonNull(Util.GetProperties(propertiesFile, "PortVoIP", Util.PROPERTY_TYPE_INT)).intValue; + Networking.PortText = Objects.requireNonNull(Util.GetProperties(propertiesFile, "PortText", Util.PROPERTY_TYPE_INT)).intValue; Width = Objects.requireNonNull(Util.GetProperties(propertiesFile, "Width", Util.PROPERTY_TYPE_INT)).intValue; Height = Objects.requireNonNull(Util.GetProperties(propertiesFile, "Height", Util.PROPERTY_TYPE_INT)).intValue; @@ -94,14 +90,16 @@ public class Xenon implements Runnable { public void actionPerformed(ActionEvent e) { String IPAddress = JOptionPane.showInputDialog(null, "IP Address Of Server", "127.0.0.1"); if (IPAddress != null) { - mainSocket = Networking.connectToServer(IPAddress, PortText); + // Start Text Client + Thread textClient = new Thread(new TextClient(IPAddress, nickname)); + textClient.start(); } } }); JMenuItem m22 = new JMenuItem(new AbstractAction("Disconnect From Server") { @Override public void actionPerformed(ActionEvent e) { - Networking.disconnectFromServer(mainSocket); + Networking.disconnectFromServer(TextClient.socket); } }); JMenuItem m23 = new JMenuItem(new AbstractAction("Change Nickname") { @@ -176,11 +174,10 @@ public class Xenon implements Runnable { // Text Sending Handler send.addActionListener(e -> { - if (mainSocket == null) {JOptionPane.showMessageDialog(null, "Ensure you are Connected to a Server!", "Error", JOptionPane.ERROR_MESSAGE);} + if (TextClient.socket == null || !TextClient.socket.isConnected() || TextClient.socket.isClosed()) {JOptionPane.showMessageDialog(null, "Ensure you are Connected to a Server!", "Error", JOptionPane.ERROR_MESSAGE);} else { Log.info("Sending " + sendField.getText()); - Thread textClient = new Thread(new TextClient(mainSocket, nickname, sendField.getText())); - textClient.start(); + TextClient.messageBuffer = sendField.getText(); SwingUtilities.invokeLater(() -> sendField.setText("")); } }); diff --git a/client/src/main/java/net/xircon/xenon/client/networking/Networking.java b/client/src/main/java/net/xircon/xenon/client/networking/Networking.java index eb5d468..cfa3ac5 100644 --- a/client/src/main/java/net/xircon/xenon/client/networking/Networking.java +++ b/client/src/main/java/net/xircon/xenon/client/networking/Networking.java @@ -3,36 +3,17 @@ package net.xircon.xenon.client.networking; import net.xircon.xenon.client.io.Log; import javax.annotation.Nullable; -import java.io.BufferedReader; import java.io.IOException; -import java.io.InputStreamReader; -import java.io.PrintWriter; import java.net.InetSocketAddress; import java.net.Socket; import java.net.SocketAddress; import java.net.SocketTimeoutException; public class Networking { - - - @Nullable - public static Socket connectToServer(String Address, int Port) { - try { - Log.info("Connecting To Server " + Address + ":" + Port); - Socket socket = new Socket(); - SocketAddress address = new InetSocketAddress(Address, Port); - socket.connect(address, 5000); - Log.info("Connected to Server!"); - socket.setKeepAlive(true); - return socket; - } catch (SocketTimeoutException e) { - Log.warn("Connection timed out!"); - return null; - } catch (Exception e) { - Log.err("Failed to Connect to Server!"); - return null; - } - } + public static final String NAME_TERMINATOR = "\uffff"; + public static final String MESSAGE_TERMINATOR = "\ufffe"; + public static int PortVoIP = 49190; + public static int PortText = 49180; public static void disconnectFromServer(Socket socket) { try { diff --git a/client/src/main/java/net/xircon/xenon/client/networking/textclient/TextClient.java b/client/src/main/java/net/xircon/xenon/client/networking/textclient/TextClient.java index 736d8f1..bbff71c 100644 --- a/client/src/main/java/net/xircon/xenon/client/networking/textclient/TextClient.java +++ b/client/src/main/java/net/xircon/xenon/client/networking/textclient/TextClient.java @@ -1,33 +1,73 @@ package net.xircon.xenon.client.networking.textclient; import net.xircon.xenon.client.io.Log; +import net.xircon.xenon.client.networking.Networking; +import javax.annotation.Nullable; import java.io.BufferedReader; import java.io.IOException; import java.io.InputStreamReader; import java.io.PrintWriter; +import java.net.InetSocketAddress; import java.net.Socket; +import java.net.SocketAddress; +import java.net.SocketTimeoutException; public class TextClient implements Runnable { - private final String nameTerminator = "\uffff"; private String nickname; - private String message; - private Socket socket; + public static String messageBuffer = ""; + private String address; + public static Socket socket; - public TextClient(Socket serverSocket, String nickname, String message) { - this.socket = serverSocket; this.message = message; this.nickname = nickname; + public TextClient(String address, String nickname) { + this.address = address; this.nickname = nickname; } @Override public void run() { try { - BufferedReader input = new BufferedReader(new InputStreamReader(socket.getInputStream())); + socket = connectToServer(address, Networking.PortText); + assert socket != null; + +// BufferedReader input = new BufferedReader(new InputStreamReader(socket.getInputStream())); +// PrintWriter output = new PrintWriter(socket.getOutputStream(), true); +// output.println(nickname + Networking.NAME_TERMINATOR + messageBuffer + Networking.MESSAGE_TERMINATOR); +// String messageFromServer = input.readLine(); +// Log.info("Server Message: " + messageFromServer); PrintWriter output = new PrintWriter(socket.getOutputStream(), true); - output.println(nickname + nameTerminator + message); - String messageFromServer = input.readLine(); - Log.info("Server Message: " + messageFromServer); - } catch (IOException e) { - Log.warn("Could not Read/Send Message!"); + BufferedReader input = new BufferedReader(new InputStreamReader(socket.getInputStream())); + while(socket.isConnected()) { + if (!messageBuffer.isEmpty()) { + output.println(nickname + Networking.NAME_TERMINATOR + messageBuffer + Networking.MESSAGE_TERMINATOR); + Log.info("Sending! " + nickname + Networking.NAME_TERMINATOR + messageBuffer + Networking.MESSAGE_TERMINATOR); + messageBuffer = new String(); + String messageFromServer = input.readLine(); + Log.info("Server Message: " + messageFromServer); + } else { + Thread.sleep(500); + } + } + } catch (IOException | InterruptedException e) { + Log.warn("Could not Read/Send Data!"); + } + } + + @Nullable + private static Socket connectToServer(String Address, int Port) { + try { + Log.info("Connecting To Server " + Address + ":" + Port); + Socket socket = new Socket(); + SocketAddress address = new InetSocketAddress(Address, Port); + socket.connect(address, 5000); + socket.setKeepAlive(true); + Log.info("Connected to Server!"); + return socket; + } catch (SocketTimeoutException e) { + Log.warn("Connection timed out!"); + return null; + } catch (Exception e) { + Log.err("Failed to Connect to Server!"); + return null; } } } diff --git a/server/src/main/java/net/xircon/xenon/server/Xenon.java b/server/src/main/java/net/xircon/xenon/server/Xenon.java index 09a1189..e28bae4 100644 --- a/server/src/main/java/net/xircon/xenon/server/Xenon.java +++ b/server/src/main/java/net/xircon/xenon/server/Xenon.java @@ -8,19 +8,17 @@ import java.io.IOException; import java.net.*; import java.util.Objects; +import static net.xircon.xenon.server.networking.Networking.*; + //import java.net. public class Xenon implements Runnable { private Thread serverThread; public static void main(String[] args) {new Xenon().start();} - private ServerSocket textServerSocket; - private static final String propertiesFile = "server.properties"; // Sever Properties - public static String ServerName = "Xenon Test Server"; - public static int PortVoIP = 49190; - public static int PortText = 49180; + public void start() { serverThread = new Thread(this, "serverThread"); @@ -44,8 +42,7 @@ public class Xenon implements Runnable { Log.err("IOException Whilst Fetching External IP! {" + e + "}"); } Log.info("Server Name is " + '"' + ServerName + '"'); - textServerSocket = Networking.createTextServer(PortText); - TextServer textServer = new TextServer(textServerSocket); + TextServer textServer = new TextServer(); Thread textServerThread = new Thread(textServer); textServerThread.start(); } diff --git a/server/src/main/java/net/xircon/xenon/server/io/database/Database.java b/server/src/main/java/net/xircon/xenon/server/io/database/Database.java new file mode 100644 index 0000000..96a8265 --- /dev/null +++ b/server/src/main/java/net/xircon/xenon/server/io/database/Database.java @@ -0,0 +1,54 @@ +package net.xircon.xenon.server.io.database; + +import net.xircon.xenon.server.io.Log; +import net.xircon.xenon.server.io.Util; + +import java.io.File; +import java.io.FileWriter; +import java.io.IOException; +import java.util.Objects; + +public class Database { + private static String DatabaseLocation = null; + public static final String NAME_TERMINATOR = "\uffff"; + public static final String MESSAGE_TERMINATOR = "\ufffe"; + + static class DatabaseData { + String name; + String message; + int time; + } + + public static void create() { + DatabaseLocation = Util.GetProperties("server.properties", "DatabaseLocation", Util.PROPERTY_TYPE_STRING).stringValue; + if (DatabaseLocation == null | Objects.equals(DatabaseLocation, "")) { + Log.err("Database Location was Null/Empty!"); + } else { + File database = new File(DatabaseLocation); + Log.info("Creating a New Database"); + try { + if (!database.createNewFile()) { + Log.warn("Database Already Exists"); + } + } catch (IOException e) { + Log.err("Could Not Create Database!"); + } + } + } + public static void write(String data) { + try { + assert DatabaseLocation != null; + File database = new File(DatabaseLocation); + if (database.exists() && database.canWrite()) { + FileWriter databaseWriter = new FileWriter(DatabaseLocation, true); + databaseWriter.write(data); + databaseWriter.close(); + } + } catch (IOException e) { + Log.err("Database Could not be Written to!"); + } + } + public static void read() { + + } +} diff --git a/server/src/main/java/net/xircon/xenon/server/networking/Networking.java b/server/src/main/java/net/xircon/xenon/server/networking/Networking.java index 1e50d1b..ee725ae 100644 --- a/server/src/main/java/net/xircon/xenon/server/networking/Networking.java +++ b/server/src/main/java/net/xircon/xenon/server/networking/Networking.java @@ -1,21 +1,7 @@ package net.xircon.xenon.server.networking; -import net.xircon.xenon.server.io.Log; - -import javax.annotation.Nullable; -import java.io.IOException; -import java.net.ServerSocket; - public class Networking { - @Nullable - public static ServerSocket createTextServer(int Port) { - try { - ServerSocket serverSocket = new ServerSocket(Port); - Log.info("Text Server Waiting For Clients"); - return serverSocket; - } catch (IOException e) { - Log.info("Failed to Create Text Server!"); - return null; - } - } + public static String ServerName = "Xenon Test Server"; + public static int PortVoIP = 49190; + public static int PortText = 49180; } diff --git a/server/src/main/java/net/xircon/xenon/server/networking/textserver/ClientHandler.java b/server/src/main/java/net/xircon/xenon/server/networking/textserver/ClientHandler.java index ed69636..f738fac 100644 --- a/server/src/main/java/net/xircon/xenon/server/networking/textserver/ClientHandler.java +++ b/server/src/main/java/net/xircon/xenon/server/networking/textserver/ClientHandler.java @@ -1,6 +1,7 @@ package net.xircon.xenon.server.networking.textserver; import net.xircon.xenon.server.io.Log; +import net.xircon.xenon.server.io.database.Database; import java.io.BufferedReader; import java.io.IOException; @@ -9,7 +10,7 @@ import java.io.PrintWriter; import java.net.Socket; public class ClientHandler implements Runnable { - private Socket clientSocket; + private final Socket clientSocket; public ClientHandler(Socket clientSocket) { this.clientSocket = clientSocket; @@ -17,14 +18,16 @@ public class ClientHandler implements Runnable { @Override public void run() { - try { + while (clientSocket.isConnected()) try { BufferedReader input = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); - PrintWriter output = output = new PrintWriter(clientSocket.getOutputStream(), true); + PrintWriter output = new PrintWriter(clientSocket.getOutputStream(), true); String message = input.readLine(); - String namedMessage[] = message.split("\uffff", -1); + String[] namedMessage = message.split(Database.NAME_TERMINATOR, -1); Log.info("<" + namedMessage[0] + "> " + namedMessage[1]); + Database.write(message); output.println("Server Received Message!"); clientSocket.setKeepAlive(true); + } catch (IOException e) { Log.warn("Could not Read Message From Client"); } diff --git a/server/src/main/java/net/xircon/xenon/server/networking/textserver/TextServer.java b/server/src/main/java/net/xircon/xenon/server/networking/textserver/TextServer.java index 326147a..05bd3a8 100644 --- a/server/src/main/java/net/xircon/xenon/server/networking/textserver/TextServer.java +++ b/server/src/main/java/net/xircon/xenon/server/networking/textserver/TextServer.java @@ -1,7 +1,10 @@ package net.xircon.xenon.server.networking.textserver; import net.xircon.xenon.server.io.Log; +import net.xircon.xenon.server.io.database.Database; +import net.xircon.xenon.server.networking.Networking; +import javax.annotation.Nullable; import java.io.IOException; import java.net.ServerSocket; import java.net.Socket; @@ -9,23 +12,32 @@ import java.net.Socket; public class TextServer implements Runnable { private ServerSocket mainServerSocket; - public TextServer(ServerSocket serverSocket) { - this.mainServerSocket = serverSocket; - } + public TextServer() {} @Override public void run() { - while (true) { - try { - Socket clientSocket = mainServerSocket.accept(); - Log.info("Client Connected: " + clientSocket); - ClientHandler clientHandler = new ClientHandler(clientSocket); - Thread thread = new Thread(clientHandler); - thread.start(); - } catch (IOException e) { - Log.err("Text Server Did not correctly Accept a Client!"); - } + mainServerSocket = createTextServer(Networking.PortText); + Database.create(); + while (true) try { + Socket clientSocket = mainServerSocket.accept(); + Log.info("Client Connected: " + clientSocket); + ClientHandler clientHandler = new ClientHandler(clientSocket); + Thread thread = new Thread(clientHandler); + thread.start(); + } catch (IOException e) { + Log.err("Text Server Did not correctly Accept a Client!"); + } + } + @Nullable + public static ServerSocket createTextServer(int Port) { + try { + ServerSocket serverSocket = new ServerSocket(Port); + Log.info("Text Server Waiting For Clients"); + return serverSocket; + } catch (IOException e) { + Log.info("Failed to Create Text Server!"); + return null; } } } diff --git a/server/src/main/resources/server.properties b/server/src/main/resources/server.properties index b61e188..2e51fc7 100644 --- a/server/src/main/resources/server.properties +++ b/server/src/main/resources/server.properties @@ -1,4 +1,5 @@ # Server.properties PortText=49180 PortVoIP=49190 -ServerName=Xircon's Test Server \ No newline at end of file +ServerName=Xircon's Test Server +DatabaseLocation=server.db \ No newline at end of file