Skip to content

Commit d9f8a6e

Browse files
committed
Enhanced Exception Handling and Improved Server Performance
Made the client stop using Thread.interrupt Modified most of the classes to properly throw exceptions so the user can handle them accordingly Added IOException throwing to PacketReader Replaced List of sockets in Server with LinkedHashSet and added ExecutorService for tcp handling
1 parent 2953854 commit d9f8a6e

8 files changed

Lines changed: 113 additions & 167 deletions

File tree

pom.xml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66

77
<groupId>xyz.synse</groupId>
88
<artifactId>PacketNet</artifactId>
9-
<version>1.1</version>
9+
<version>1.2</version>
1010

1111
<properties>
1212
<maven.compiler.source>20</maven.compiler.source>

src/main/java/xyz/synse/packetnet/client/Client.java

Lines changed: 42 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -18,9 +18,10 @@ public class Client {
1818
private final List<IClientListener> listeners = new ArrayList<>();
1919
private Socket tcpSocket;
2020
private DatagramSocket udpSocket;
21-
22-
public Client(int bufferSize){
21+
private Thread tcpThread;
22+
private Thread udpThread;
2323

24+
public Client(int bufferSize) {
2425
this.bufferSize = bufferSize;
2526
}
2627

@@ -39,13 +40,13 @@ public void connect(String serverAddress, int tcpPort, int udpPort) throws IOExc
3940

4041
// Init tcp
4142
tcpSocket = new Socket(serverAddress, tcpPort);
42-
Thread tcpThread = new Thread(this::startTcpListener);
43+
tcpThread = new Thread(this::startTcpListener);
4344
tcpThread.start();
4445

4546
udpListenerRunning = true;
4647
// Init udp
4748
udpSocket = new DatagramSocket();
48-
Thread udpThread = new Thread(this::startUdpListener);
49+
udpThread = new Thread(this::startUdpListener);
4950
udpThread.start();
5051

5152
// Notify listeners about the connection
@@ -55,22 +56,38 @@ public void connect(String serverAddress, int tcpPort, int udpPort) throws IOExc
5556
/**
5657
* Disconnects the client from the server.
5758
*/
58-
public void disconnect() {
59-
if (tcpSocket != null) {
60-
try (Socket socket = tcpSocket) {
61-
// No need to manually set tcpSocket to null
62-
} catch (IOException e) {
63-
e.printStackTrace();
64-
}
59+
public void disconnect() throws IOException {
60+
if (tcpSocket != null && !tcpSocket.isClosed()) {
61+
tcpSocket.close();
6562
tcpSocket = null;
6663
}
6764

68-
if (udpSocket != null) {
65+
if (udpSocket != null && !udpSocket.isClosed()) {
6966
udpSocket.close();
7067
udpListenerRunning = false;
7168
udpSocket = null;
7269
}
7370

71+
if (tcpThread != null) {
72+
tcpThread.interrupt();
73+
try {
74+
tcpThread.join();
75+
} catch (InterruptedException e) {
76+
// Handle the interrupted exception if required
77+
}
78+
tcpThread = null;
79+
}
80+
81+
if (udpThread != null) {
82+
udpThread.interrupt();
83+
try {
84+
udpThread.join();
85+
} catch (InterruptedException e) {
86+
// Handle the interrupted exception if required
87+
}
88+
udpThread = null;
89+
}
90+
7491
// Notify listeners about the disconnection
7592
listeners.forEach(IClientListener::onDisconnected);
7693
}
@@ -103,6 +120,7 @@ private void startTcpListener() {
103120
listeners.forEach(iClientListener -> iClientListener.onReceived(ProtocolType.TCP, packet));
104121
}
105122
} catch (SocketException ignored) {
123+
106124
} catch (IOException e) {
107125
e.printStackTrace();
108126
}
@@ -120,6 +138,7 @@ private void startUdpListener() {
120138
Packet constructedPacket = Packet.fromByteArray(data);
121139
listeners.forEach(iClientListener -> iClientListener.onReceived(ProtocolType.UDP, constructedPacket));
122140
} catch (SocketException ignored) {
141+
123142
} catch (IOException e) {
124143
e.printStackTrace();
125144
}
@@ -132,38 +151,30 @@ private void startUdpListener() {
132151
* @param packet The packet to send.
133152
* @param protocol The protocol to use (TCP or UDP).
134153
*/
135-
public void send(Packet packet, ProtocolType protocol) {
154+
public void send(Packet packet, ProtocolType protocol) throws IOException {
136155
switch (protocol) {
137156
case TCP -> sendTcp(packet);
138157
case UDP -> sendUdp(packet);
139158
default -> System.out.println("Unsupported protocol: " + protocol);
140159
}
141160
}
142161

143-
private void sendTcp(Packet packet) {
162+
private void sendTcp(Packet packet) throws IOException {
144163
if (tcpSocket != null) {
145-
try {
146-
byte[] data = packet.toByteArray();
147-
tcpSocket.getOutputStream().write(data);
164+
byte[] data = packet.toByteArray();
165+
tcpSocket.getOutputStream().write(data);
148166

149-
listeners.forEach(listener -> listener.onSent(ProtocolType.TCP, packet));
150-
} catch (IOException e) {
151-
e.printStackTrace();
152-
}
167+
listeners.forEach(listener -> listener.onSent(ProtocolType.TCP, packet));
153168
}
154169
}
155170

156-
private void sendUdp(Packet packet) {
171+
private void sendUdp(Packet packet) throws IOException {
157172
if (udpSocket != null) {
158-
try {
159-
byte[] data = packet.toByteArray();
160-
DatagramPacket datagramPacket = new DatagramPacket(data, data.length, serverAddress, udpPort);
161-
udpSocket.send(datagramPacket);
173+
byte[] data = packet.toByteArray();
174+
DatagramPacket datagramPacket = new DatagramPacket(data, data.length, serverAddress, udpPort);
175+
udpSocket.send(datagramPacket);
162176

163-
listeners.forEach(listener -> listener.onSent(ProtocolType.UDP, packet));
164-
} catch (IOException e) {
165-
e.printStackTrace();
166-
}
177+
listeners.forEach(listener -> listener.onSent(ProtocolType.UDP, packet));
167178
}
168179
}
169180

@@ -193,4 +204,4 @@ public int getUdpPort() {
193204
public InetAddress getServerAddress() {
194205
return serverAddress;
195206
}
196-
}
207+
}
Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
package xyz.synse.packetnet.common.compression;
22

3+
import java.io.IOException;
4+
35
public interface ICompressor {
4-
byte[] compress(byte[] data);
5-
byte[] decompress(byte[] data);
6+
byte[] compress(byte[] data) throws IOException;
7+
byte[] decompress(byte[] data) throws IOException;
68
}

src/main/java/xyz/synse/packetnet/common/compression/PacketCompressor.java

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,16 +4,18 @@
44
import xyz.synse.packetnet.common.compression.compressors.LZ4Compressor;
55
import xyz.synse.packetnet.common.packets.Packet;
66

7+
import java.io.IOException;
8+
79
public class PacketCompressor {
810
public static final ICompressor GZIP_COMPRESSOR = new GZipCompressor();
911
public static final ICompressor LZ4_COMPRESSOR = new LZ4Compressor();
1012

11-
public static Packet decompress(Packet packet, ICompressor compressor) {
13+
public static Packet decompress(Packet packet, ICompressor compressor) throws IOException {
1214
byte[] decompressed = compressor.decompress(packet.getData());
1315
return new Packet(packet.getID(), decompressed);
1416
}
1517

16-
public static Packet compress(Packet packet, ICompressor compressor) {
18+
public static Packet compress(Packet packet, ICompressor compressor) throws IOException {
1719
byte[] compressed = compressor.compress(packet.getData());
1820
return new Packet(packet.getID(), compressed);
1921
}

src/main/java/xyz/synse/packetnet/common/compression/compressors/GZipCompressor.java

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,18 +10,16 @@
1010

1111
public class GZipCompressor implements ICompressor {
1212
@Override
13-
public byte[] compress(byte[] data) {
13+
public byte[] compress(byte[] data) throws IOException {
1414
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
1515
try (GZIPOutputStream gzipOutputStream = new GZIPOutputStream(byteArrayOutputStream)) {
1616
gzipOutputStream.write(data);
17-
} catch (IOException e) {
18-
throw new RuntimeException(e);
1917
}
2018
return byteArrayOutputStream.toByteArray();
2119
}
2220

2321
@Override
24-
public byte[] decompress(byte[] compressedData) {
22+
public byte[] decompress(byte[] compressedData) throws IOException {
2523
ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream(compressedData);
2624
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
2725
try (GZIPInputStream gzipInputStream = new GZIPInputStream(byteArrayInputStream)) {
@@ -30,8 +28,6 @@ public byte[] decompress(byte[] compressedData) {
3028
while ((bytesRead = gzipInputStream.read(buffer)) != -1) {
3129
byteArrayOutputStream.write(buffer, 0, bytesRead);
3230
}
33-
} catch (IOException e) {
34-
throw new RuntimeException(e);
3531
}
3632
return byteArrayOutputStream.toByteArray();
3733
}

src/main/java/xyz/synse/packetnet/common/compression/compressors/LZ4Compressor.java

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88

99
public class LZ4Compressor implements ICompressor {
1010
@Override
11-
public byte[] compress(byte[] data) {
11+
public byte[] compress(byte[] data) throws IOException {
1212
try (
1313
ByteArrayOutputStream byteOut = new ByteArrayOutputStream();
1414
DataOutputStream dataOut = new DataOutputStream(byteOut);
@@ -22,13 +22,11 @@ public byte[] compress(byte[] data) {
2222
}
2323

2424
return byteOut.toByteArray();
25-
} catch (IOException ex) {
26-
throw new RuntimeException(ex);
2725
}
2826
}
2927

3028
@Override
31-
public byte[] decompress(byte[] data) {
29+
public byte[] decompress(byte[] data) throws IOException {
3230
try (
3331
ByteArrayInputStream byteIn = new ByteArrayInputStream(data);
3432
DataInputStream dataIn = new DataInputStream(byteIn);
@@ -42,8 +40,6 @@ public byte[] decompress(byte[] data) {
4240
outStream.read(restored);
4341
return restored;
4442
}
45-
} catch (IOException ex) {
46-
throw new RuntimeException(ex);
4743
}
4844
}
4945
}

src/main/java/xyz/synse/packetnet/common/packets/PacketReader.java

Lines changed: 25 additions & 69 deletions
Original file line numberDiff line numberDiff line change
@@ -14,95 +14,51 @@ public PacketReader(Packet packet) {
1414
this.in = new DataInputStream(byteIn);
1515
}
1616

17-
public byte[] readBytes() {
18-
try {
19-
int size = in.readInt();
20-
return in.readNBytes(size);
21-
} catch (IOException e) {
22-
throw new RuntimeException(e);
23-
}
17+
public byte[] readBytes() throws IOException {
18+
int size = in.readInt();
19+
return in.readNBytes(size);
2420
}
2521

26-
public byte[] readBytes(int len) {
27-
try {
28-
return in.readNBytes(len);
29-
} catch (IOException e) {
30-
throw new RuntimeException(e);
31-
}
22+
public byte[] readBytes(int len) throws IOException {
23+
return in.readNBytes(len);
3224
}
3325

34-
public byte readByte() {
35-
try {
36-
return in.readByte();
37-
} catch (IOException e) {
38-
throw new RuntimeException(e);
39-
}
26+
public byte readByte() throws IOException {
27+
return in.readByte();
4028
}
4129

42-
public boolean readBoolean() {
43-
try {
44-
return in.readBoolean();
45-
} catch (IOException e) {
46-
throw new RuntimeException(e);
47-
}
30+
public boolean readBoolean() throws IOException {
31+
return in.readBoolean();
4832
}
4933

50-
public String readString() {
51-
try {
52-
return in.readUTF();
53-
} catch (IOException e) {
54-
throw new RuntimeException(e);
55-
}
34+
public String readString() throws IOException {
35+
return in.readUTF();
5636
}
5737

58-
public int readInt() {
59-
try {
60-
return in.readInt();
61-
} catch (IOException e) {
62-
throw new RuntimeException(e);
63-
}
38+
public int readInt() throws IOException {
39+
return in.readInt();
6440
}
6541

66-
public long readLong() {
67-
try {
68-
return in.readLong();
69-
} catch (IOException e) {
70-
throw new RuntimeException(e);
71-
}
42+
public long readLong() throws IOException {
43+
return in.readLong();
7244
}
7345

74-
public float readFloat() {
75-
try {
76-
return in.readFloat();
77-
} catch (IOException e) {
78-
throw new RuntimeException(e);
79-
}
46+
public float readFloat() throws IOException {
47+
return in.readFloat();
8048
}
8149

82-
public double readDouble() {
83-
try {
84-
return in.readDouble();
85-
} catch (IOException e) {
86-
throw new RuntimeException(e);
87-
}
50+
public double readDouble() throws IOException {
51+
return in.readDouble();
8852
}
8953

90-
public short readShort() {
91-
try {
92-
return in.readShort();
93-
} catch (IOException e) {
94-
throw new RuntimeException(e);
95-
}
54+
public short readShort() throws IOException {
55+
return in.readShort();
9656
}
9757

98-
public UUID readUUID() {
99-
try {
100-
long mostSignificantBits = in.readLong();
101-
long leastSignificantBits = in.readLong();
102-
return new UUID(mostSignificantBits, leastSignificantBits);
103-
} catch (IOException e) {
104-
throw new RuntimeException(e);
105-
}
58+
public UUID readUUID() throws IOException {
59+
long mostSignificantBits = in.readLong();
60+
long leastSignificantBits = in.readLong();
61+
return new UUID(mostSignificantBits, leastSignificantBits);
10662
}
10763

10864
@Override

0 commit comments

Comments
 (0)