/**
 * Service which provides helper methods for extracting information out from a Dockerfile
 * or an archive containing a Dockerfile.
 */
angular.module('quay').factory('DockerfileService', ['DataFileService', 'Config', function(DataFileService, Config) {
  var dockerfileService = {};

  function DockerfileInfo(contents) {
    this.contents = contents;
  }

  DockerfileInfo.prototype.getRegistryBaseImage = function() {
    var baseImage = this.getBaseImage();
    if (!baseImage) {
      return;
    }

    if (baseImage.indexOf(Config.getDomain() + '/') != 0) {
      return;
    }

    return baseImage.substring(Config.getDomain().length + 1);
  };

  DockerfileInfo.prototype.getBaseImage = function() {
    var fromIndex = this.contents.indexOf('FROM ');
    if (fromIndex < 0) {
      return;
    }

    var newline = this.contents.indexOf('\n', fromIndex);
    if (newline < 0) {
      newline = this.contents.length;
    }

    return $.trim(this.contents.substring(fromIndex + 'FROM '.length, newline));
  };

  DockerfileInfo.forData = function(contents) {
    if (contents.indexOf('FROM ') < 0) {
      return;
    }

    return new DockerfileInfo(contents);
  };

  var processFiles = function(files, dataArray, success, failure) {
    // The files array will be empty if the submitted file was not an archive. We therefore
    // treat it as a single Dockerfile.
    if (files.length == 0) {
      DataFileService.arrayToString(dataArray, function(c) {
        var result = DockerfileInfo.forData(c);
        if (!result) {
          failure('File chosen is not a valid Dockerfile');
          return;
        }

        success(result);
      });
      return;
    }

    var found = false;
    files.forEach(function(file) {
      if (file['name'] == 'Dockerfile') {
        DataFileService.blobToString(file.toBlob(), function(c) {
          var result = DockerfileInfo.forData(c);
          if (!result) {
            failure('Dockerfile inside archive is not a valid Dockerfile');
            return;
          }

          success(result);
        });
        found = true;
      }
    });

    if (!found) {
      failure('No Dockerfile found in root of archive');
    }
  };

  dockerfileService.getDockerfile = function(file, success, failure) {
    var reader = new FileReader();
    reader.onload = function(e) {
      var dataArray = reader.result;
      DataFileService.readDataArrayAsPossibleArchive(dataArray, function(files) {
        processFiles(files, dataArray, success, failure);
      }, function() {
        // Not an archive. Read directly as a single file.
        processFiles([], dataArray, success, failure);
      });
    };

    reader.onerror = failure;
    reader.readAsArrayBuffer(file);
  };

  return dockerfileService;
}]);