import os
import os.path

class ArgParser:
  def __init__(self):
    self.i = 0
    self.args = []

  def parse_type(self, make_type):
    opt = self.args[self.i]
    self.i += 1
    if self.i >= len(self.args):
      return ("Not enough params to " + opt, None)
    val = None
    try:
      val = self.args[self.i] if make_type is None else make_type(self.args[self.i])
    except Exception, e:
      pass
    if val is None:
      return ("Bad argument to " + opt + ": " + self.args[self.i], None)
    return (None, val)

  def possible(self, opts, make_type):
    return lambda v: make_type(v) if v in opts else None

  def condition(self, make_type, condition):
    return lambda v: make_type(v) if condition(make_type(v)) else None

  def folder(self, v):
    path = abspath(v)
    if os.path.isdir(path):
      return path
    return None

  def parse_args(self, args):
    self.args = args
    self.i = 0
    ret = {"input":[]}
    allow_opts = True

    while self.i < len(self.args):
      arg = self.args[self.i].strip()
      if arg == "--":
        allow_opts = False
        self.i += 1
        continue

      if arg == "--port" or arg == "-p":
        (msg, p) = self.parse_type(int)
        if msg is not None:
          return (msg, None)
        ret["port"] = p
      elif arg == "--type" or arg == "-t":
        (msg, t) = self.parse_type(self.possible(["1", "3"], int))
        if msg is not None:
          return (msg, None)
        ret["type"] = t
      elif arg == "--scale" or arg == "-s":
        (msg, s) = self.parse_type(self.condition(int, lambda s: s > 0.00001))
        if msg is not None:
          return (msg, None)
        ret["scale"] = s
      elif arg == "--base" or arg == "-b":
        (msg, b) = self.parse_type(self.folder)
        if msg is not None:
          return (msg, None)
        ret["base"] = b
      else:
        ret["input"].append(arg)
      self.i += 1
    return (None, ret)

def abspath(path):
  return os.path.abspath(os.path.expanduser(path))

def file_in_path(file, path):
  file = abspath(file)
  path = abspath(path)
  if not os.path.isdir(path) or not os.path.isfile(file):
    return False
  return os.path.commonprefix([path, file]) == path
