Я создаю HTTP-сервер в качестве проекта для класса, который я прислушиваюсь, в течение недели я застрял, пытаясь найти решение. У меня есть DataInputStream, и мне нужно дождаться клиента выслать запрос HTTP, может пройти несколько часов до, что происходит, так как соединение остается open.This мой кодБлокировать до тех пор, пока не будет доступен DataInputStream
DataInputStream dis=new DataInputStream(socket.getInputStream());
DataOutputStream dos =new DataOutputStream(socket.getOutputStream());
while(!socket.isClosed()){
try{
/**wait until there are new data in to the stream,if the connection is no more alive then close it*/
while(dis.available()==0){
if(alive==false){
socket.close();
break;
}
}
/*at this point the stream has new data ,or the alive attribute has been set to false */
if(!socket.isClosed()){
/*parse the request text */
Request request=new Request(dis,this);
/*generate a response based on the request*/
Response response=new Response(request,this);
/*send the response back to the client*/
response.send(dos);
/*log the details of the communication*/
Logger.log(toString(request,response,socket));
/*if the request is bad formatted or it has its Connection header set to close , close the connection after sending the response*/
if(request.isBadRequest() || !"keep-alive".equalsIgnoreCase(request.getHeader("Connection"))){
close();
}
}
} catch (IOException e) {
e.printStackTrace();
break;
}
}
на while(dis.available()==0)
части я ждал потока, чтобы иметь какие-то данные, но проблема в том, что, если у меня много соединений, мой сервер начинает получать очень много времени, замедляя мой компьютер, поскольку он просто зависает, делая цикл снова и снова, не давая возможности процессору делать хорошее планирование. Если dis.available() был блокирующая запятая и тогда все было бы идеально. Любой обходной путь?
Это не так, как вы обычно обрабатываете HTTP-запросы. Обычно ваш серверный сокет ожидает соединения. Как только у вас есть соединение, вы предполагаете, что данные должны поступать очень скоро, и если они не попадают в заданный тайм-аут (обычно не более минуты), вы закрываете соединение. – RealSkeptic
@RealSkeptic, но что, если в первом запросе есть заголовок соединения, настроенный на сохранение?, Не должен ли я поддерживать соединение в ожидании, пока клиент не отправит следующий запрос? – SteveL
Существует также истечение срока действия для keepalives. На реальных серверах он настраивается. Например, в Apache значение по умолчанию составляет 5 секунд, и они предупреждают вас, что увеличение его слишком сильно влияет на производительность. Идея keepalive заключается в том, чтобы позволить пользователю избежать накладных расходов на установление нового соединения, это не означает постоянное бесконечное соединение. – RealSkeptic