client/server only reading one message? - java

my client/server works perfectly for one message, then no matter what's next it says it's blank.
I believe the problem resolves in here or my commands class:
package MyServer;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.Socket;
import java.net.UnknownHostException;
public class Main {
public static String line;
public static void main(String[] args){
while(true){
try {
//Creates a socket to receive commands from!
Socket socket = new Socket("localhost", 7586);
//Uses that socket to create a Reader to read the commands!
BufferedReader in = new BufferedReader(new InputStreamReader(socket.getInputStream()));
//Waits for Lines to be sent and then executes them!
while(true){
line = in.readLine();
if(line != null){
Commands.ReceiveCommand();
}else {
break;
}
}
} catch (UnknownHostException e){
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
or in my commands:
package MyServer;
import javax.swing.JOptionPane;
public class Commands {
static String command = (Main.line).toString(); //<--This was the problem, just had to move it into the method below.
public static void ReceiveCommand(){
if(command.equals("test")){
JOptionPane.showMessageDialog(null,"works","command: " + command,JOptionPane.WARNING_MESSAGE);
//System.out.println("WORKEDS MOFO");
command = "";
}else{
JOptionPane.showMessageDialog(null,"not recognized","command: " + command,JOptionPane.WARNING_MESSAGE);
//System.out.println("no bueno");
//System.out.println("line is " + command);
command = "";
}
}
}
Edit: For some reason when debugging, command is just blank no matter what after it's been used once, so it might be in my main server class:
package MyClient;
import java.util.List;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.ArrayList;
public class Main {
//Sets the Port
final static int PORT = 7591;
//Creates a list of Connected Clients
static List<Socket> connectedClients = new ArrayList<Socket>();
public static void main(String[] args){
//Creates a Thread to Send Messages to connectedClients
new Thread(new messageThread()).start();
try {
//Creates the ServerSocket
ServerSocket serverSocket = new ServerSocket(PORT);
while(true){
//Waits for a Connection and Accepts it...
Socket clientSocket = serverSocket.accept();
System.out.println("A Client has connected!");
//Adds it to the List
connectedClients.add(clientSocket);
}
} catch (IOException e) {
e.printStackTrace();
}
} }
and the messageThread:
package MyClient;
import java.io.IOException;
import java.io.PrintWriter;
import java.net.Socket;
import java.util.Scanner;
public class messageThread implements Runnable {
public void run() {
while(true){
System.out.println(">>");
Scanner in = new Scanner(System.in);
String command = in.nextLine();
for(Socket clientToSendCommand : Main.connectedClients){
try {
PrintWriter commandWriter = new PrintWriter(clientToSendCommand.getOutputStream());
commandWriter.println(command);
commandWriter.flush();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}

This dosen't work, because th line
static String command = (Main.line).toString();
in the Commands-class is executed exactly once, when the Commands-class is first referenced.
When the second command is send, the class was already referenced, so this line is not executed again.
To solve this put the line inside the method, or - much better - pass it as a parameter to the method.
P.S.: Have you mixed up the packages? The class with the ServerSocket should be the server and thus be in the MyServer package. :-)

Related

How to handle multiple streams from a lobby server to clients

So, I'm having an issue with a project of mine. I'm writing a multiplayer lobby system which will enable multiple users to join a lobby, readying themselves by pressing a key. The issue that I'm facing is when two players is readying themselves, the lobby is only printing out a message for the last player who readied themselves. The system is built up in the following way.
Main Server
package master;
import java.net.*;
import java.io.*;
import java.util.*;
import java.io.*;
import java.net.InetAddress;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.Date;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.ArrayList;
import main.Lobby;
public class MainServer {
public static final int PORT = 4444;
public static final String HOST = "localhost";
public ArrayList<Lobby> serverList = new ArrayList<>();
public static void main(String[] args) throws IOException, ClassNotFoundException {
new MainServer().runServer();
}
public void runServer() throws IOException, ClassNotFoundException {
// Creating the server
ServerSocket serverSocket = new ServerSocket(PORT);
System.out.println("Main Server initiated.");
while (true) {
Socket socket = serverSocket.accept();
try {
// Establishing the connection to the Lobby server and then adding it to its list
ObjectInputStream objectInputStream = new ObjectInputStream(socket.getInputStream());
ObjectOutputStream objectOutputStream = new ObjectOutputStream(socket.getOutputStream());
objectOutputStream.writeObject("Server created successfully.");
Lobby s = (Lobby) objectInputStream.readObject();
this.serverList.add(s);
System.out.println("Server \"" + s.name + "\" added to game list.");
} catch (IOException e) {
e.printStackTrace();
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
}
}
The lobby
package main;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.net.ServerSocket;
import java.net.Socket;
import java.net.UnknownHostException;
import java.util.concurrent.Semaphore;
import master.MainServer;
/**
* The Class Server.
*/
public class Lobby implements Serializable {
private static final long serialVersionUID = -21654L;
public static final int PORT = 4445;
public static final int MAX_USERS = 5000;
public static final String HOST = "localhost";
public String name = "Lobby Server";
public int clientNumber;
public int playerNumberReady = 0;
public boolean allPlayersReady = false;
public boolean OddurIsNice = false;
public static void main(String[] args) throws IOException, ClassNotFoundException {
Lobby s = new Lobby();
s.runServer();
}
public void runServer() throws IOException, ClassNotFoundException {
registerServer();
new Thread( () -> {
try {
ServerSocket serverSocket = new ServerSocket(PORT);
System.out.println("Server waiting for connections...");
while (true) {
Socket socket = serverSocket.accept();
System.out.println("User 1 is now connected");
clientNumber++;
new ObjectOutputStream(socket.getOutputStream()).writeObject("You are connected man");
Socket socket2 = serverSocket.accept();
System.out.println("User 2 is now connected");
clientNumber++;
// ObjectOutputStream objectOutputStream2 = new ObjectOutputStream(socket2.getOutputStream());
// objectOutputStream2.writeObject("You are player number " + clientNumber + ". Waiting for other players to join");
new ServerThread(socket, socket2).start();
}
} catch (IOException ex) {
ex.printStackTrace();
}
}).start();
}
private void registerServer() throws UnknownHostException, IOException, ClassNotFoundException {
// Method for establishing a connection to the MainServer
Socket socket = new Socket(MainServer.HOST, MainServer.PORT);
ObjectOutputStream objectOutputStream = new ObjectOutputStream(socket.getOutputStream());
ObjectInputStream objectInputStream = new ObjectInputStream(socket.getInputStream());
objectOutputStream.writeObject(this);
System.out.println((String) objectInputStream.readObject());
}
public class ServerThread extends Thread {
public Socket socket = null;
public Socket socket2 = null;
ServerThread(Socket socket, Socket socket2) {
this.socket = socket;
this.socket2 = socket2;
}
public void run() {
try {
// This method is for when the client want's to connect to the lobby
ObjectInputStream objectInputStream = new ObjectInputStream(socket.getInputStream());
ObjectOutputStream objectOutputStream = new ObjectOutputStream(socket.getOutputStream());
System.out.println("User 1 is now connected");
ObjectInputStream objectInputStream2 = new ObjectInputStream(socket2.getInputStream());
ObjectOutputStream objectOutputStream2 = new ObjectOutputStream(socket2.getOutputStream());
System.out.println("User 2 is now connected");
BoardGameClient joined = (BoardGameClient) objectInputStream.readObject();
System.out.println(joined.name + " is now connected.");
while(true) {
objectOutputStream.writeObject("You joined the server.");
objectOutputStream.writeObject("You are player Number " + 1);
objectOutputStream.writeObject("Press '1' if you are ready");
objectOutputStream2.writeObject("You joined the server.");
objectOutputStream2.writeObject("You are player Number " + 2);
objectOutputStream2.writeObject("Press '1' if you are ready");
if(objectInputStream.readObject().equals(1)) {
playerNumberReady++;
}
if(objectInputStream2.readObject().equals(1)) {
playerNumberReady++;
}
if(playerNumberReady != 2) {
allPlayersReady = false;
} else {
allPlayersReady = true;
}
if (allPlayersReady == false) {
objectOutputStream.writeObject("Waiting...");
objectOutputStream2.writeObject("Waiting...");
}
if (allPlayersReady == true) {
objectOutputStream.writeObject("Lets GO");
objectOutputStream2.writeObject("Lets GO");
}
while (true) {
System.out.println(objectInputStream.readObject());
}
}
} catch (ClassNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
And the client
package main;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.net.Socket;
import java.net.UnknownHostException;
import java.util.Scanner;
import java.util.concurrent.Semaphore;
import master.MainServer;
public class BoardGameClient implements Serializable {
private int playerName;
private static final long serialVersionUID = -6224L;
public String name = "User";
private transient Socket socket;
public transient Scanner input = new Scanner(System.in);
public static void main(String[] args) {
BoardGameClient c = new BoardGameClient();
if (args.length > 0) {
c.name = args[0];
}
try {
c.joinServer();
} catch (ClassNotFoundException | IOException e) {
System.out.println("Failed to join server.");
e.printStackTrace();
}
}
public void joinServer() throws UnknownHostException, IOException, ClassNotFoundException {
socket = new Socket(Lobby.HOST, Lobby.PORT);
ObjectOutputStream objectOutputStream = new ObjectOutputStream(socket.getOutputStream());
ObjectInputStream objectInputStream = new ObjectInputStream(socket.getInputStream());
while(true) {
objectOutputStream.writeObject(this);
BufferedReader inputReader = new BufferedReader(new InputStreamReader(System.in));
System.out.println(objectInputStream.readObject());
System.out.println(objectInputStream.readObject());
System.out.println(objectInputStream.readObject());
int ready = input.nextInt();
objectOutputStream.writeObject(ready);
System.out.println(objectInputStream.readObject());
objectOutputStream.writeObject(name + ": " + inputReader.readLine());
}
}
}
I sincerely hope, that someone will be able to help me out <3
Firstly, there's a few things that bug me about this code. Not to sound condescending but you need to avoid rewriting code as much as possible. What happens if you want 3 or more players in the future? Currently you'd have to manually create a whole socket eg socket3, and then rewrite all the code you've already written. This is bad. You've manually spent the time creating 2 sockets and then created 2 streams for both of these sockets etc etc.
This can be automated don't you think?
Secondly, you have a lot of public variables. Unless they are static and final, for the most part you should keep variables as private.
I've tinkered with your lobby class as seen below, which is more scalable. It's not perfect by any means, but I feel illustrates the direction of improvement you should be heading for. Look up SOLID OOP principles, they'll help you guaranteed.
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.net.ServerSocket;
import java.net.Socket;
import java.net.UnknownHostException;
import java.util.LinkedHashSet;
import java.util.Set;
/**
* The Class Server.
*/
public class Lobby implements Serializable {
private static final long serialVersionUID = -21654L;
public static final int PORT = 4445;
public static final int MAX_USERS = 5000;
public static final String HOST = "localhost";
private static final int MIN_USERS = 2;
private String name = "Lobby Server";
private int clientNumber;
private boolean gameRunning = false;
// set of client connections
private final Set<ServerThread> clientConnectionThreads = new LinkedHashSet<>();
public static void main(String[] args) throws IOException, ClassNotFoundException {
Lobby s = new Lobby();
s.createLobby();
}
public void createLobby() throws IOException, ClassNotFoundException {
// waits for all players to ready up in a different thread
new Thread(this::waitReady).start();
registerServer();
// Listens for clients
runServer();
}
public void runServer() {
// closes serverSocket automatically in this way
try (ServerSocket serverSocket = new ServerSocket(PORT)) {
System.out.println("Server waiting for connections...");
long ids = 0;
while (!gameRunning) {
// accepts a new client connection
Socket socket = serverSocket.accept();
if (clientConnectionThreads.size() >= MAX_USERS) {
// tell user server is full and dont add the connection
} else {
// calculates the new id of the incoming player and adds them to the lobby
ids++;
this.clientConnectionThreads.add(new ServerThread(ids, socket));
System.out.println("User " + ids + " is now connected");
}
}
} catch (IOException ex) {
ex.printStackTrace();
}
}
/*
* loops until every player is ready and there is enough players and then starts
* the game.
*/
public void waitReady() {
while (true) {
try {
if (areAllReady() && this.clientConnectionThreads.size() >= MIN_USERS) {
startGame();
return;
}
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
// returns true if all users are ready
public boolean areAllReady() {
return clientConnectionThreads.stream().allMatch(ServerThread::isReady);
}
public void startGame() {
System.out.println("Starting game...");
this.gameRunning = true;
clientConnectionThreads.forEach(ServerThread::startGame);
// do game stuff
}
// i havent touched this function
private void registerServer() throws UnknownHostException, IOException, ClassNotFoundException {
// Method for establishing a connection to the MainServer
Socket socket = new Socket(MainServer.HOST, MainServer.PORT);
ObjectOutputStream objectOutputStream = new ObjectOutputStream(socket.getOutputStream());
ObjectInputStream objectInputStream = new ObjectInputStream(socket.getInputStream());
objectOutputStream.writeObject(this);
System.out.println((String) objectInputStream.readObject());
}
public class ServerThread extends Thread {
private final Socket socket;
private final ObjectInputStream in;
private final ObjectOutputStream out;
private final long id;
boolean ready = false;
private ServerThread(long id, Socket socket) throws IOException {
// does some basic initialization
this.socket = socket;
this.id = id;
in = new ObjectInputStream(socket.getInputStream());
out = new ObjectOutputStream(socket.getOutputStream());
// starts this connection thread
this.start();
}
public boolean isReady() {
return ready;
}
public void run() {
try {
// sets up the client and waits for their input
BoardGameClient joined = (BoardGameClient) in.readObject();
System.out.println(joined.name + " is now connected.");
out.writeObject("You joined the server.");
out.writeObject("You are player Number " + id);
out.writeObject("Press '1' if you are ready");
out.flush();
// waits for user to return ready
while (!ready) {
try {
int input = in.readInt();
System.out.println("input: " + input);
ready = input == 1;
} catch (ClassCastException e) {
e.printStackTrace();
}
}
out.writeObject("Waiting for players...");
} catch (ClassNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
public void startGame() {
// send client message etc etc
}
}
public String getName() {
return name;
}
}
I basically didn't change any of the other classes, except a few lines within the client class to make this work. (I've changed the ready input type from writeObject() to writeInt())
I haven't tested this for problems, but I know it works at least on a basic level.
I also suggest using writeUTS()/readUTS() instead of writeObject()/readObject() for sending and receiving Strings across streams as this will add extra complexity to the code.

Java Object streams to libGDX project

i did try to test some stuff about Client/server communication in Java because i wanted to build a game with a client/server architecture.
So i read some articles and so on... it all worked till i tried to use the same classes and methods in a libGDX project client and the other as server was still the original java project.
than the fun started and i got class not found exceptions on the server side when the server where trying to read the object.
after that i tried to build client and server both as libGDX projects.
still the same error.
the serve:
package com.mygdx.game;
import java.io.IOException;
import java.net.*;
public class Server {
public static void main(String[] args) {
int port = 8800;
try {
ServerSocket serverSocket = new ServerSocket(port);
while (true) {
System.out.println("raedy");
Socket clientSocket = serverSocket.accept();
System.out.println(clientSocket+"verbunden!");
Worker worker = new Worker(clientSocket);
worker.start();
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
package com.mygdx.game;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.net.Socket;
public class Worker extends Thread{
private Socket clientSocket;
public Worker(Socket clientsocket) {
this.clientSocket = clientsocket;
}
#Override
public void run() {
System.out.println("worker started");
try {
ObjectInputStream in= new ObjectInputStream(clientSocket.getInputStream());
Object obj = (Object) in.readObject();
if(obj instanceof Message) {
Message msg= (Message) in.readObject();
System.out.println("Client said: "+msg.getMessage());
}
System.out.println("input auf"+clientSocket.getLocalPort());
ObjectOutputStream out = new ObjectOutputStream(clientSocket.getOutputStream());
out.writeObject(new Message("Hello there!"));
System.out.println("output auf"+clientSocket.getPort());
} catch (IOException | ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
package com.mygdx.game;
import java.io.Serializable;
public class Message implements Serializable{
private static final long serialVersionUID = 1L;
private String message;
public Message(String message) {
this.message = message;
}
public String getMessage(){
return message;
}
}
the client has the the same Message class and this:
package com.mygdx.game.desktop;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.net.Socket;
import java.net.UnknownHostException;
import com.badlogic.gdx.backends.lwjgl.LwjglApplication;
import com.badlogic.gdx.backends.lwjgl.LwjglApplicationConfiguration;
import com.mygdx.game.MyGdxGame;
public class DesktopLauncher {
public static void main (String[] arg) {
int port = 8800;
try {
System.out.println("hello there!");
Socket client = new Socket("localhost", port );
ObjectOutputStream out = new ObjectOutputStream(client.getOutputStream());
out.writeObject(new Message("ich bin der client"));
System.err.println(client.getPort());
ObjectInputStream in = new ObjectInputStream(client.getInputStream());
Message msg= (Message) in.readObject();
System.out.println("Server said: "+msg.getMessage());
System.out.println(client.getLocalPort());
} catch (UnknownHostException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
LwjglApplicationConfiguration config = new LwjglApplicationConfiguration();
new LwjglApplication(new MyGdxGame(), config);
}
}
so my question is why does the same code work in normal java but when i build the same as a libGDX project and try the code there it doesn't work?
yes the message class is only for testing how a serializable object is transferred.
Later i want to send game commands via the object stream.
ps: you made it till the end! thank you :D
pps: the first try in java was without
Object obj = (Object) in.readObject();
if(obj instanceof Message)
I would really recommend you to use Kryonet instead of writing all the stuff from scratch yourself. It does exactly what you are trying to achieve, is mature and well tested with libGDX.

Threads in client/server application

I made client server app, which is joining new clients in new thread each. I want to send information to server like in auction system bidding up value. How Can I check if thread in client class is the same as in server class? If not How Can I check in which Thread on server side is client?
package com.multi;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import oracle.jdbc.driver.OracleDriver;
public class Server {
public static final int PORT = 5545;
public static int I = 1;
public static String[] users = null;
private static final String URL = "jdbc:oracle:thin:#localhost:1521:XE";
Connection conn = null;
Statement stmt = null;
private static final String DB_USER = "DBDEMO";
private static final String DB_PASSWORD = "******";
private ResultSet res;
private String sql = null;
public void startDataBase() {
try {
DriverManager.registerDriver(new OracleDriver());
conn = DriverManager.getConnection(URL, DB_USER, DB_PASSWORD);
System.out.println("conn done");
conn.setAutoCommit(false);
conn.setTransactionIsolation(Connection.TRANSACTION_SERIALIZABLE);
} catch (SQLException e) {
e.printStackTrace();
}
}
public void runQuery(){
try {
stmt = conn.createStatement();
res = stmt.executeQuery("select * from ITEAMS");
System.out.println("query works");
while(res.next()){
System.out.println(res.getString("DESCRIBE"));
}
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public void startServer() {
try {
ServerSocket server = new ServerSocket(PORT);
System.out.println("Server is waiting for connetions...");
startDataBase();
runQuery();
while (true) {
Socket socket = server.accept();
if (socket.isBound()) {
System.out.println("user" + I + " connected");
++I;
}
new ServerThread(socket).start();
}
} catch (IOException e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
new Server().startServer();
}
}
//serverthreads
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.Socket;
public class ServerThread extends Thread {
Socket socket;
String message = null;
ServerThread(Socket socket) {
this.socket = socket;
}
public void run(){
try {
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(socket.getInputStream()));
while ((message = bufferedReader.readLine()) != null){
System.out.println(message);
}
socket.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
//client
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.Socket;
import java.net.UnknownHostException;
import javax.swing.JFrame;
import javax.swing.JScrollPane;
import javax.swing.JTextField;
public class Client extends JFrame{
/**
*
*/
private static final long serialVersionUID = 1L;
private static String[] names = new String[]{ "Sara", "Jessica", "Tom", "Emanuel", "Joshua",
"Kristin", "Kirito", "Goku", "Bulma" };
private JTextField chatWindow;
private static int c = 0;
public void clientJoin(String name) {
try {
chatWindow = new JTextField();
add(new JScrollPane(chatWindow));
setSize(300, 150);
setVisible(true);
Socket socket = new Socket("localhost", 5545);
chatWindow.setText(name);
PrintWriter printWriter = new PrintWriter(
socket.getOutputStream(), true);
BufferedReader bufferedReader = new BufferedReader(
new InputStreamReader(System.in));
// System.out.println(name);
// System.out.println(name);
// while (true) {
// String readerInput = bufferedReader.readLine();
for(int i = 0 ; i < 3;i++){
printWriter.print(name+":" );
printWriter.println(c+=5+10*Math.random());
}
// }
} catch (UnknownHostException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public static void main(String[] args) {
for(String name : names) {
Runnable r = new Runnable() {
#Override
public void run() {
new Client().clientJoin(name);
}
};
new Thread(r).start();
// System.out.println("ges here");
c++;
}
}
}
How Can I check if thread in client class is the same as in server class?
Unless the Client and Server classes are running in the same JVM (i.e. on the same machine and in the same process), they cannot share threads. They cannot be the same.
Furthermore, since the client and server threads are instances of different classes: Thread and ServerThread respective. That means that even if Client and Server were instantiated in the same JVM, the respective threads still could not be the same.
(Two objects with different classes cannot be the same. Especially threads, since thread equality is determined by object identity.)
As you can see, the question makes little sense if you interpret it literally. If you are actually trying to ask something different ... you will need to clarify the question.

How to create an event in Java

I am currently working on a multi-threaded socket based Java program that should allow multiple threads to send request to this program. This should be handled with the event activation but I am having hard time understanding events and their implementation. Below is the code that should allow more than 1 thread to communicate with the program but I only have 1 thread there. Can someone please shed more light on this? Much appreciated.
//this is a a threads class
import java.io.BufferedOutputStream;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.Socket;
import java.util.logging.Level;
import java.util.logging.Logger;
public class Niti implements Runnable {
public String line;
public Socket soc;
public boolean active=true;
public Niti(Socket soc)
{
this.soc=soc;
this.line=line;
this.active=active;
}
public synchronized void run() {
try {
BufferedReader br = new BufferedReader(new InputStreamReader(soc.getInputStream()));
line=br.readLine();
while(line!=null && !line.equals("")){
if(!this.active)
break;
System.out.println(line);
line=br.readLine();
}
BufferedOutputStream bos = new BufferedOutputStream(soc.getOutputStream());
bos.write("Poruka iz Programa".getBytes());
}
catch (IOException ex) {
Logger.getLogger(Niti.class.getName()).log(Level.SEVERE, null, ex);
}
try {
soc.close();
} catch (IOException ex) {
Logger.getLogger(Niti.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
import java.io.BufferedOutputStream;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.ServerSocket;
import java.net.Socket;
//and this is the main class
public class Server{
public static synchronized void main(String[] args) throws IOException, InterruptedException{
ServerSocket ss = new ServerSocket(1000);
while(true){
Socket sokit = ss.accept();
Niti n = new Niti(sokit);
while(true){
Thread t = new Thread(n);
t.start();
//Thread.sleep(4000);
//n.active=false;
System.out.println("nit broj:" + Thread.currentThread().getId());
}
}
}
}
Well, without look to Niti class (that is the client handler class as I suppose) you have a logic error here:
while(true){
Socket sokit = ss.accept();
Niti n = new Niti(sokit);
while(true){ // LOGIC ERROR!!!
Thread t = new Thread(n);
t.start();
//Thread.sleep(4000);
//n.active=false;
System.out.println("nit broj:" + Thread.currentThread().getId());
}
}
With the above code you are creating infinit Threads after pass the first time through accept method. What you have to do is to remove the second while(true), like this:
while(true){
Socket sokit = ss.accept();
Niti n = new Niti(sokit);
Thread t = new Thread(n);
t.start();
//Thread.sleep(4000);
//n.active=false;
System.out.println("nit broj:" + Thread.currentThread().getId());
}

NullPointerException in Thread's run method

I would really appreciate help with my program. It is some sort of chat server with multiple clients.
Here's the server code:
package com.server;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
public class Server {
public static int PORT;
private ServerSocket server;
private Socket socket;
public Server(int port) throws IOException {
PORT = port;
server = new ServerSocket(PORT);
System.out.println("server started");
try {
while (true) {
socket = server.accept();
try {
new ServeClient(socket);
} catch (IOException e) {
socket.close();
}
}
} finally {
server.close();
}
}
public static void main(String[] args) throws IOException {
int port = Integer.parseInt(args[0]);
Server server = new Server(port);
}
}
I start the server and then create a Client. The server receives connection socket from socket
and creates a ServeClient Thread.
Here's ServeClient code:
package com.server;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.net.Socket;
import java.util.Enumeration;
import java.util.Vector;
import com.gui.WindowManager;
public class ServeClient extends Thread {
private final Socket socket;
private BufferedReader in;
private PrintWriter out;
private String msg;
public static final String ENDSTRING = "END";
public static Vector clients = new Vector();
public ServeClient(final Socket socket) throws IOException {
this.socket = socket;
System.out.println("socket " + socket);
in = new BufferedReader(new InputStreamReader(socket.getInputStream()));
out = new PrintWriter(new BufferedWriter(new OutputStreamWriter(
socket.getOutputStream())), true);
start();
}
public void run() {
try {
clients.add(this);
while (true) {
msg = in.readLine();
if (msg == ENDSTRING)
break;
broadcast(msg);
}
System.out.println("closing...");
} catch (IOException e) {
System.err.println("IO EXCEPTION");
} finally {
try {
socket.close();
} catch (IOException e) {
System.err.println("SOCKET NOT CLOSED");
}
}
}
#SuppressWarnings("deprecation")
public void broadcast(String msg) {
synchronized (clients) {
Enumeration<ServeClient> e = clients.elements();
while (e.hasMoreElements()) {
ServeClient serveClient = e.nextElement();
try {
synchronized (serveClient.out) {
serveClient.out.println(msg);
}
} catch (Exception eee) {
serveClient.stop();
}
}
}
}
}
What i get is a NullPointerException when ServeClient invokes run() method
server started
socket Socket[addr=/127.0.0.1,port=51438,localport=8888]
Exception in thread "Thread-0" java.lang.NullPointerException
at com.server.ServeClient.run(ServeClient.java:33)
line 33 is the line with first "try" statement in ServeClient run() method
com.server.ServeClient.run(ServeClient.java:33)
I don't believe that it's happening at the try.
Open up an IDE, turn on debugging, and step through until you can see what's happening. That's the fastest way to figure out what you've missed.
There's an object that you're assuming is fine that is not. Find it.
Here's an example of how to do this properly:
http://www.kodejava.org/examples/216.html
Your problem is with the order in which static instance variables are initialised. Try doing something like:
...
private static Vector clients = null;
...
if (clients==null) {
clients = new Vector(); // consider putting this in a synchronized block
}
before you add the client to the vector.
Sorry for necroing such an old issue but it seemed like this problem wasn't resolved, so I'll give a bit of input from my end.
I've had a similar problem and the compiler also kept telling me that the problem was at the start() method. However, when I commented out the thread part and just ran the code on the same thread as the UI, the compiler directed me to the real source of the problem: the code inside the thread.
After making sure the code didn't give an error, I enclosed the code with the original thread code, and it stopped giving me the NullPointerException error.
Hope this helps someone along the way.
Remove the duplicate class declaration in JPanel.
I was trying to run a timer thread that updated a clock in the main application window.
I had created the JFrame with Eclipse/WindowBuilder and had followed a tutorial on how to make a timer. I had copied the declaration of the textfield into the class declaration to make it available for the entire class, but forgot to remove the Class Id in front of the widget definition. So it still initialized the local instance and not the global one. Thus when I accessed the global one it was still null.

Categories

Resources