var color = require('cli-color')
var execSync = require('child_process').execSync || require('execSync').exec
var fs = require('fs')
var path = require('path')

/**
 * So most of this stuff will be sync, because we are moving
 * files around building docker images, etc. These all have
 * to be done in a specific order or chaos ensues
 */
var cwd = path.join(process.cwd(),"tests")
process.stdout.write("Fetching Distributions... ")
var distros = fs.readdirSync(cwd)
var failed = []
process.stdout.write("["+color.green("OK!")+"]\n")
distros.forEach(function(v1) {
  if(!fs.statSync(path.join(cwd,v1)).isDirectory()) return;
  process.stdout.write("Fetching versions of "+capitalize(v1)+"... ")
  var versions = fs.readdirSync(path.join(cwd,v1))
  process.stdout.write("["+color.green("OK!")+"]\n")
  versions.forEach(function(v2) {
    if(!fs.statSync(path.join(cwd,v1,v2)).isDirectory()) return;
    //If Dockerfile already exists, delete it.
    if(fs.existsSync(path.join(process.cwd(),"Dockerfile")))
      fs.unlinkSync(path.join(process.cwd(),"Dockerfile"))
    //Move the dockerfile to the base of our repo
    fs.linkSync(path.join(cwd,v1,v2,"Dockerfile"),path.join(process.cwd(),"Dockerfile"))
    //Build the docker image using the dockerfile
    process.stdout.write("Building version "+v2+" of "+capitalize(v1)+"... ")
    var cmd = "docker build -t \"getos:"+v1+v2+"\" ."
    try {
      var dockerResult = execSync("docker build -t \"getos:"+v1+v2+"\" .",{stdio:[]})
    } catch (e) {
      dockerResult = dockerResult || {}
      dockerResult.code = e
    }
    if(dockerResult.code&&dockerResult.code!==0) {
      failed.push(dockerResult)
      process.stdout.write("["+color.red("FAILED!")+"]\n")
    } else {
      process.stdout.write("["+color.green("OK!")+"]\n")
      process.stdout.write("Running container... ")
      //Show output from distribution
      try {
        var nodeResult = execSync("docker run -d getos:"+v1+v2,{stdio:[]})
      } catch (e) {
        nodeResult = nodeResult || {}
        nodeResult.code = e
      }
      if(nodeResult.code && nodeResult.code!==0) {
        failed.push(nodeResult)
        process.stdout.write("["+color.red("FAILED!")+"]\n")
      } else {
        try {
          var dockerLog = execSync("sleep 2s && docker logs "+(nodeResult.stdout || nodeResult.toString()),{stdio:[]})
        } catch (e) {
          dockerLog = dockerLog || {}
          dockerLog.code = e
        }
        if(dockerLog.code && dockerLog.code!==0) {
          failed.push(dockerLog)
          process.stdout.write("["+color.red("FAILED!")+"]\n")
        } else {
          process.stdout.write("["+color.green("OK!")+"]\n")
          process.stdout.write("Output from version "+v2+" of "+capitalize(v1)+": \n")
          process.stdout.write(dockerLog.stdout||dockerLog.toString())
        }
      }
    }
    //Delete the dockerfile
    fs.unlinkSync(path.join(process.cwd(),"Dockerfile"))
  })
})

if(failed.length>0) {
  fs.writeFileSync("tests.log",JSON.stringify(failed,null," "))
}

function capitalize(str) {
  return str.charAt(0).toUpperCase()+str.slice(1)
}
