#!/usr/bin/python

# Copyright (c) 2012, the Dart project authors.  Please see the AUTHORS file
# for details. All rights reserved. Use of this source code is governed by a
# BSD-style license that can be found in the LICENSE file.

# Run to install the necessary components to run webdriver on the buildbots or
# on your local machine.
# Note: The setup steps can be done fairly easily by hand. This script is
# intended to simply and reduce the time for setup since there are a fair number
# of steps.

# TODO(efortuna): Rewrite this script in Dart when the Process module has a
# better high level API.
import HTMLParser
import optparse
import os
import platform
import re
import shutil
import string
import subprocess
import sys
import urllib
import urllib2
import zipfile

def run_cmd(cmd, stdin=None):
  """Run the command on the command line in the shell. We print the output of
  the command.
  """
  print cmd
  p = subprocess.Popen(cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE,
      stdin=subprocess.PIPE, shell=True)
  output, stderr = p.communicate(input=stdin)
  if output:
    print output
  if stderr:
    print stderr

def parse_args():
  parser = optparse.OptionParser()
  parser.add_option('--firefox', '-f', dest='firefox',
      help="Don't install Firefox", action='store_true', default=False)
  parser.add_option('--opera', '-o', dest='opera', default=False,
      help="Don't install Opera", action='store_true')
  parser.add_option('--chromedriver', '-c', dest='chromedriver',
      help="Don't install chromedriver.", action='store_true', default=False)
  parser.add_option('--iedriver', '-i', dest='iedriver',
      help="Don't install iedriver (only used on Windows).",
      action='store_true', default=False)
  parser.add_option('--seleniumrc', '-s', dest='seleniumrc',
      help="Don't install the Selenium RC server (used for Safari and Opera "
           "tests).", action='store_true', default=False)
  parser.add_option('--python', '-p', dest='python',
      help="Don't install Selenium python bindings.", action='store_true',
      default=False)
  parser.add_option('--buildbot', '-b', dest='buildbot', action='store_true',
      help='Perform a buildbot selenium setup (buildbots have a different' +
      'location for their python executable).', default=False)
  args, _ = parser.parse_args()
  return args

def find_depot_tools_location(is_buildbot):
  """Depot_tools is our default install location for chromedriver, so we find
  its location on the filesystem.
  Arguments:
  is_buildbot - True if we are running buildbot machine setup (we can't detect
      this automatically because this script is not run at build time).
  """
  if is_buildbot:
    depot_tools = os.sep + os.path.join('b', 'depot_tools')
    if 'win32' in sys.platform or 'cygwin' in sys.platform:
      depot_tools = os.path.join('e:', depot_tools)
    return depot_tools
  else:
    path = os.environ['PATH'].split(os.pathsep)
    for loc in path:
      if 'depot_tools' in loc:
        return loc
  raise Exception("Could not find depot_tools in your path.")

class GoogleBasedInstaller(object):
  """Install a project from a Google source, pulling latest version."""

  def __init__(self, project_name, destination, download_path_func):
    """Create an object that will install the project.
    Arguments:
    project_name - Google code name of the project, such as "selenium" or
    "chromedriver."
    destination - Where to download the desired file on our filesystem.
    download_path_func - A function that takes a dictionary (currently with keys
    "os" and "version", but more can be added) that calculates the string
    representing the path of the download we want.
    """
    self.project_name = project_name
    self.destination = destination
    self.download_path_func = download_path_func

  @property
  def get_os_str(self):
    """The strings to indicate what OS a download is for."""
    os_str = 'win'
    if 'darwin' in sys.platform:
      os_str = 'mac'
    elif 'linux' in sys.platform:
      os_str = 'linux32'
      if '64bit' in platform.architecture()[0]:
        os_str = 'linux64'
    if self.project_name == 'chromedriver' and (
        os_str == 'mac' or os_str == 'win'):
      os_str = os_str + '32'
    return os_str

  def run(self):
    """Download and install the project."""
    print 'Installing %s' % self.project_name
    os_str = self.get_os_str
    version = self.find_latest_version()
    download_path = self.download_path_func({'os': os_str, 'version': version})
    download_name = os.path.basename(download_path)
    urllib.urlretrieve(os.path.join(self.source_path(), download_path),
        os.path.join(self.destination, download_name))
    if download_name.endswith('.zip'):
      if platform.system() != 'Windows':
        # The Python zip utility does not preserve executable permissions, but
        # this does not seem to be a problem for Windows, which does not have a
        # built in zip utility. :-/
        run_cmd('unzip -u %s -d %s' % (os.path.join(self.destination,
                download_name), self.destination), stdin='y')
      else:
        z = zipfile.ZipFile(os.path.join(self.destination, download_name))
        z.extractall(self.destination)
        z.close()
      os.remove(os.path.join(self.destination, download_name))
    chrome_path = os.path.join(os.path.dirname(os.path.abspath(__file__)),
        'orig-chromedriver')
    if self.project_name == 'chromedriver' and os.path.exists(chrome_path):
      # We have one additional location to make sure chromedriver is updated.
      # TODO(efortuna): Remove this. See move_chrome_driver_if_needed in
      # perf_testing/run_perf_tests.py
      driver = 'chromedriver'
      if platform.system() == 'Windows':
        driver += '.exe'
      shutil.copy(os.path.join(self.destination, driver),
          os.path.join(chrome_path, driver))

class ChromeDriverInstaller(GoogleBasedInstaller):
  """Install chromedriver from Google Storage."""

  def __init__(self, destination):
    """Create an object to install ChromeDriver
    destination - Where to download the desired file on our filesystem.
    """
    super(ChromeDriverInstaller, self).__init__('chromedriver', destination,
        lambda x: '%(version)s/chromedriver_%(os)s.zip' % x)

  def find_latest_version(self):
    """Find the latest version number of ChromeDriver."""
    source_page = urllib2.urlopen(self.source_path())
    source_text = source_page.read()
    regex = re.compile('(?:<Key>)(\d+\.\d+)')
    latest = max(regex.findall(source_text))
    return latest

  def source_path(self):
    return 'http://chromedriver.storage.googleapis.com'

class GoogleCodeInstaller(GoogleBasedInstaller):
  """Install a project from Google Code."""

  def google_code_downloads_page(self):
    return 'http://code.google.com/p/%s/downloads/list' % self.project_name

  def find_latest_version(self):
    """Find the latest version number of some code available for download on a
    Google code page. This was unfortunately done in an ad hoc manner because
    Google Code does not seem to have an API for their list of current
    downloads(!).
    """
    google_code_site = self.google_code_downloads_page()
    f = urllib2.urlopen(google_code_site)
    latest = ''

    download_regex_str = self.download_path_func({'os': self.get_os_str,
        'version': '.+'})

    for line in f.readlines():
      if re.search(download_regex_str, line):
        suffix_index = line.find(
            download_regex_str[download_regex_str.rfind('.'):])
        name_end = download_regex_str.rfind('.+')
        name = self.download_path_func({'os': self.get_os_str, 'version': ''})
        name = name[:name.rfind('.')]
        version_str = line[line.find(name) + len(name) : suffix_index]
        orig_version_str = version_str
        if version_str.count('.') == 0:
          version_str = version_str.replace('_', '.')
          version_str = re.compile(r'[^\d.]+').sub('', version_str)
        if latest == '':
          latest = '0.' * version_str.count('.')
          latest += '0'
          orig_latest_str = latest
        else:
          orig_latest_str = latest
          latest = latest.replace('_', '.')
          latest = re.compile(r'[^\d.]+').sub('', latest)
        nums = version_str.split('.')
        latest_nums = latest.split('.')
        for (num, latest_num) in zip(nums, latest_nums):
          if int(num) > int(latest_num):
            latest = orig_version_str
            break
          else:
            latest = orig_latest_str
    if latest == '':
      raise Exception("Couldn't find the desired download on " + \
          ' %s.' % google_code_site)
    return latest

  def source_path(self):
    return 'http://%s.googlecode.com/files/' % self.project_name


class FirefoxInstaller(object):
  """Installs the latest version of Firefox on the machine."""

  def ff_download_site(self, os_name):
    return 'http://releases.mozilla.org/pub/mozilla.org/firefox/releases/' + \
        'latest/%s/en-US/' % os_name

  @property
  def get_os_str(self):
    """Returns the string that Mozilla uses to denote which operating system a
    Firefox binary is for."""
    os_str = ('win32', '.exe')
    if 'darwin' in sys.platform:
      os_str = ('mac', '.dmg')
    elif 'linux' in sys.platform:
      os_str = ('linux-i686', '.tar.bz2')
      if '64bit' in platform.architecture()[0]:
        os_str = ('linux-x86_64', '.tar.bz2')
    return os_str

  def get_download_url(self):
    """Parse the html on the page to determine what is the latest download
    appropriate for our system."""
    f = urllib2.urlopen(self.ff_download_site(self.get_os_str[0]))
    download_name = ''
    for line in f.readlines():
      suffix = self.get_os_str[1]
      if (suffix + '"') in line:
        link_str = '<a href="'
        download_name = line[line.find(link_str) + len(link_str) : \
            line.find(suffix) + len(suffix)]
        break
    return '%s%s' % (self.ff_download_site(self.get_os_str[0]), download_name)

  def run(self):
    print 'Installing Firefox'
    if 'darwin' in sys.platform:
      urllib.urlretrieve(self.get_download_url(), 'firefox.dmg')
      run_cmd('hdiutil mount firefox.dmg')
      run_cmd('sudo cp -R /Volumes/firefox/Firefox.app /Applications')
      run_cmd('hdiutil unmount /Volumes/firefox/')
    elif 'win' in sys.platform:
      urllib.urlretrieve(self.get_download_url(), 'firefox_install.exe')
      run_cmd('firefox_install.exe -ms')
    else:
      run_cmd('wget -O - %s | tar -C ~ -jxv' % self.get_download_url())


class SeleniumBindingsInstaller(object):
  """Install the Selenium Webdriver bindings for Python."""

  SETUPTOOLS_SITE = 'http://python-distribute.org/distribute_setup.py'
  PIP_SITE = 'https://raw.github.com/pypa/pip/master/contrib/get-pip.py'
  def __init__(self, is_buildbot):
    self.is_buildbot = is_buildbot

  def run(self):
    print 'Installing Selenium Python Bindings'
    admin_keyword = ''
    python_cmd = 'python'
    pip_cmd = 'pip'
    if 'win32' not in sys.platform and 'cygwin' not in sys.platform:
      admin_keyword = 'sudo'
      pip_cmd = '/usr/local/bin/pip'
    else:
      # The python installation is "special" on Windows buildbots.
      if self.is_buildbot:
        python_loc = os.path.join(
            find_depot_tools_location(self.is_buildbot), 'python_bin')
        python_cmd = os.path.join(python_loc, 'python')
        pip_cmd = os.path.join(python_loc, 'Scripts', pip_cmd)
      else:
        path = os.environ['PATH'].split(os.pathsep)
        for loc in path:
          if 'python' in loc or 'Python' in loc:
            pip_cmd = os.path.join(loc, 'Scripts', pip_cmd)
            break
    page = urllib2.urlopen(self.SETUPTOOLS_SITE)
    run_cmd('%s %s' % (admin_keyword, python_cmd), page.read())
    page = urllib2.urlopen(self.PIP_SITE)
    run_cmd('%s %s' % (admin_keyword, python_cmd), page.read())
    run_cmd('%s %s install -U selenium' % (admin_keyword, pip_cmd))

class OperaHtmlParser(HTMLParser.HTMLParser):
  """A helper class to parse Opera pages listing available downloads to find the
  correct download we want."""

  def initialize(self, rejection_func, accept_func):
    """Initialize some state for our parser.
    Arguments:
    rejection_func: A function that accepts the value of the URL and determines
      if it is of the type we are looking for.
    accept_func: A function that takes the URL and the "current best" URL and
      determines if it is better than our current download url."""
    self.latest = 0
    self.rejection_func = rejection_func
    self.accept_func = accept_func

  def handle_starttag(self, tag, attrs):
    """Find the latest version."""
    if (tag == 'a' and attrs[0][0] == 'href' and
        self.rejection_func(attrs[0][1])):
      self.latest = self.accept_func(attrs[0][1], self.latest)

class OperaInstaller(object):
  """Install from the Opera FTP website."""

  def find_latest_version(self, download_page, rejection_func, accept_func):
    """Get the latest non-beta version.
    Arguments:
    download_page: The initial page that lists all the download options.
    rejection_func: A function that accepts the value of the URL and determines
      if it is of the type we are looking for.
    accept_func: A function that takes the URL and the "current best" URL and
      determines if it is better than our current download url."""
    f = urllib2.urlopen(download_page)
    parser = OperaHtmlParser()
    parser.initialize(rejection_func, accept_func)
    parser.feed(f.read())
    return str(parser.latest)

  def run(self):
    """Download and install Opera."""
    print 'Installing Opera'
    os_str = self.get_os_str
    download_name = 'http://ftp.opera.com/pub/opera/%s/' % os_str

    def higher_revision(new_version_str, current):
      version_string = new_version_str[:-1]
      if int(version_string) > current:
        return int(version_string)
      return current

    version = self.find_latest_version(
        download_name,
        lambda x: x[0] in string.digits and 'b' not in x and 'rc' not in x,
        higher_revision)
    download_name += version
    if ('linux' in sys.platform and
        platform.linux_distribution()[0] == 'Ubuntu'):
      # Last time I tried, the .deb file you download directly from opera was
      # not installing correctly on Ubuntu. This installs Opera more nicely.
      os.system("sudo sh -c 'wget -O - http://deb.opera.com/archive.key | "
          "apt-key add -'")
      os.system("""sudo sh -c 'echo "deb http://deb.opera.com/opera/ """
          """stable non-free" > /etc/apt/sources.list.d/opera.list'""")
      run_cmd('sudo apt-get update')
      run_cmd('sudo apt-get install opera', stdin='y')
    else:
      if 'darwin' in sys.platform:
        dotted_version = '%s.%s' % (version[:2], version[2:])
        download_name += '/Opera_%s_Setup_Intel.dmg' % dotted_version
        urllib.urlretrieve(download_name, 'opera.dmg')
        run_cmd('hdiutil mount opera.dmg', stdin='qY\n')
        run_cmd('sudo cp -R /Volumes/Opera/Opera.app /Applications')
        run_cmd('hdiutil unmount /Volumes/Opera/')
      elif 'win' in sys.platform:
        download_name += '/en/Opera_%s_en_Setup.exe' % version
        urllib.urlretrieve(download_name, 'opera_install.exe')
        run_cmd('opera_install.exe -ms')
      else:
        # For all other flavors of linux, download the tar.
        download_name += '/'
        extension = '.tar.bz2'
        if '64bit' in platform.architecture()[0]:
          platform_str = '.x86_64'
        else:
          platform_str = '.i386'
        def get_acceptable_file(new_version_str, current):
          return new_version_str
        latest = self.find_latest_version(
            download_name,
            lambda x: x.startswith('opera') and x.endswith(extension)
                and platform_str in x,
            get_acceptable_file)
        download_name += latest
        run_cmd('wget -O - %s | tar -C ~ -jxv' % download_name)
        print ('PLEASE MANUALLY RUN "~/%s/install" TO COMPLETE OPERA '
            'INSTALLATION' %
            download_name[download_name.rfind('/') + 1:-len(extension)])

  @property
  def get_os_str(self):
    """The strings to indicate what OS a download is."""
    os_str = 'win'
    if 'darwin' in sys.platform:
      os_str = 'mac'
    elif 'linux' in sys.platform:
      os_str = 'linux'
    return os_str

def main():
  args = parse_args()
  if not args.python:
    SeleniumBindingsInstaller(args.buildbot).run()
  if not args.chromedriver:
    ChromeDriverInstaller(find_depot_tools_location(args.buildbot)).run()
  if not args.seleniumrc:
    GoogleCodeInstaller('selenium', os.path.dirname(os.path.abspath(__file__)),
        lambda x: 'selenium-server-standalone-%(version)s.jar' % x).run()
  if not args.iedriver and platform.system() == 'Windows':
    GoogleCodeInstaller('selenium', find_depot_tools_location(args.buildbot),
        lambda x: 'IEDriverServer_Win32_%(version)s.zip' % x).run()
  if not args.firefox:
    FirefoxInstaller().run()
  if not args.opera:
    OperaInstaller().run()

if __name__ == '__main__':
  main()
