Здравствуйте! Пишу общий чат. При каждом подключении Сервер создает новый поток, там проинициализированы:
output = new ObjectOutputStream (connection.getOutputStream ( )); //Пишем в чат
input = new ObjectInputStream (connection.getInputStream ( )); //читаем с сервера
Поток при получении сообщения отправляет (output.writeObject()) всем другим потокам из списка подключенных пользователей.
Если 1 пользователь, то все работает. Но как только подключается 2 пользователь, 1 пользователь теряет способность отправлять сообщения, 2 пользователь отправляет и получает все как надо.
Если 1 пользователь отправляет сообщение, программа виснет, а потом выдает EOFException на стороне клиента при попытке чтения с сервера(input.readObject())
Полностью проект на GitHub: https://github.com/Evleaps/Messenger.git
Часть клиента:
private void Send(Object messagesText) {
try {
SimpleDateFormat date = new SimpleDateFormat ("HH:mm:ss");
output.writeObject ( "\n" + Constant.LOGIN + ": "
+ date.format (new Date ()) + "\n"
+ messagesText.toString ());
output.flush ();
chat.setText (input.readObject().toString ()); //ТУТ ОШИБКА!!!!!!
messages.setText ("");
} catch (IOException e) {
e.printStackTrace ( );
} catch (ClassNotFoundException e) {
e.printStackTrace ( );
}
}
Cервер:
public class Server {
public static final int PORT_MESSAGE = 7000;
private static ServerSocket server;
private static List<ConnectedClient> clients = Collections.synchronizedList ( new ArrayList<ConnectedClient> () );
private static StringBuffer historyMassages = new StringBuffer ("История сообщений: ");
/**
* Сервер ждет подключение в бесконечном цикле, если есть подключение, отправляем в список подключенных клиентов
* Список клиентов clients содержит каждого клиента как новый поток
* Если в historyMassages больше 5000 символов, удаляем ранние сообщения
*/
public static void main(String[] args) throws IOException {
try {
new Thread (new CheckForOnline()).start ();//проверка: в сети ли пользователь?
server = new ServerSocket (PORT_MESSAGE);
while (true) {
ConnectedClient client = new ConnectedClient (server.accept ( ));
System.out.println ("Колличество клиентов main = " + clients.size () );
clients.add (client);
ConnectedClient.nameClient = client;
client.start ( );
}
} catch (IOException e) {
e.printStackTrace ( );
} finally {
server.close ();
}
}
private static class ConnectedClient extends Thread {
private static Socket connection;
private static ObjectInputStream input;
private static ObjectOutputStream output;
protected static ConnectedClient nameClient;
private static String messages;
public ConnectedClient(Socket socket) throws IOException {
connection = socket;
System.out.println ("К серверу подключен пользователь...");
output = new ObjectOutputStream (connection.getOutputStream ( )); //Пишем в чат
input = new ObjectInputStream (connection.getInputStream ( )); //читаем с сервера
output.writeObject (CheckForOnline.nameUser);
output.flush ();
System.out.println ("Сервер передал новому пользователю список занятых логинов" );
}
@Override
public void run() {
try {
System.out.println ("Колличество клиентов run = " + clients.size () );
while (connection.isConnected ()) {
messages = (String) input.readObject();
historyMassages.append (messages);
if (historyMassages.length ( ) > 5000)
historyMassages.delete (5000, historyMassages.length ( ));
synchronized (clients) {
for (ConnectedClient empty : Server.clients) {
empty.output.writeObject (historyMassages.toString ( ));
}
}
}
} catch (IOException e) {
} catch (ClassNotFoundException e) {
} finally {
clients.remove (nameClient);
System.out.println ("Пользователь отключился");
System.out.println ("Количество клиентов = " + clients.size () );
}
}
}
Кофе для программистов: как напиток влияет на продуктивность кодеров?
Рекламные вывески: как привлечь внимание и увеличить продажи
Стратегії та тренди в SMM - Технології, що формують майбутнє сьогодні
Выделенный сервер, что это, для чего нужен и какие характеристики важны?
Современные решения для бизнеса: как облачные и виртуальные технологии меняют рынок
Как объект шара нарисовывается на панели в другом классе?
Всем привет, Возник вопрос по битовым операциям в JavaЕсли брать нативные языки на подобие "с++" или "С" то там понятен выиграш в производительности...
Хочу сделать анимацию вроде той, какая на гифке внизу, но не для ViewPager-а, а для замещения одного View другим