0

I have been writing an embedded webserver on a small micro. I have many things working and can serve up webpages, etc. One page allows the user to upload a new firmware file. I have this working except that I cannot figure out how to return useful error information to them if they make a mistake (say try to upload a file with the wrong file extension). The webpage properly tells them that the Upload Failed (event listener for "error"), but I cannot figure out how to capture the status that was returned by the server - it is always 0 on failure (correctly 200 on success) and responseText is blank.

In this case I am sending "HTTP/1.1 400 Bad Request: Invalid argument (File Extension Invalid)." from the server. In onreadystatechange, readyState does get to 4 but status is always 0.

Please don't 'shoot' me as I am pretty new to Javascript... Below is the code in my firmware upload webpage. The "uploadFile" function is called when they push a button after selecting the file to upload.

Mike.

<script>
      var downloadTimer;
      var ajax;
      
      function _(el) {
        return document.getElementById(el);
      }
      
      function uploadFile() {
        var file = _("file1").files[0];
        var formdata = new FormData();
        formdata.append("file1", file);
        ajax = new XMLHttpRequest();
        ajax.upload.addEventListener("progress", progressHandler, false);
        ajax.addEventListener("load", completeHandler, false);
        ajax.addEventListener("error", errorHandler, false);
        ajax.addEventListener("abort", abortHandler, false);
    _("progressBar").style.visibility = 'visible';
 
        ajax.onreadystatechange = function() {
          if ((this.readyState === 4) && (this.status > 0)){
            console.log(this.responseText);
          }
        }
        
        ajax.open("POST", "/upload.cgi");
    var timeleft = 90;
    uploadTimer = setInterval(function(){
      if (timeleft <= 0){
        clearInterval(downloadTimer);
        _("progressBar").style.visibility = 'hidden';
        _("loaded_n_total").innerHTML = "";
        _("status").innerHTML = "Firmware Update Complete";
        clearInterval(downloadTimer);
      } else {
        var percent = Math.round((90 - timeleft) * 1.111);
        _("progressBar").value = percent;
            _("status").innerHTML = Math.round(percent) + "% uploaded... please wait";
        timeleft -= 1;
      }
    }, 1000);
        ajax.send(formdata);
      }
      
      function progressHandler(event) {
        _("loaded_n_total").innerHTML = "Uploaded " + event.loaded + " bytes of " + event.total;
      }
      
      function completeHandler(event) {
    _("loaded_n_total").innerHTML = "Applying new Firmware...please wait";
        
      }
      
      function errorHandler(event) {
    clearInterval(uploadTimer);
    _("progressBar").style.visibility = 'hidden';
    _("loaded_n_total").innerHTML = "";
        _("status").innerHTML = "Upload Failed";
      }
      
      function abortHandler(event) {
    clearInterval(uploadTimer);
    _("progressBar").style.visibility = 'hidden';
    _("loaded_n_total").innerHTML = "";
        _("status").innerHTML = "Upload Aborted";
      } 
    
</script>

2 Answers 2

0

If your web page is being served from a different origin than your microcontroller, the browser may block the response due to CORS policy. Ensure that your server is configured to send the appropriate CORS headers, such as: ********** Access-Control-Allow-Origin: *************

Sign up to request clarification or add additional context in comments.

Comments

0

OK, I found the issue. Turns out if you send the status from the server to the browser BEFORE you read all of the data sent to you by the browser, the lwIP stack (part of my server project on an ST Micro) sets the RST flag. The browser then ignores the status. This includes status of 200 (meaning the upload succeeded) or any other status such as 400 (Bad).

So, even though I find the error early on - such as the user sent a file of the wrong file type - I have to receive all of the file (through the Content Length) before I respond...

Works now!

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.