<!--

 Licensed to the Apache Software Foundation (ASF) under one
 or more contributor license agreements.  See the NOTICE file
 distributed with this work for additional information
 regarding copyright ownership.  The ASF licenses this file
 to you under the Apache License, Version 2.0 (the
 "License"); you may not use this file except in compliance
 with the License.  You may obtain a copy of the License at

   http://www.apache.org/licenses/LICENSE-2.0

 Unless required by applicable law or agreed to in writing,
 software distributed under the License is distributed on an
 "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 KIND, either express or implied.  See the License for the
 specific language governing permissions and limitations
 under the License.

-->

<!DOCTYPE html>
<html>
<head>
  <title>Cordova: File API Specs</title>

  <meta name="viewport" content="width=device-width, height=device-height, user-scalable=yes, initial-scale=1.0;" />
  <!-- Load jasmine -->
  <link href="../jasmine.css" rel="stylesheet"/>
  <script type="text/javascript" src="../jasmine.js"></script>
  <script type="text/javascript" src="../html/HtmlReporterHelpers.js"></script>
  <script type="text/javascript" src="../html/HtmlReporter.js"></script>
  <script type="text/javascript" src="../html/ReporterView.js"></script>
  <script type="text/javascript" src="../html/SpecView.js"></script>
  <script type="text/javascript" src="../html/SuiteView.js"></script>
  <script type="text/javascript" src="../html/TrivialReporter.js"></script>

  <!-- Source -->
  <script type="text/javascript" src="../../cordova.js"></script>

  <!-- Load Test Runner -->
  <script type="text/javascript" src="../test-runner.js"></script>

  <!-- Tests -->
  <script type="text/javascript" src="../tests/file.tests.js"></script>

  <script type="text/javascript">
      var root, temp_root, persistent_root;

      document.addEventListener('deviceready', function () {
          // one-time retrieval of the root file system entry
          var onError = function(e) {
              console.log('[ERROR] Problem setting up root filesystem for test running! Error to follow.');
              console.log(JSON.stringify(e));
          };

          window.requestFileSystem(LocalFileSystem.PERSISTENT, 0,
              function(fileSystem) {
                  console.log('File API test Init: Setting PERSISTENT FS.');
                  root = fileSystem.root; // set in file.tests.js
                  persistent_root = root;

                  // Once root is set up, fire off tests
                  var jasmineEnv = jasmine.getEnv();
                  jasmineEnv.updateInterval = 1000;

                  var htmlReporter = new jasmine.HtmlReporter();

                  jasmineEnv.addReporter(htmlReporter);

                  jasmineEnv.specFilter = function(spec) {
                    return htmlReporter.specFilter(spec);
                  };

                  jasmineEnv.execute();
              }, onError);
          window.requestFileSystem(LocalFileSystem.TEMPORARY, 0,
              function(fileSystem) {
                  console.log('File API test Init: Setting TEMPORARY FS.');
                  temp_root = fileSystem.root; // set in file.tests.js
              }, onError);
      }, false);
  </script>
</head>

<body>
  <a href="javascript:" class="backBtn" onclick="backHome();">Back</a>
</body>
</html>
