<html manifest=resources/online-fallback-layering.manifest>
<head>
<script>

if (window.layoutTestController) {
    layoutTestController.dumpAsText();
    layoutTestController.waitUntilDone();
}

function log(message) {
    document.getElementById("log").innerHTML += message + "<br>";
}

function testComplete(result) {
    log(result);
    if (window.layoutTestController)
       layoutTestController.notifyDone();
}

function syncGet(url) {
    var xhr = new XMLHttpRequest();
    xhr.open("GET", url, false);
    xhr.send();
    if (xhr.status == 200)
        return xhr.responseText;
    if (xhr.status == 404)
        return "404 not found";
    log ("unexpected status code");
    return "";
}

applicationCache.oncached = function() { setTimeout(startTest, 0); }
applicationCache.onnoupdate = function() { setTimeout(startTest, 0); }
applicationCache.onupdateready = function() { log('onupdateready'); location.reload(); }
applicationCache.onerror = function() { testComplete('FAIL - onerror'); }
applicationCache.onobsolete = function() { testComplete('FAIL - onobsolete'); }

function startTest() {
    applicationCache.oncached = null;
    applicationCache.onnoupdate = null;

    var response;

    log('Sanity check the presence of the fallback namespace, should get the fallback resource.');
    response = syncGet('resources/fallbacknamespace-nonexisting-resource');
    if (!response.match('fallback resource'))
        return testComplete('FAIL - did not get the fallback resource');

    log('Getting a network namespace resource that exists on the server, should succeed.');
    response = syncGet('resources/fallbacknamespace-networknamespace-existing-resource.html');
    if (!response.match('hello'))
        return testComplete('FAIL - did not get the existing resource');

    log('Getting a network namespace resource that does not exist on the server, should get a 404.');
    response = syncGet('resources/fallbacknamespace-networknamespace-nonexisting-resource');
    if (response != "404 not found")
        return testComplete('FAIL - did not get a 404 for the nonexisting resource');

    log('Creating two iframes for an existing and non-existing page, one should say "hello" the other should 404.');
    createFrame('resources/fallbacknamespace-networknamespace-existing-resource.html');
    createFrame('resources/fallbacknamespace-networknamespace-nonexisting-resource');
}

function createFrame(src) {
    var frame = document.createElement("iframe");
    frame.setAttribute("src", src);
    document.body.appendChild(frame);
}
 
function frameCreated() {
    log('- hello heard');
    setTimeout(waitFor404, 0);
}

function waitFor404() {
  try {
      var frameContent = frames[1].document.documentElement.innerHTML;
      if (frameContent.match("Not Found")) {
          log('- 404 detected');
          testComplete('PASS');
      } else if (frameContent.match("fallback resource"))
          testComplete('FAIL - subframe was loaded with the fallback resource.');
      else
          throw "Try again";
  } catch (ex) {
      setTimeout(waitFor404, 100);
  }
}

</script>
</head>

<body>
<p>Test that a network namespace trumps a fallback namespace where they overlap.</p>
<div id=log></div> 
</body>
</html>
