Pergunta

Eu estive trabalhando em um gadget do Windows (ou seja, o "navegador" Internet Explorer) que as consultas especificadas endereços de sub-rede para obter informações.Agora, ele às vezes faz isso a um ritmo relativamente rápido (aproximadamente a cada 5 segundos), e que funciona bem o suficiente.No entanto, às vezes, ele vai ficar preso no estado pronto 1 e só vai ficar lá para sempre.Sempre que o gadget tenta refazer a função para obter o xmlhttprequest e recebendo informações de que ele vai permanecer no estado 1.Isso é facilmente replicável ao abrir várias instâncias do gadget e, em seguida, fechar todos, mas um deles.Nesse ponto, o que ainda está aberto quase sempre ficam presos no estado.Eu sinto que ele pode ter algo a ver com todos eles, acessando o mesmo site, ou só pode ter a ver com xmlhttprequests ser interrompido meados de transmissão e que a prevenção outra de trabalho.Abaixo está o código correspondente.

//Reference to this for the inner function
var me = this;
var request = new XMLHttpRequest();
request.onreadystatechange = onReadyStateChange;
var url = this.url;
//Make the URL random to prevent being cached
url += ("&a=" + ((new Date()).getTime()));
Trace(DEBUG_COMM, "Sase.updateStatus url: " + url);
request.open("GET", url, true);
request.send();   // fire off the request, calls httpRequestReadyStateChange as things continue
Trace(DEBUG_COMM, "Request sent" + request.readyState); 
function onReadyStateChange() {Trace(DEBUG_COMM, "Sase.httpRequestReadyStateChange: state=" + request.readyState);
    if (4 == request.readyState) {
        Trace(DEBUG_COMM, "Sase.httpRequestReadyStateChange: status=" + request.status);

        if (request.status == 200) {
            Trace(DEBUG_COMM, "retrieved html: " + request.responseText);
            var results = request.responseText;
            var resultsString = request.responseText.toString();
            Trace(DEBUG_COMM, "results String: " + resultsString);
            me.ParseStatusData(resultsString);
        }
        else {
            //me.commError(request.status);
        }

        request = null;
    }
}
Foi útil?

Solução

Bem parece que eu descobri.Eu tinha a sensação de que foi um não resolvido pedido, uma vez que isso só acontece quando instâncias são fechadas (o que significa que, se um deles é fechada enquanto na comunicação com o servidor permanece na comunicação para sempre e ninguém pode acessar o servidor) e parece que é o caso.Eu fiz algumas modificações para o código em várias áreas e, basicamente, o que ele vem para baixo é quando o gadget fecha torna-se de anular todos os pedidos.A pedidos agora são variáveis de instância (para permitir a abortar deles), mas ainda são feitas novas todas as vezes que elas são necessárias.

Outras dicas

Para aqueles que tropeçam nisso e precisam de um exemplo de código concreto, aqui está.

Eu tive o mesmo problema e a solução era reutilizar o objeto xmlHttPrequest, para garantir que qualquer solicitação anterior fosse cancelada antes de iniciar um novo. Isso não funcionará se você quiser ter várias solicitações de Ajax voando, mas no meu caso desencadear uma nova solicitação significava que a última não era mais necessária.

Todas as solicitações da minha página passaram pelo mesmo método de invólucro xmlHttPrequest, que parecia assim;

//Declare the XMLHttpRequest object to be re-used
var global_xHttpRequest = null;

function xmlHttpHandler(type, params, complete, postData) {

   //Prevents an issue where previous requests get stuck and new ones then fail
   if (global_xHttpRequest == null) {
       global_xHttpRequest = new XMLHttpRequest();
   } else {
       global_xHttpRequest.abort();
   }

   //Parse out current URL
   var baseURL = window.location.host;
   var svc = "https://" + baseURL + "/processAction?";

   var url = svc + params;

   global_xHttpRequest.open(type, url, true);

   //Add the callback
   global_xHttpRequest.onreadystatechange = complete;

   global_xHttpRequest.send(postData);
}

Que pode ser usado assim:

   xmlHttpHandler("GET", params, completeFnc);
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top