#!/usr/bin/python -u
#----------------------------------------------------------------------
# Name:        build-all.py
# Purpose:     Master build script for building all the wxPython
#              installers and such on all the build machines in
#              my lab, and then distributing the results as needed.
#
#              This will replace the build-all bash script and is
#              needed because the needs of the build have outgrown
#              what I can do with bash.
#
# Author:      Robin Dunn
#
# Created:     05-Nov-2004
# RCS-ID:      $Id: build-all 55807 2008-09-22 21:34:51Z RD $
# Copyright:   (c) 2004 by Total Control Software
# Licence:     wxWindows license
#----------------------------------------------------------------------

import sys
import os
import time
from taskrunner import Job, Task, TaskRunner, Config

#----------------------------------------------------------------------
# Configuration items

CFGFILE = "./distrib/all/build-environ.cfg"
config = Config()
config.read(CFGFILE)

#----------------------------------------------------------------------
# Define all the build tasks

class Job(Job):
    LOGBASE = "./tmp"

#----------------------------------------------------------------------

def getTasks(config_env):
    # Things that need to be done before any of the builds
    initialTask = Task([
        Job("", "distrib/all/build-setup", env=config_env),
        Job("", "distrib/all/build-docs", env=config_env),
        Job("", "distrib/all/build-sources", env=config_env),
        ])
    
    # Build tasks.  Anything that can be done in parallel (depends greatly
    # on the nature of the build machines configurations...) is a separate
    # task.
    

    tigerTask =  Task([ #Job("smallfry.23",
                        #    "distrib/all/build-osx",
                        #    [config.OSX_HOST_tiger, "2.3", "both"], env=config_env),
                        Job("smallfry.24",
                            "distrib/all/build-osx",
                            [config.OSX_HOST_tiger, "2.4", "both"], env=config_env),
                        Job("smallfry.25",
                            "distrib/all/build-osx",
                            [config.OSX_HOST_tiger, "2.5", "both"], env=config_env)
                    ])

    
    beastTask1 = Task(
        [ Job("beast.23",     "distrib/all/build-windows", ["2.3"], env=config_env),
          Job("beast.24",     "distrib/all/build-windows", ["2.4"], env=config_env),
          Job("beast.25",     "distrib/all/build-windows", ["2.5"], env=config_env),
          ])
    

    cyclopsTask1 = Task([
        Job("cyclops.hardy",   "distrib/all/build-deb", ["cyclops", "/work/chroot/hardy",   "hardy"], env=config_env),
        Job("cyclops.hardy64", "distrib/all/build-deb", ["cyclops", "/work/chroot/hardy64", "hardy64"], env=config_env),
        Job("cyclops.feisty",   "distrib/all/build-deb", ["cyclops", "/work/chroot/feisty",   "feisty"], env=config_env),
        Job("cyclops.feisty64", "distrib/all/build-deb", ["cyclops", "/work/chroot/feisty64", "feisty64"], env=config_env),
        Job("cyclops.fc6", "distrib/all/build-chrpm",  ["cyclops", "/work/chroot/fc6", "fc6", "fc6", "2.4"], env=config_env),
        Job("cyclops.fc7", "distrib/all/build-chrpm",  ["cyclops", "/work/chroot/fc7", "fc7", "fc7", "2.5"], env=config_env),
        Job("cyclops.etch64", "distrib/all/build-deb", ["cyclops", "/work/chroot/etch64",   "etch64"], env=config_env),
        ])

    cyclopsTask2 = Task([
        Job("cyclops.win64", "distrib/all/build-vmwin", ["cyclops", "WinXP-x64-1", "cy-win64", "2.5", "AMD64"], env=config_env),
        Job("cyclops.gutsy",   "distrib/all/build-deb", ["cyclops", "/work/chroot/gutsy",   "gutsy"], env=config_env),
        Job("cyclops.gutsy64", "distrib/all/build-deb", ["cyclops", "/work/chroot/gutsy64", "gutsy64"], env=config_env),
        Job("cyclops.etch",   "distrib/all/build-deb", ["cyclops", "/work/chroot/etch",     "etch"], env=config_env),
        ])

    buildTasks = [
                   tigerTask,
                   beastTask1,
                   cyclopsTask1,
                   cyclopsTask2,
                   ]
    
    # Finalization.  This is for things that must wait until all the
    # builds are done, such as copying the installers someplace, sending
    # emails, etc.
    finalizationTask = Task( Job("", "distrib/all/build-finalize", env=config_env) )

    return initialTask, buildTasks, finalizationTask


#----------------------------------------------------------------------

def usage():
    print ""
    print "Usage: build-all [command flags...]"
    print ""
    print "build types:"
    print "   dryrun       Do the build, but don't copy anywhere (default)"
    print "   daily        Do a daily build, copy to starship"
    print "   release      Do a normal release (cantidate) build, copy to starship"
    print ""
    print "optional command flags:"
    print "   skipsource   Don't build the source archives, use the ones"
    print "                already in the staging dir."
    print "   onlysource   Exit after building the source and docs archives"
    print "   skipdocs     Don't rebuild the docs"
    print "   skipwin      Don't do the remote Windows build"
    print "   skiposx      Don't do the remote OSX build"
    print "   skiprpm      Don't do the remote Linux (RPM) build"
    print "   skipdeb      Don't do the remote Linux (DEB) build"
    print "   skipclean    Don't do the cleanup step on the remote builds"
    print "   skipupload   Don't upload the builds to starship"
    print "   ansi         Also do the ansi builds"
    print ""
    print "   nocohost     Don't start the coLinux sessions if they are"
    print "                not already online"
    print ""
    

#----------------------------------------------------------------------

def main(args):
    # Make sure we are running in the right directory.  TODO: make
    # this test more robust.  Currenly we just test for the presence
    # of 'wxPython' and 'wx' subdirs.
    if not os.path.isdir("wxPython") or not os.path.isdir("wx"):
        print "Please run this script from the root wxPython directory."
        sys.exit(1)
        
    

    # Check command line flags
    for flag in args:
        if flag in ["dryrun", "daily", "release"]:
            config.KIND = flag

        elif flag == "skipsource":
            config.skipsource = "yes"
            
        elif flag == "onlysource":
            config.onlysource = "yes"
            
        elif flag == "skipdocs":
            config.skipdocs = "yes"
            
        elif flag == "skipnewdocs":
            config.skipnewdocs = "yes"
            
        elif flag == "skipwin":
            config.skipwin = "yes"
            
        elif flag == "skiposx":
            config.skiposx = "yes"
            
        elif flag == "skipdeb":
            config.skipdeb = "yes"
            
        elif flag == "skiprpm":
            config.skiprpm = "yes"
            
        elif flag == "skipclean":
            config.skipclean = "yes"
            
        elif flag == "skipupload":
            config.skipupload = "yes"

        elif flag == "ansi":
            config.buildansi = "yes"

        elif flag == "nocohost":
            config.startcohost = "no"
            
        else:
            print 'Unknown flag: "%s"' % flag
            usage()
            sys.exit(2)


    # ensure the staging area exists
    if not os.path.exists(config.STAGING_DIR):
        os.makedirs(config.STAGING_DIR)

    # Figure out the wxPython version number, possibly adjusted for being a daily build
    if config.KIND == "daily":
        t = time.localtime()
        config.DAILY = time.strftime("%Y%m%d")   # should it include the hour too?  2-digit year?
        file("DAILY_BUILD", "w").write(config.DAILY)
    sys.path.append('.')
    import setup
    v = config.VERSION = setup.VERSION
    config.VER2 = '.'.join(v.split('.')[:2])

    config_env = config.asDict()
    config_env.update(os.environ)

    initialTask, buildTasks, finalizationTask = getTasks(config_env)

    print "Build getting started at: ", time.ctime()

    # Run the first task, which will create the docs and sources tarballs
    tr = TaskRunner(initialTask)
    rc = tr.run()

    # cleanup the DAILY_BUILD file
    if config.KIND == "daily":
        os.unlink("DAILY_BUILD")

    # Quit now?
    if rc != 0 or config.onlysource == "yes":
        sys.exit(rc)


    # Run the main build tasks
    tr = TaskRunner(buildTasks)
    rc = tr.run()
    if rc != 0:
        sys.exit(rc)


    # when all the builds are done, run the finalization task
    tr = TaskRunner(finalizationTask)
    rc = tr.run()
    if rc != 0:
        sys.exit(rc)

    
    print "Build finished at: ", time.ctime()
    sys.exit(0)




if __name__ == "__main__":
    main(sys.argv[1:])
