#!/usr/bin/python -tt
#skvidal, (c) Red Hat, Inc 2012

# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
#

#todo
# add 'execution time' option output to the output

import sys
import os
import getpass
import ansible.runner
import shlex
from ansible.scripts import base_ans_parser, error_print


def main(args):

    parser = base_ans_parser()
    parser.usage = "ans-command [options] command-to-run"

    parser.add_option('-1', '--one-line', dest='one_line', action='store_true', 
        help="output results on one line to make grepping easier, however will \
            not remove newlines from command output")
    parser.add_option('-o', '--output-dir', dest='output_dest', default=None,
        help="output each host's results to a file in a dir named for the host")

    options, args = parser.parse_args(args)

    # TODO: move into lib/ansible/scripts.py
    sshpass = None
    if options.askpass:
        sshpass = getpass.getpass(prompt="SSH password: ")

    if options.output_dest:
        if options.output_dest[0] != '/':
            options.output_dest = os.path.realpath(os.path.expanduser(options.output_dest))
        if not os.path.exists(options.output_dest):
            try:
                os.makedirs(options.output_dest)
            except (IOError, OSError), e:
                print >> sys.stderr, "Could not make dir %s: %s" % (options.output_dest, e)
                sys.exit(1)
        
        if not os.access(options.output_dest, os.W_OK):
            print >> sys.stderr, "Cannot write to path %s" % options.output_dest
            sys.exit(1)

    if len(args) == 0:
       print >> sys.stderr, "Missing argument.  What should be executed?"
       sys.exit(1)

    mycmd = ' '.join(args)
   
    runner = ansible.runner.Runner(
                module_name='command',
                module_path=options.module_path,
                module_args=shlex.split(mycmd),
                remote_user=options.remote_user,
                remote_pass=sshpass,
                host_list=options.host_list,
                forks=options.forks,
                pattern=options.pattern,
                verbose=True,
            )

    results = runner.run()

    for hostname in sorted(results['contacted']):

        result    = results['contacted'][hostname]
        rc        = result.get('rc',0)
        failed    = result.get('failed', 0)
        stdout    = result.get('stdout', '')
        stderr    = result.get('stderr', '')
        traceback = result.get('traceback', '')
        error     = result.get('error', '')

        if rc != 0 or failed:
            msg = 'Error: %s: ' % hostname
            # too bad stdout/stderr is not interleaved :(
            msg += stdout
            msg += stderr
            msg += traceback
            msg += error
            error_print(msg)
            continue

        if options.one_line:
            msg = "(stdout) %s" % stdout
            if stderr.rstrip() != '':
                msg = "(stdout) %s (stderr) %s" % (stdout,stderr)
            print "%s | rc=%s | %s" % (
                hostname, rc, msg
            )
        else:
            print "%s | rc=%s >>" % (hostname, rc)
            print stdout
            if stderr:
                print stderr

    if results['dark']:
        error_print('Hosts which could not be contacted or did not respond:')
        failed_hosts = results['dark'].keys()
        for hostname in keys:
            error_print("%s:%s" % (hostname, results['dark'][hostname]))
        print ''

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





