#!/usr/bin/env python

#Signed-off-by: Anne Mulhern <mulhern@yoctoproject.org>

import argparse, os, shutil, sys, tempfile, traceback
from os import path



def get_config(lines):
  """
  From a sequence of lines retrieve the question file name, question identifier
  pairs.
  """
  for l in lines:
    if not l.startswith("#"):
      try:
        (coord, value) = l.split("=")
        try:
          (fname, ident) = coord.split(".")
          yield fname, ident
        except ValueError as e:
          raise ValueError("Badly formatted coordinates %s in line %s." % (coord, l.strip()))
      except ValueError as e:
        raise ValueError("Skipping badly formatted line %s, %s" % (l.strip(), e))



def check_contains(line, name):
  """
  Check if the value field for REQUIRE_DISTRO contains the given name.
  @param name line The REQUIRE_DISTRO line
  @param name name The name to look for in the value field of the line.
  """
  try:
    (label, distros) = line.split(":")
    return name in distros.split()
  except ValueError as e:
    raise ValueError("Error splitting REQUIRE_DISTRO line: %s" % e)



def add_requires(the_ident, distro, lines):

  """
  Yield a sequence of lines the same as lines except that where
  the_ident matches a question identifier change the REQUIRE_DISTRO so that
  it includes the specified distro.

  @param name the_ident The question identifier to be matched.
  @param name distro The distribution to added to the questions REQUIRE_DISTRO
                     field.
  @param lines The sequence to be processed.
  """
  for l in lines:
    yield l
    if l.startswith("LABEL:"):
      try:
        (label, ident) = l.split(":")
        if ident.strip() == the_ident:
          break
      except ValueError as e:
        raise ValueError("Unexpected line %s in questions file." % l.strip())
  for l in lines:
    if l.startswith("REQUIRE_DISTRO"):
      if not check_contains(l, distro):
        yield l.rstrip() + " " + distro + "\n"
      else:
        yield l
      break;
    else:
      yield l
  for l in lines:
    yield l



def xform_file(qfile, distro, qlabel):
  """
  Transform a Questions file.
  @param name qfile The designated questions file.
  @param name distro The distribution to add to the required distributions.
  @param name qlabel The question label for which the distro is to be added.
  """
  questions_in = open(qfile)
  questions_out = tempfile.NamedTemporaryFile(delete=False)
  for l in add_requires(qlabel, distro, questions_in):
    questions_out.write(l)
  questions_out.close()
  questions_in.close()
  shutil.copystat(qfile, questions_out.name)
  os.remove(qfile)
  shutil.move(questions_out.name, qfile)



def handle_args(parser):
  parser.add_argument('config_file',
                      help = "Configuration file path.")
  parser.add_argument('questions_dir',
                      help = "Directory containing Questions files.")
  parser.add_argument('--distro', '-d',
                      help = "The distribution, the default is Yocto.",
                      default = "Yocto")
  parser.add_argument('--debug', '-b',
                      help = "Print debug information.",
                      action = 'store_true')
  return parser.parse_args()



def check_args(args):
  args.config_file = os.path.abspath(args.config_file)
  args.questions_dir = os.path.abspath(args.questions_dir)

  if not os.path.isdir(args.questions_dir):
    raise ValueError("Specified Questions directory %s does not exist or is not a directory." % args.questions_dir)

  if not os.path.isfile(args.config_file):
    raise ValueError("Specified configuration file %s not found." % args.config_file)



def main():
  opts = handle_args(argparse.ArgumentParser(description="A simple script that sets required questions based on the question/answer pairs in a configuration file."))

  try:
    check_args(opts)
  except ValueError as e:
    if opts.debug:
      traceback.print_exc()
    else:
      sys.exit("Fatal error:\n%s" % e)


  try:
    config_in = open(opts.config_file)
    for qfile, qlabel in get_config(config_in):
      questions_file = os.path.join(opts.questions_dir, qfile + ".txt")
      xform_file(questions_file, opts.distro, qlabel)
    config_in.close()

  except IOError as e:
    if opts.debug:
      traceback.print_exc()
    else:
      sys.exit("Fatal error reading or writing file:\n%s" % e)
  except ValueError as e:
    if opts.debug:
      traceback.print_exc()
    else:
      sys.exit("Fatal error:\n%s" % e)



if __name__ == "__main__":
  main()
