Example #1
0
    def __init__(self,
                 form,
                 handler,
                 default_path='get_computer_names',
                 **kwargs):
        super(Paths, self).__init__()

        self.next_action = 'main.py'

        # setup jinja2 template system
        self.jinja2_env = jinja2.Environment(
            loader=jinja2.FileSystemLoader('jinja_templates'))
        self.jinja2_env.filters['getitem'] = common.getitem

        # convert the form to a python dictionary
        self.formdict = common.formtodict(form)

        self.handler = handler

        # get the path key from formdict, default to 'get_computer_names' if not defined
        self.path_choice = self.formdict.get('path', default_path)

        # get the path method from Paths class based on path_choice
        self.path_method = getattr(self, self.path_choice, self.unsupported)

        # get the return from path_method
        self.path_return = self.path_method()
Example #2
0
File: main.py Project: tanium/pytan
    def __init__(self, form, handler, default_path='start', **kwargs):
        super(Paths, self).__init__()

        self.next_action = 'main.py'

        # setup jinja2 template system
        self.jinja2_env = jinja2.Environment(loader=jinja2.FileSystemLoader('jinja_templates'))
        self.jinja2_env.filters['getitem'] = common.getitem

        # convert the form to a python dictionary
        self.formdict = common.formtodict(form)

        self.handler = handler

        # get the path key from formdict, default to 'start' if not defined
        self.path_choice = self.formdict.get('path', default_path)

        # get the path method from Paths class based on path_choice
        self.path_method = getattr(self, self.path_choice, self.unsupported)

        # get the return from path_method
        self.path_return = self.path_method()
Example #3
0
my_dir = os.path.dirname(my_file)
sys.path.append(my_dir)

from config import config
import common

sys.path.append(config['pytan_dir'])

import pytan
import cgi
import json

# get the form submission
form = cgi.FieldStorage()

formdict = common.formtodict(form)

action_id = formdict.get('action_id', None)
computer_id = formdict.get('computer_id', None)

if not action_id or not computer_id:
    status = "ERROR: Missing action_id or computer_id!"
else:
    # connect to Tanium
    handler = pytan.Handler(
        username=config['tanium_username'],
        password=config['tanium_password'],
        host=config['tanium_host'],
    )

    # this logic assumes only one system should be being deployed to,
Example #4
0
sys.path.append(config['pytan_dir'])

import pytan
import cgi
import json


def json_print_end(x):
    common.print_html(pytan.utils.jsonify(x))
    sys.exit()


# get the form submission
form = cgi.FieldStorage()

formdict = common.formtodict(form)

question_id = formdict.get('question_id', "")

ret = {
    'status': None,
    'percent': 0,
    'finished': False,
    'question_obj': None,
    'result_info': None,
    'result_data': None,
    'error': False,
}

if not question_id:
    ret['status'] = "ERROR: Missing question_id!"
Example #5
0
def main(ret):
    # get the form submission
    form = cgi.FieldStorage()

    formdict = common.formtodict(form)

    # BOOTSTRAP TESTS
    # formdict['computer_id'] = '1987595770'
    # formdict['substep'] = "11"
    # formdict['jobs'] = ["18372"]

    computer_id = formdict.get('computer_id', "")
    substep = int(formdict.get('substep', 0))

    ret['substep'] = substep
    ret['computer_id'] = computer_id

    if not computer_id:
        die(ret, "Missing computer_id!")

    try:
        # connect to Tanium
        handler = pytan.Handler(
            username=config['tanium_username'],
            password=config['tanium_password'],
            host=config['tanium_host'],
        )
    except Exception as e:
        jobs = get_jobs(ret, formdict)
        ret = add_job(ret, jobs)
        die(ret, "Unable to connect to Tanium: {}!".format(e), False)

    if substep == 1:
        '''
        Ask the question Get Computer Name for this computer_id
        '''
        ret = ask_question(handler, computer_id, formdict, ret, 'Computer Name')
    elif substep == 2:
        '''
        Get the results of previous question, if data ready add computer name to return dict
        for consumption by calling javascript
        '''
        jobs = get_jobs(ret, formdict)
        job = jobs[0]
        ret = add_job(ret, job)

        ret = check_question(handler, computer_id, formdict, ret, job)
        if ret['data_ready'] and ret['results']:
            ret['computer_name'] = ret['results'][0]['Computer Name']
            m = "Found computer name {} for computer ID {}".format
            ret = add_status(ret, m(ret['computer_name'], computer_id), next=True)
            # ret['substep'] = 10  # BOOTSTRAP

    elif substep == 3:
        '''
        Deploy the action "Distribute Patch Tools"
        '''
        ret = deploy_action(handler, computer_id, "Distribute Patch Tools", ret)
    elif substep == 4:
        '''
        Check if previous action done, go to next step if so
        '''
        jobs = get_jobs(ret, formdict)
        job = jobs[0]

        ret = add_job(ret, job)
        ret = check_action(handler, formdict, ret, job)
        if ret['action_done']:
            ret['substep'] += 1
    elif substep == 5:
        '''
        Check that sync scan pkg exists, create if not
        '''
        ret, pkg = create_get_pkg(handler, ret, config['sync_scan_name'], config['sync_scan_opts'])
        ret['substep'] += 1
    elif substep == 6:
        '''
        Deploy the action "Run Patch Scan Synchronously"
        '''
        ret = deploy_action(handler, computer_id, config['sync_scan_name'], ret)
    elif substep == 7:
        '''
        Check if previous action done, go to next step if so
        '''
        jobs = get_jobs(ret, formdict)
        job = jobs[0]
        ret = add_job(ret, job)

        ret = check_action(handler, formdict, ret, job)
        if ret['action_done']:
            ret['substep'] += 1
    elif substep == 8:
        '''
        Ask the question Get Tanium Action Log for previous action for this computer_id
        '''
        jobs = get_jobs(ret, formdict)
        job = jobs[0]

        sensors = 'Tanium Action Log{{actionNumber={}}}'.format(job),
        ret = ask_question(handler, computer_id, formdict, ret, sensors)
    elif substep == 9:
        '''
        Get the results of previous question, if data ready and patch scan finished, go to next step
        '''
        jobs = get_jobs(ret, formdict)
        job = jobs[0]
        ret = add_job(ret, job)

        ret = check_question(handler, computer_id, formdict, ret, job)
        if ret['data_ready'] and ret['results']:
            lines = sorted([x.values()[0] for x in ret['results']])
            log_output = '\n'.join(lines)
            m = "VERBOSE: Tanium Action Log contents finish:\n{}".format
            ret = add_status(ret, m(log_output))

            did_not_run = "patch scan currently running"
            scan_done = "finished running patch scan"
            max_lines = "max number of lines reached"

            if did_not_run in log_output.lower():
                m = 'Re-running patch scan, one already running'
                ret = add_status(ret, m)
                ret['substep'] = 6
            elif scan_done in log_output.lower() or max_lines in log_output.lower():
                m = 'Patch scan finished, getting available patches'
                ret = add_status(ret, m, next=True)
    elif substep == 10:
        '''
        Ask the question Get Available Patches for this computer_id
        '''
        ret = ask_question(handler, computer_id, formdict, ret, 'Available Patches')
    elif substep == 11:
        '''
        Get the results of previous question,
        if data ready and no available patches, go to step 14
        if data ready and available patches, create pkgs for each patch and go to next step
        if data ready and current results unavailable (??) re-ask the question
        '''
        jobs = get_jobs(ret, formdict)
        job = jobs[0]
        ret = add_job(ret, job)

        ret = check_question(handler, computer_id, formdict, ret, job)
        if ret['data_ready']:
            ret['results'] = common.remove_noresults(ret['results'])
            if ret['results']:
                title = ret['results'][0]['Title']
                # TODO: DO THIS BETTER
                if 'current results unavailable' in title.lower():
                    m = "Re-asking due to {}".format
                    ret = add_status(ret, m(title))
                    ret['substep'] = 10
                elif 'all available patches queued for installation' in title.lower():
                    ret = add_status(ret, title, next=True)
                    ret['substep'] = 14
                else:
                    m = "Retrieved {} available patches".format
                    ret = add_status(ret, m(len(ret['results'])), next=True)
                    for rd_row in ret['results']:
                        ret, pkg = create_get_patch_pkg(handler, ret, rd_row)
            else:
                m = "No available patches to deploy"
                ret = add_status(ret, m)
                ret['substep'] = 14
    elif substep == 12:
        '''
        Get the results of previous question,
        if data ready and available patches, deploy pkgs for each patch
        '''
        jobs = get_jobs(ret, formdict)
        job = jobs[0]

        ret = check_question(handler, computer_id, formdict, ret, job)
        if ret['data_ready']:
            if ret['results']:
                for rd_row in ret['results']:
                    ret = deploy_patch_pkg(handler, computer_id, ret, rd_row)
                ret['substep'] += 1
    elif substep == 13:
        '''
        Get the results of each previous deploy patch pkg,
        if all actions finished, go to next step
        '''
        jobs = get_jobs(ret, formdict)
        ret = add_job(ret, jobs)
        done_list = []

        for job in jobs:
            ret = check_action(handler, formdict, ret, job)
            done_list.append(ret['action_done'])

        if all(done_list):
            m = "All {} patch packages have finished deploying".format
            ret = add_status(ret, m(len(done_list)), True)
        else:
            m = "VERBOSE: {} patch packages have finished deploying out of {}".format
            ret = add_status(ret, m(len([x for x in done_list if x]), len(jobs)))
    elif substep == 14:
        ret = ask_question(handler, computer_id, formdict, ret, 'Has Patch Files')
    elif substep == 15:
        jobs = get_jobs(ret, formdict)
        job = jobs[0]
        ret = add_job(ret, job)

        ret = check_question(handler, computer_id, formdict, ret, job)
        ret['results'] = common.remove_noresults(ret['results'])
        if ret['data_ready'] and ret['results']:
            has_patch_files = ret['results'][0]['Has Patch Files']
            if 'yes' in has_patch_files.lower():
                m = "Patch files exist that need to be deployed".format
                ret = add_status(ret, m(), next=True)
            else:
                m = "No patch files exist that need to be deployed, patch process finished".format
                ret = add_status(ret, m())
                ret['finished'] = True

    elif substep == 16:
        ret = deploy_action(handler, computer_id, "Install Deployed Patches", ret)
    elif substep == 17:
        jobs = get_jobs(ret, formdict)
        job = jobs[0]
        ret = add_job(ret, job)

        ret = check_action(handler, formdict, ret, job)
        if ret['action_done']:
            ret['substep'] += 1
    elif substep == 18:
        ret = ask_question(handler, computer_id, formdict, ret, 'Has Patch Files')
    elif substep == 19:
        jobs = get_jobs(ret, formdict)
        job = jobs[0]
        ret = add_job(ret, job)

        ret = check_question(handler, computer_id, formdict, ret, job)
        ret['results'] = common.remove_noresults(ret['results'])
        if ret['data_ready'] and ret['results']:
            has_patch_files = ret['results'][0]['Has Patch Files']
            if 'yes' in has_patch_files.lower():
                m = "Patch files still exist, Install Deployed Patches must still be running"
                ret = add_status(ret, m)
                ret['substep'] = 18
            else:
                m = "No patch files exist, Install Deployed Patches must be finished"
                ret = add_status(ret, m, next=True)
    # elif substep == 20:
    #     ret = deploy_action(handler, computer_id, "Reboot Windows Machine", ret)
    # elif substep == 21:
    #     jobs = get_jobs(ret, formdict)
    #     job = jobs[0]
    #     ret = add_job(ret, job)

    #     ret = check_action(handler, formdict, ret, job)
    #     if ret['action_done']:
    #         ret['substep'] += 1

        '''
        How to determine Install Deployed Patches == Finished (Just Has Patch Files == No?)
        How to determine reboot is done?
1) best way to see if Installed Deployed Patches is finished is if the "Patches deployed by Tanium" sensor returns what you tried to deploy

greg_smith [9:37 AM]
or if Installed patches returns what you deployed

greg_smith [9:38 AM]
I would pick those, as you definitely know it finished and was a success in those cases

greg_smith [9:38 AM]
2)  You can use boot time (its something like that, maybe last reboot time, not sure)

greg_smith [9:38 AM]9:38
when it changes to 5 minutes ago, you know the machine rebooted and is back online
        go back to 6
        '''
    else:
        die(ret, "Invalid substep {}!".format(substep))

    json_print_end(ret)
    return