Пример #1
0
def main():
    """Scans through ZODB checking objects for dangling references"""

    execution_start = time.time()
    sys.path.append ("/opt/zenoss/Products/ZenModel")               # From ZEN-12160
    scriptName = os.path.basename(__file__).split('.')[0]
    parser = ZenToolboxUtils.parse_options(scriptVersion, scriptName + scriptSummary + documentationURL)
    # Add in any specific parser arguments for %scriptName
    cli_options = vars(parser.parse_args())
    log, logFileName = ZenToolboxUtils.configure_logging(scriptName, scriptVersion, cli_options['tmpdir'])
    log.info("Command line options: %s" % (cli_options))
    if cli_options['debug']:
        log.setLevel(logging.DEBUG)

    print "\n[%s] Initializing %s v%s (detailed log at %s)" % \
          (time.strftime("%Y-%m-%d %H:%M:%S"), scriptName, scriptVersion, logFileName)

    # Attempt to get the zenoss.toolbox lock before any actions performed
    if not ZenToolboxUtils.get_lock("zenoss.toolbox", log):
        sys.exit(1)

    number_of_issues = ZenToolboxUtils.Counter(0)

    zodb_name = getGlobalConfiguration().get("zodb-db", "zodb")

    PKEReporter(zodb_name).run(log, number_of_issues)
    log.info("%d Dangling References were detected" % (number_of_issues.value()))

    print("[%s] Execution finished in %s\n" % (strftime("%Y-%m-%d %H:%M:%S", localtime()),
                                               datetime.timedelta(seconds=int(time.time() - execution_start))))
    log.info("zodbscan completed in %1.2f seconds" % (time.time() - execution_start))
    log.info("############################################################")

    if (number_of_issues.value() > 0):
        print("** WARNING ** Dangling Reference(s) were detected - Consult KB article at")
        print("      https://support.zenoss.com/hc/en-us/articles/203118175\n")
        sys.exit(1)
    else:
        sys.exit(0)
Пример #2
0
def scan_catalog(catalogObject, fix, dmd, log, createEvents):
    """Scan through a catalog looking for broken references"""

    # Fix for ZEN-14717 (only for global_catalog)
    if (catalogObject.prettyName == 'global_catalog'):
        global_catalog_paths_to_uids(catalogObject, fix, dmd, log,
                                     createEvents)

    catalog = eval(catalogObject.dmdPath)
    catalogObject.initialSize = len(catalog)

    print("[%s] Examining %-35s (%d Objects)" %
          (time.strftime("%Y-%m-%d %H:%M:%S"), catalogObject.prettyName,
           catalogObject.initialSize))
    log.info("Examining %s catalog with %d objects" %
             (catalogObject.prettyName, catalogObject.initialSize))

    currentCycle = 0

    while (currentCycle < maxCycles):
        currentCycle += 1
        catalogObject.runResults[currentCycle] = {
            'itemCount': ZenToolboxUtils.Counter(0),
            'errorCount': ZenToolboxUtils.Counter(0),
            'repairCount': ZenToolboxUtils.Counter(0)
        }
        log.info("Beginning cycle %d for catalog %s" %
                 (currentCycle, catalogObject.prettyName))
        scan_progress_message(False, fix, currentCycle,
                              catalogObject.prettyName, 0, 0, log)

        try:
            brains = eval(catalogObject.dmdPath)()
        except Exception:
            raise

        catalogSize = len(brains)
        if (catalogSize > 50):
            progressBarChunkSize = (catalogSize // 50) + 1
        else:
            progressBarChunkSize = 1

        for brain in brains:
            catalogObject.runResults[currentCycle]['itemCount'].increment()
            if (catalogObject.runResults[currentCycle]['itemCount'].value() %
                    progressBarChunkSize) == 0:
                chunkNumber = catalogObject.runResults[currentCycle][
                    'itemCount'].value() // progressBarChunkSize
                scan_progress_message(
                    False, fix, currentCycle, catalogObject.prettyName,
                    catalogObject.runResults[currentCycle]
                    ['errorCount'].value(), chunkNumber, log)
            try:
                testReference = brain.getObject()
                testReference._p_deactivate()
            except Exception:
                catalogObject.runResults[currentCycle]['errorCount'].increment(
                )
                objectPathString = brain.getPath()
                log.error("Catalog %s contains broken object %s" %
                          (catalogObject.prettyName, objectPathString))
                if fix:
                    log.info("Attempting to uncatalog %s" % (objectPathString))
                    try:
                        catalogObject.runResults[currentCycle][
                            'repairCount'].increment()
                        transact(catalog.uncatalog_object)(objectPathString)
                    except Exception as e:
                        log.exception(e)

        # Final transaction.abort() to try and free up used memory
        log.debug("Calling transaction.abort() to minimize memory footprint")
        transaction.abort()

        scan_progress_message(
            True, fix, currentCycle, catalogObject.prettyName,
            catalogObject.runResults[currentCycle]['errorCount'].value(),
            chunkNumber, log)

        if fix:
            if catalogObject.runResults[currentCycle]['errorCount'].value(
            ) == 0:
                break
            if currentCycle > 1:
                if catalogObject.runResults[currentCycle]['errorCount'].value(
                ) == catalogObject.runResults[currentCycle -
                                              1]['errorCount'].value():
                    break

    if createEvents:
        scriptName = os.path.basename(__file__).split('.')[0]
        eventMsg = ""
        for cycleID in catalogObject.runResults.keys():
            eventMsg += "Cycle %d scanned %d items, found %d errors and attempted %d repairs\n" % \
                        (cycleID, catalogObject.runResults[cycleID]['itemCount'].value(),
                         catalogObject.runResults[cycleID]['errorCount'].value(),
                         catalogObject.runResults[cycleID]['repairCount'].value())
        if not catalogObject.runResults[currentCycle]['errorCount'].value():
            eventSeverity = 1
            if currentCycle == 1:
                eventSummaryMsg = "'%s' - No Errors Detected (%d total items)" % \
                                   (catalogObject.prettyName, catalogObject.initialSize)
            else:
                eventSummaryMsg = "'%s' - No Errors Detected [--fix was successful] (%d total items)" % \
                                   (catalogObject.prettyName, catalogObject.initialSize)
        else:
            eventSeverity = 4
            if fix:
                eventSummaryMsg = "'%s' - %d Errors Remain after --fix [consult log file]  (%d total items)" % \
                                   (catalogObject.prettyName, catalogObject.runResults[currentCycle]['errorCount'].value(), catalogObject.initialSize)
            else:
                eventSummaryMsg = "'%s' - %d Errors Detected [run with --fix]  (%d total items)" % \
                                   (catalogObject.prettyName, catalogObject.runResults[currentCycle]['errorCount'].value(), catalogObject.initialSize)

        log.debug("Creating event with %s, %s" %
                  (eventSummaryMsg, eventSeverity))
        ZenToolboxUtils.send_summary_event(eventSummaryMsg, eventSeverity,
                                           scriptName,
                                           catalogObject.prettyName,
                                           documentationURL, dmd, eventMsg)

    return (catalogObject.runResults[currentCycle]['errorCount'].value() != 0)
Пример #3
0
            else:
                eventSummaryMsg = "global_catalog 'paths to uids' - No Errors Detected [--fix was successful] (%d total items)" % \
                                   (catalogObject.initialSize)
        else:
            eventSeverity = 4
            if fix:
                eventSummaryMsg = "global_catalog 'paths to uids' - %d Errors Remain after --fix [consult log file]  (%d total items)" % \
                                   (catalogObject.runResults[currentCycle]['errorCount'].value(), catalogObject.initialSize)
            else:
                eventSummaryMsg = "global_catalog 'paths to uids' - %d Errors Detected [run with --fix]  (%d total items)" % \
                                   (catalogObject.runResults[currentCycle]['errorCount'].value(), catalogObject.initialSize)

        log.debug("Creating event with %s, %s" %
                  (eventSummaryMsg, eventSeverity))
        ZenToolboxUtils.send_summary_event(eventSummaryMsg, eventSeverity,
                                           scriptName,
                                           "global_catalog_paths_to_uids",
                                           documentationURL, dmd, eventMsg)

    return (catalogObject.runResults[currentCycle]['errorCount'].value() != 0)


def scan_catalog(catalogObject, fix, dmd, log, createEvents):
    """Scan through a catalog looking for broken references"""

    # Fix for ZEN-14717 (only for global_catalog)
    if (catalogObject.prettyName == 'global_catalog'):
        global_catalog_paths_to_uids(catalogObject, fix, dmd, log,
                                     createEvents)

    catalog = eval(catalogObject.dmdPath)
    catalogObject.initialSize = len(catalog)
Пример #4
0
def main():
    '''Checks for old/unused ip addresses.  If --fix, attempts to remove old unused ip addresses.
       Builds list of available non-empty catalogs.'''

    execution_start = time.time()
    scriptName = os.path.basename(__file__).split('.')[0]
    parser = ZenToolboxUtils.parse_options(
        scriptVersion, scriptName + scriptSummary + documentationURL)
    # Add in any specific parser arguments for %scriptName
    parser.add_argument("-f",
                        "--fix",
                        action="store_true",
                        default=False,
                        help="attempt to remove any stale references")
    parser.add_argument("-n",
                        "--cycles",
                        action="store",
                        default="12",
                        type=int,
                        help="maximum times to cycle (with --fix)")
    parser.add_argument("-l",
                        "--list",
                        action="store_true",
                        default=False,
                        help="output all supported catalogs")
    parser.add_argument("-c",
                        "--catalog",
                        action="store",
                        default="",
                        help="only scan/fix specified catalog")
    cli_options = vars(parser.parse_args())
    log, logFileName = ZenToolboxUtils.configure_logging(
        scriptName, scriptVersion, cli_options['tmpdir'])
    log.info("Command line options: %s" % (cli_options))
    if cli_options['debug']:
        log.setLevel(logging.DEBUG)

    print "\n[%s] Initializing %s v%s (detailed log at %s)" % \
          (time.strftime("%Y-%m-%d %H:%M:%S"), scriptName, scriptVersion, logFileName)

    # Attempt to get the zenoss.toolbox lock before any actions performed
    if not ZenToolboxUtils.get_lock("zenoss.toolbox", log):
        sys.exit(1)

    # Obtain dmd ZenScriptBase connection
    dmd = ZenScriptBase(noopts=True, connect=True).dmd
    log.debug("ZenScriptBase connection obtained")

    any_issue = [False, 0]
    unrecognized_catalog = False

    # Build list of catalogs, then process catalog(s) and perform reindex if --fix
    present_catalog_dict = build_catalog_dict(dmd, log)
    if cli_options['list']:
        # Output list of present catalogs to the UI, perform no further operations
        print "List of supported Zenoss catalogs to examine:\n"
        print "\n".join(present_catalog_dict.keys())
        log.info(
            "zennetworkclean finished - list of supported catalogs output to CLI"
        )
    else:
        # Scan through catalog(s) depending on --catalog parameter
        if cli_options['catalog']:
            if cli_options['catalog'] in present_catalog_dict.keys():
                # Catalog provided as parameter is present - scan just that catalog
                any_issue = scan_catalog(
                    cli_options['catalog'],
                    present_catalog_dict[cli_options['catalog']],
                    cli_options['fix'], cli_options['cycles'], dmd, log)
            else:
                unrecognized_catalog = True
                print("Catalog '%s' unrecognized - unable to scan" %
                      (cli_options['catalog']))
                log.error("CLI input '%s' doesn't match recognized catalogs" %
                          (cli_options['catalog']))
        else:
            # Else scan for all catalogs in present_catalog_dict
            for catalog in present_catalog_dict.keys():
                any_issue = scan_catalog(
                    catalog, present_catalog_dict[catalog], cli_options['fix'],
                    cli_options['cycles'], dmd, log) or any_issue

    # Print final status summary, update log file with termination block
    print("\n[%s] Execution finished in %s\n" %
          (time.strftime("%Y-%m-%d %H:%M:%S"),
           datetime.timedelta(seconds=int(time.time() - execution_start))))
    log.info("zennetworkclean completed in %1.2f seconds" %
             (time.time() - execution_start))
    log.info("############################################################")

    if any_issue and not cli_options['fix']:
        sys.exit(1)
    else:
        sys.exit(0)
Пример #5
0
def main():
    '''Performs reindex call on different DMD categories (used to be a part of zencatalogscan)'''

    execution_start = time.time()
    scriptName = os.path.basename(__file__).split('.')[0]
    parser = ZenToolboxUtils.parse_options(
        scriptVersion, scriptName + scriptSummary + documentationURL)
    # Add in any specific parser arguments for %scriptName
    parser.add_argument("-l",
                        "--list",
                        action="store_true",
                        default=False,
                        help="output all supported reIndex() types")
    parser.add_argument("-t",
                        "--type",
                        action="store",
                        default="",
                        help="specify which type to reIndex()")
    cli_options = vars(parser.parse_args())
    log, logFileName = ZenToolboxUtils.configure_logging(
        scriptName, scriptVersion, cli_options['tmpdir'])
    log.info("Command line options: %s" % (cli_options))
    if cli_options['debug']:
        log.setLevel(logging.DEBUG)

    print "\n[%s] Initializing %s v%s (detailed log at %s)" % \
          (time.strftime("%Y-%m-%d %H:%M:%S"), scriptName, scriptVersion, logFileName)

    # Attempt to get the zenoss.toolbox lock before any actions performed
    if not ZenToolboxUtils.get_lock("zenoss.toolbox", log):
        sys.exit(1)

    # Obtain dmd ZenScriptBase connection
    dmd = ZenScriptBase(noopts=True, connect=True).dmd
    log.debug("ZenScriptBase connection obtained")

    any_issue = False

    # Else build list of catalogs, then process catalog(s) and perform reindex if --fix
    types_to_reIndex = {
        'Devices': 'dmd.Devices',
        'Events': 'dmd.Events',
        'Manufacturers': 'dmd.Manufacturers',
        'Networks': 'dmd.Networks',
        'Services': 'dmd.Services',
    }

    if not USE_MODEL_CATALOG:
        types_to_reIndex['DeviceSearch'] = ' dmd.Devices.deviceSearch'

    if cli_options['list'] or not cli_options['type']:
        # Output list of present catalogs to the UI, perform no further operations
        print "List of dmd types that support reIndex() calls from this script:\n"
        print "\n".join(types_to_reIndex.keys())
        log.info(
            "Zenreindextool finished - list of supported types output to CLI")
        exit(1)

    if cli_options['type'] in types_to_reIndex.keys():
        any_issue = reindex_dmd_objects(cli_options['type'],
                                        types_to_reIndex[cli_options['type']],
                                        dmd, log)
    else:
        print("Type '%s' unrecognized - unable to reIndex()" %
              (cli_options['type']))
        log.error("CLI input '%s' doesn't match recognized types" %
                  (cli_options['type']))
        exit(1)

    # Print final status summary, update log file with termination block
    print("\n[%s] Execution finished in %s\n" %
          (time.strftime("%Y-%m-%d %H:%M:%S"),
           datetime.timedelta(seconds=int(time.time() - execution_start))))
    log.info("zenindextool completed in %1.2f seconds" %
             (time.time() - execution_start))
    log.info("############################################################")

    if any_issue:
        print("** WARNING ** Issues were encountered - Consult KB article at")
        print("      https://support.zenoss.com/hc/en-us/articles/203263689\n")
        sys.exit(1)

    sys.exit(0)
Пример #6
0
def main():
    '''Gathers metrics and statistics about the database that Zenoss uses for Zope/ZEP.'''

    execution_start = time.time()
    scriptName = os.path.basename(__file__).split('.')[0]
    parser = ZenToolboxUtils.parse_options(
        scriptVersion, scriptName + scriptSummary + documentationURL)
    # Add in any specific parser arguments for %scriptName
    parser.add_argument("-n",
                        "-t",
                        "--times",
                        action="store",
                        default=1,
                        type=int,
                        help="number of times to gather data")
    parser.add_argument("-g",
                        "--gap",
                        action="store",
                        default=60,
                        type=int,
                        help="gap between gathering subsequent datapoints")
    parser.add_argument("-l3",
                        "--level3",
                        action="store_true",
                        default=False,
                        help="Data gathering for L3 (standardized parameters)")
    cli_options = vars(parser.parse_args())
    log, logFileName = ZenToolboxUtils.configure_logging(
        scriptName, scriptVersion, cli_options['tmpdir'])
    log.info("Command line options: %s" % (cli_options))
    if cli_options['debug']:
        log.setLevel(logging.DEBUG)

    print "\n[%s] Initializing %s v%s (detailed log at %s)" % \
          (time.strftime("%Y-%m-%d %H:%M:%S"), scriptName, scriptVersion, logFileName)

    # Attempt to get the zenoss.toolbox lock before any actions performed
    if not ZenToolboxUtils.get_lock("zenoss.toolbox.checkdbstats", log):
        sys.exit(1)

    if cli_options['level3']:
        cli_options['times'] = 120
        cli_options['gap'] = 60
        cli_options['debug'] = True
    if cli_options['debug']:
        log.setLevel(logging.DEBUG)

    # Load up the contents of global.conf for using with MySQL
    global_conf_dict = parse_global_conf(
        os.environ['ZENHOME'] + '/etc/global.conf', log)

    # ZEN-19373: zencheckdbstats needs to take into account split databases
    databases_to_examine = []
    intermediate_dict = {
        'prettyName': "'zodb' Database",
        'host': global_conf_dict['zodb-host'],
        'port': global_conf_dict['zodb-port'],
        'admin-user': global_conf_dict['zodb-admin-user'],
        'admin-password': global_conf_dict['zodb-admin-password'],
        'database': global_conf_dict['zodb-db'],
        'mysql_results_list': []
    }
    if global_conf_dict['zodb-host'] == 'localhost':
        if 'zodb-socket' in global_conf_dict:
            intermediate_dict['socket'] = global_conf_dict['zodb-socket']
    databases_to_examine.append(intermediate_dict)
    if global_conf_dict['zodb-host'] != global_conf_dict['zep-host']:
        intermediate_dict = {
            'prettyName': "'zenoss_zep' Database",
            'host': global_conf_dict['zep-host'],
            'port': global_conf_dict['zep-port'],
            'admin-user': global_conf_dict['zep-admin-user'],
            'admin-password': global_conf_dict['zep-admin-password'],
            'database': global_conf_dict['zep-db'],
            'mysql_results_list': []
        }
        if global_conf_dict['zep-host'] == 'localhost':
            # No zep-socket param, use zodb-socket
            if 'zodb-socket' in global_conf_dict:
                intermediate_dict['socket'] = global_conf_dict['zodb-socket']
        databases_to_examine.append(intermediate_dict)

    # If running in debug, log global.conf, grab 'SHOW VARIABLES' and zends.cnf, if straightforward (localhost)
    if cli_options['debug']:
        if global_conf_dict['zodb-host'] == 'localhost':
            log_zends_conf(os.environ['ZENDSHOME'] + '/etc/zends.cnf', log)
        try:
            for item in databases_to_examine:
                mysql_connection = connect_to_mysql(item, log)
                log_MySQL_variables(mysql_connection, log)
                if mysql_connection:
                    mysql_connection.close()
                    log.info(
                        "Closed connection to MySQL/ZenDS for database %s at %s",
                        item['prettyName'], item['host'])
        except Exception as e:
            print "Exception encountered: ", e
            log.error(e)
            exit(1)

    sample_count = 0
    mysql_results_list = []

    while sample_count < cli_options['times']:
        sample_count += 1
        current_time = time.time()
        inline_print(
            "[%s] Gathering MySQL/ZenDS metrics... (%d/%d)" %
            (time.strftime(TIME_FORMAT), sample_count, cli_options['times']))
        try:
            for item in databases_to_examine:
                mysql_connection = connect_to_mysql(item, log)
                mysql_results = gather_MySQL_statistics(mysql_connection, log)
                item['mysql_results_list'].append(
                    (current_time, mysql_results))
                if mysql_connection:
                    mysql_connection.close()
                    log.info(
                        "Closed connection to MySQL/ZenDS for database %s at %s",
                        item['prettyName'], item['host'])
        except Exception as e:
            print "Exception encountered: ", e
            log.error(e)
            exit(1)
        if sample_count < cli_options['times']:
            time.sleep(cli_options['gap'])

    # Process and display results (calculate statistics)
    print("")
    for database in databases_to_examine:
        print("\n[%s] Results for %s:" %
              (time.strftime(TIME_FORMAT), database['prettyName']))
        log.info("[%s] Final Results for %s:", time.strftime(TIME_FORMAT),
                 database['prettyName'])
        observed_results_dict = OrderedDict([])
        observed_results_dict['History List Length'] = [
            item[1]['history_list_length']
            for item in database['mysql_results_list']
        ]
        observed_results_dict['Bufferpool Used (%)'] = [
            item[1]['buffer_pool_used_percentage']
            for item in database['mysql_results_list']
        ]
        observed_results_dict['ACTIVE TRANSACTIONS'] = [
            item[1]['number_active_transactions']
            for item in database['mysql_results_list']
        ]
        observed_results_dict['ACTIVE TRANS > 100s'] = [
            item[1]['number_active_transactions_over']
            for item in database['mysql_results_list']
        ]
        for key in observed_results_dict:
            values = observed_results_dict[key]
            if min(values) != max(values):
                output_message = "[{}]  {}: {:<10} (Average {:.2f}, Minimum {}, Maximum {})".format(
                    time.strftime(TIME_FORMAT), key, values[-1],
                    float(sum(values) / len(values)), min(values), max(values))
            else:
                output_message = "[{}]  {}: {}".format(
                    time.strftime(TIME_FORMAT), key, values[-1])

            print output_message
            log.info(output_message)

    # Print final status summary, update log file with termination block
    print("\n[%s] Execution finished in %s\n" %
          (time.strftime(TIME_FORMAT),
           datetime.timedelta(
               seconds=int(math.ceil(time.time() - execution_start)))))
    print("** Additional information and next steps at %s **\n" %
          documentationURL)
    log.info("zencheckdbstats completed in %1.2f seconds",
             time.time() - execution_start)
    log.info("############################################################")
    sys.exit(0)
Пример #7
0
def scan_catalog(catalogObject, fix, dmd, log, createEvents):
    """Scan through a catalog looking for broken references"""

    # Fix for ZEN-14717 (only for global_catalog)
    if (catalogObject.prettyName == 'global_catalog'):
        global_catalog_paths_to_uids(catalogObject, fix, dmd, log, createEvents)

    catalog = eval(catalogObject.dmdPath)
    catalogObject.initialSize = len(catalog)

    print("[%s] Examining %-35s (%d Objects)" %
          (time.strftime("%Y-%m-%d %H:%M:%S"), catalogObject.prettyName, catalogObject.initialSize))
    log.info("Examining %s catalog with %d objects" % (catalogObject.prettyName, catalogObject.initialSize))

    currentCycle = 0

    while (currentCycle < maxCycles):
        currentCycle += 1
        catalogObject.runResults[currentCycle] = {'itemCount': ZenToolboxUtils.Counter(0),
                                                  'errorCount': ZenToolboxUtils.Counter(0),
                                                  'repairCount': ZenToolboxUtils.Counter(0)
                                                  }
        log.info("Beginning cycle %d for catalog %s" % (currentCycle, catalogObject.prettyName))
        scan_progress_message(False, fix, currentCycle, catalogObject.prettyName, 0, 0, log)

        try:
            brains = eval(catalogObject.dmdPath)()
        except Exception:
            raise

        catalogSize = len(brains)
        if (catalogSize > 50):
            progressBarChunkSize = (catalogSize//50) + 1
        else:
            progressBarChunkSize = 1

        for brain in brains:
            catalogObject.runResults[currentCycle]['itemCount'].increment()
            if (catalogObject.runResults[currentCycle]['itemCount'].value() % progressBarChunkSize) == 0:
                chunkNumber = catalogObject.runResults[currentCycle]['itemCount'].value() // progressBarChunkSize
                scan_progress_message(False, fix, currentCycle, catalogObject.prettyName,
                                      catalogObject.runResults[currentCycle]['errorCount'].value(), chunkNumber, log)
            try:
                testReference = brain.getObject()
                testReference._p_deactivate()
            except Exception:
                catalogObject.runResults[currentCycle]['errorCount'].increment()
                objectPathString = brain.getPath()
                log.error("Catalog %s contains broken object %s" % (catalogObject.prettyName, objectPathString))
                if fix:
                    log.info("Attempting to uncatalog %s" % (objectPathString))
                    try:
                        catalogObject.runResults[currentCycle]['repairCount'].increment()
                        transact(catalog.uncatalog_object)(objectPathString)
                    except Exception as e:
                        log.exception(e)

        # Final transaction.abort() to try and free up used memory
        log.debug("Calling transaction.abort() to minimize memory footprint")
        transaction.abort()

        scan_progress_message(True, fix, currentCycle, catalogObject.prettyName,
                              catalogObject.runResults[currentCycle]['errorCount'].value(), chunkNumber, log)

        if fix:
            if catalogObject.runResults[currentCycle]['errorCount'].value() == 0:
                break
            if currentCycle > 1:
                if catalogObject.runResults[currentCycle]['errorCount'].value() == catalogObject.runResults[currentCycle-1]['errorCount'].value():
                    break

    if createEvents:
        scriptName = os.path.basename(__file__).split('.')[0]
        eventMsg = ""
        for cycleID in catalogObject.runResults.keys():
            eventMsg += "Cycle %d scanned %d items, found %d errors and attempted %d repairs\n" % \
                        (cycleID, catalogObject.runResults[cycleID]['itemCount'].value(),
                         catalogObject.runResults[cycleID]['errorCount'].value(),
                         catalogObject.runResults[cycleID]['repairCount'].value())
        if not catalogObject.runResults[currentCycle]['errorCount'].value():
            eventSeverity = 1
            if currentCycle == 1:
                eventSummaryMsg = "'%s' - No Errors Detected (%d total items)" % \
                                   (catalogObject.prettyName, catalogObject.initialSize)
            else:
                eventSummaryMsg = "'%s' - No Errors Detected [--fix was successful] (%d total items)" % \
                                   (catalogObject.prettyName, catalogObject.initialSize)
        else:
            eventSeverity = 4
            if fix:
                eventSummaryMsg = "'%s' - %d Errors Remain after --fix [consult log file]  (%d total items)" % \
                                   (catalogObject.prettyName, catalogObject.runResults[currentCycle]['errorCount'].value(), catalogObject.initialSize)
            else:
                eventSummaryMsg = "'%s' - %d Errors Detected [run with --fix]  (%d total items)" % \
                                   (catalogObject.prettyName, catalogObject.runResults[currentCycle]['errorCount'].value(), catalogObject.initialSize)

        log.debug("Creating event with %s, %s" % (eventSummaryMsg, eventSeverity))
        ZenToolboxUtils.send_summary_event(
            eventSummaryMsg, eventSeverity,
            scriptName, catalogObject.prettyName,
            documentationURL, dmd, eventMsg
        )

    return (catalogObject.runResults[currentCycle]['errorCount'].value() != 0)
Пример #8
0
def main():
    '''Checks for old/unused ip addresses.  If --fix, attempts to remove old unused ip addresses.
       Builds list of available non-empty catalogs.'''

    execution_start = time.time()
    scriptName = os.path.basename(__file__).split('.')[0]
    parser = ZenToolboxUtils.parse_options(scriptVersion, scriptName + scriptSummary + documentationURL)
    # Add in any specific parser arguments for %scriptName
    parser.add_argument("-f", "--fix", action="store_true", default=False,
                        help="attempt to remove any stale references")
    parser.add_argument("-n", "--cycles", action="store", default="12", type=int,
                        help="maximum times to cycle (with --fix)")
    parser.add_argument("-l", "--list", action="store_true", default=False,
                        help="output all supported catalogs")
    parser.add_argument("-c", "--catalog", action="store", default="",
                        help="only scan/fix specified catalog")
    cli_options = vars(parser.parse_args())
    log, logFileName = ZenToolboxUtils.configure_logging(scriptName, scriptVersion, cli_options['tmpdir'])
    log.info("Command line options: %s" % (cli_options))
    if cli_options['debug']:
        log.setLevel(logging.DEBUG)

    print "\n[%s] Initializing %s v%s (detailed log at %s)" % \
          (time.strftime("%Y-%m-%d %H:%M:%S"), scriptName, scriptVersion, logFileName)

    # Attempt to get the zenoss.toolbox lock before any actions performed
    if not ZenToolboxUtils.get_lock("zenoss.toolbox", log):
        sys.exit(1)

    # Obtain dmd ZenScriptBase connection
    dmd = ZenScriptBase(noopts=True, connect=True).dmd
    log.debug("ZenScriptBase connection obtained")

    any_issue = [False, 0]
    unrecognized_catalog = False

    # Build list of catalogs, then process catalog(s) and perform reindex if --fix
    present_catalog_dict = build_catalog_dict(dmd, log)
    if cli_options['list']:
    # Output list of present catalogs to the UI, perform no further operations
        print "List of supported Zenoss catalogs to examine:\n"
        print "\n".join(present_catalog_dict.keys())
        log.info("zennetworkclean finished - list of supported catalogs output to CLI")
    else:
    # Scan through catalog(s) depending on --catalog parameter
        if cli_options['catalog']:
            if cli_options['catalog'] in present_catalog_dict.keys():
            # Catalog provided as parameter is present - scan just that catalog
                any_issue = scan_catalog(cli_options['catalog'], present_catalog_dict[cli_options['catalog']],
                                         cli_options['fix'], cli_options['cycles'], dmd, log)
            else:
                unrecognized_catalog = True
                print("Catalog '%s' unrecognized - unable to scan" % (cli_options['catalog']))
                log.error("CLI input '%s' doesn't match recognized catalogs" % (cli_options['catalog']))
        else:
        # Else scan for all catalogs in present_catalog_dict
            for catalog in present_catalog_dict.keys():
                any_issue = scan_catalog(catalog, present_catalog_dict[catalog], cli_options['fix'],
                                         cli_options['cycles'], dmd, log) or any_issue

    # Print final status summary, update log file with termination block
    print("\n[%s] Execution finished in %s\n" % (time.strftime("%Y-%m-%d %H:%M:%S"),
                                                 datetime.timedelta(seconds=int(time.time() - execution_start))))
    log.info("zennetworkclean completed in %1.2f seconds" % (time.time() - execution_start))
    log.info("############################################################")

    if any_issue and not cli_options['fix']:
        sys.exit(1)
    else:
        sys.exit(0)
Пример #9
0
def main():
    """ Scans through zodb hierarchy (from user-supplied path, defaults to /,  checking for PKEs """

    execution_start = time.time()
    scriptName = os.path.basename(__file__).split('.')[0]
    parser = ZenToolboxUtils.parse_options(
        scriptVersion, scriptName + scriptSummary + documentationURL)
    # Add in any specific parser arguments for %scriptName
    parser.add_argument("-f",
                        "--fix",
                        action="store_true",
                        default=False,
                        help="attempt to fix ZenRelationship objects")
    parser.add_argument("-n",
                        "--cycles",
                        action="store",
                        default="2",
                        type=int,
                        help="maximum times to cycle (with --fix)")
    parser.add_argument("-p",
                        "--path",
                        action="store",
                        default="/",
                        type=str,
                        help="base path to scan from (Devices.Server)?")
    parser.add_argument(
        "-u",
        "--unlimitedram",
        action="store_true",
        default=False,
        help="skip transaction.abort() - unbounded RAM, ~40%% faster")
    cli_options = vars(parser.parse_args())
    log, logFileName = ZenToolboxUtils.configure_logging(
        scriptName, scriptVersion, cli_options['tmpdir'])
    log.info("Command line options: %s" % (cli_options))
    if cli_options['debug']:
        log.setLevel(logging.DEBUG)

    print "\n[%s] Initializing %s v%s (detailed log at %s)" % \
          (time.strftime("%Y-%m-%d %H:%M:%S"), scriptName, scriptVersion, logFileName)

    # Attempt to get the zenoss.toolbox lock before any actions performed
    if not ZenToolboxUtils.get_lock("zenoss.toolbox", log):
        sys.exit(1)

    # Obtain dmd ZenScriptBase connection
    dmd = ZenScriptBase(noopts=True, connect=True).dmd
    log.debug("ZenScriptBase connection obtained")

    counters = {
        'item_count': ZenToolboxUtils.Counter(0),
        'error_count': ZenToolboxUtils.Counter(0),
        'repair_count': ZenToolboxUtils.Counter(0)
    }

    processed_path = re.split("[./]", cli_options['path'])
    if processed_path[0] == "app":
        processed_path = processed_path[1:]
    processed_path = '/'.join(processed_path) if processed_path else '/'

    try:
        folder = dmd.getObjByPath(processed_path)
    except KeyError:
        print "Invalid path: %s" % (cli_options['path'])
    else:
        print("[%s] Examining items under the '%s' path (%s):" % (strftime(
            "%Y-%m-%d %H:%M:%S", localtime()), cli_options['path'], folder))
        log.info("Examining items under the '%s' path (%s)",
                 cli_options['path'], folder)
        findPOSKeyErrors(folder, cli_options['fix'],
                         cli_options['unlimitedram'], dmd, log, counters,
                         cli_options['cycles'])
        print

    print("\n[%s] Execution finished in %s\n" %
          (strftime("%Y-%m-%d %H:%M:%S", localtime()),
           datetime.timedelta(seconds=int(time.time() - execution_start))))
    log.info("findposkeyerror completed in %1.2f seconds",
             time.time() - execution_start)
    log.info("############################################################")

    if not cli_options['skipEvents']:
        if counters['error_count'].value():
            eventSeverity = 4
            eventSummaryMsg = "%s encountered %d errors (took %1.2f seconds)" % \
                               (scriptName, counters['error_count'].value(), (time.time() - execution_start))
        else:
            eventSeverity = 2
            eventSummaryMsg = "%s completed without errors (took %1.2f seconds)" % \
                               (scriptName, (time.time() - execution_start))

        ZenToolboxUtils.send_summary_event(eventSummaryMsg, eventSeverity,
                                           scriptName, "executionStatus",
                                           documentationURL, dmd)

    if ((counters['error_count'].value() > 0) and not cli_options['fix']):
        print("** WARNING ** Issues were detected - Consult KB article at")
        print("      https://support.zenoss.com/hc/en-us/articles/203117795\n")
        sys.exit(1)
    else:
        sys.exit(0)
Пример #10
0
            else:
                eventSummaryMsg = "global_catalog 'paths to uids' - No Errors Detected [--fix was successful] (%d total items)" % \
                                   (catalogObject.initialSize)
        else:
            eventSeverity = 4
            if fix:
                eventSummaryMsg = "global_catalog 'paths to uids' - %d Errors Remain after --fix [consult log file]  (%d total items)" % \
                                   (catalogObject.runResults[currentCycle]['errorCount'].value(), catalogObject.initialSize)
            else:
                eventSummaryMsg = "global_catalog 'paths to uids' - %d Errors Detected [run with --fix]  (%d total items)" % \
                                   (catalogObject.runResults[currentCycle]['errorCount'].value(), catalogObject.initialSize)

        log.debug("Creating event with %s, %s" % (eventSummaryMsg, eventSeverity))
        ZenToolboxUtils.send_summary_event(
            eventSummaryMsg, eventSeverity,
            scriptName, "global_catalog_paths_to_uids",
            documentationURL, dmd, eventMsg
        )

    return (catalogObject.runResults[currentCycle]['errorCount'].value() != 0)


def scan_catalog(catalogObject, fix, dmd, log, createEvents):
    """Scan through a catalog looking for broken references"""

    # Fix for ZEN-14717 (only for global_catalog)
    if (catalogObject.prettyName == 'global_catalog'):
        global_catalog_paths_to_uids(catalogObject, fix, dmd, log, createEvents)

    catalog = eval(catalogObject.dmdPath)
    catalogObject.initialSize = len(catalog)
Пример #11
0
def main():
    '''Gathers metrics and statistics about the database that Zenoss uses for Zope/ZEP.'''

    execution_start = time.time()
    scriptName = os.path.basename(__file__).split('.')[0]
    parser = ZenToolboxUtils.parse_options(scriptVersion, scriptName + scriptSummary + documentationURL)
    # Add in any specific parser arguments for %scriptName
    parser.add_argument("-n", "-t", "--times", action="store", default=1, type=int,
                        help="number of times to gather data")
    parser.add_argument("-g", "--gap", action="store", default=60, type=int,
                        help="gap between gathering subsequent datapoints")
    parser.add_argument("-l3", "--level3", action="store_true", default=False,
                        help="Data gathering for L3 (standardized parameters)")
    cli_options = vars(parser.parse_args())
    log, logFileName = ZenToolboxUtils.configure_logging(scriptName, scriptVersion, cli_options['tmpdir'])
    log.info("Command line options: %s" % (cli_options))
    if cli_options['debug']:
        log.setLevel(logging.DEBUG)

    print "\n[%s] Initializing %s v%s (detailed log at %s)" % \
          (time.strftime("%Y-%m-%d %H:%M:%S"), scriptName, scriptVersion, logFileName)

    # Attempt to get the zenoss.toolbox lock before any actions performed
    if not ZenToolboxUtils.get_lock("zenoss.toolbox.checkdbstats", log):
        sys.exit(1)

    if cli_options['level3']:
        cli_options['times'] = 120
        cli_options['gap'] = 60
        cli_options['debug'] = True
    if cli_options['debug']:
        log.setLevel(logging.DEBUG)

    # Load up the contents of global.conf for using with MySQL
    global_conf_dict = parse_global_conf(os.environ['ZENHOME'] + '/etc/global.conf', log)

    # ZEN-19373: zencheckdbstats needs to take into account split databases
    databases_to_examine = []
    intermediate_dict = { 'prettyName': "'zodb' Database",
                          'socket': global_conf_dict['zodb-socket'],
                          'host': global_conf_dict['zodb-host'],
                          'port': global_conf_dict['zodb-port'], 
                          'admin-user': global_conf_dict['zodb-admin-user'],
                          'admin-password': global_conf_dict['zodb-admin-password'],
                          'database': global_conf_dict['zodb-db'],
                          'mysql_results_list': []
                        }
    databases_to_examine.append(intermediate_dict)
    if global_conf_dict['zodb-host'] != global_conf_dict['zep-host']:
        intermediate_dict = { 'prettyName': "'zenoss_zep' Database",
                              'socket': global_conf_dict['zodb-socket'],
                              'host': global_conf_dict['zep-host'],
                              'port': global_conf_dict['zep-port'],
                              'admin-user': global_conf_dict['zep-admin-user'],
                              'admin-password': global_conf_dict['zep-admin-password'],
                              'database': global_conf_dict['zep-db'],
                              'mysql_results_list': []
                            }
        databases_to_examine.append(intermediate_dict)

    # If running in debug, log global.conf, grab 'SHOW VARIABLES' and zends.cnf, if straightforward (localhost)
    if cli_options['debug']:
        if global_conf_dict['zodb-host'] == 'localhost':
            log_zends_conf(os.environ['ZENDSHOME'] + '/etc/zends.cnf', log)
        try:
            for item in databases_to_examine:
                mysql_connection = connect_to_mysql(item, log)
                log_MySQL_variables(mysql_connection, log)
                if mysql_connection:
                    mysql_connection.close()
                    log.info("Closed connection to MySQL/ZenDS for database %s at %s", item['prettyName'], item['host'])
        except Exception as e:
            print "Exception encountered: ", e
            log.error(e)
            exit(1)

    sample_count = 0
    mysql_results_list = []

    while sample_count < cli_options['times']:
        sample_count += 1
        current_time = time.time()
        inline_print("[%s] Gathering MySQL/ZenDS metrics... (%d/%d)" %
                     (time.strftime(TIME_FORMAT), sample_count, cli_options['times']))
        try:
            for item in databases_to_examine:
                mysql_connection = connect_to_mysql(item, log)
                mysql_results = gather_MySQL_statistics(mysql_connection, log)
                item['mysql_results_list'].append((current_time, mysql_results))
                if mysql_connection:
                    mysql_connection.close()
                    log.info("Closed connection to MySQL/ZenDS for database %s at %s", item['prettyName'], item['host'])
        except Exception as e:
            print "Exception encountered: ", e
            log.error(e)
            exit(1)
        if sample_count < cli_options['times']:
            time.sleep(cli_options['gap'])

    # Process and display results (calculate statistics)
    print ("")
    for database in databases_to_examine:
        print("\n[%s] Results for %s:" % (time.strftime(TIME_FORMAT), database['prettyName']))
        log.info("[%s] Final Results for %s:", time.strftime(TIME_FORMAT), database['prettyName'])
        observed_results_dict = OrderedDict([])
        observed_results_dict['History List Length'] = [item[1]['history_list_length'] for item in database['mysql_results_list']]
        observed_results_dict['Bufferpool Used (%)'] = [item[1]['buffer_pool_used_percentage'] for item in database['mysql_results_list']]
        observed_results_dict['ACTIVE TRANSACTIONS'] = [item[1]['number_active_transactions'] for item in database['mysql_results_list']]
        observed_results_dict['ACTIVE TRANS > 100s'] = [item[1]['number_active_transactions_over'] for item in database['mysql_results_list']]
        for key in observed_results_dict:
            values = observed_results_dict[key]
            if min(values) != max(values):
                output_message = "[{}]  {}: {:<10} (Average {:.2f}, Minimum {}, Maximum {})".format(time.strftime(TIME_FORMAT), key, values[-1], float(sum(values)/len(values)), min(values), max(values))
            else:
                output_message = "[{}]  {}: {}".format(time.strftime(TIME_FORMAT), key, values[-1])

            print output_message
            log.info(output_message)

    # Print final status summary, update log file with termination block
    print("\n[%s] Execution finished in %s\n" % (time.strftime(TIME_FORMAT),
                                                 datetime.timedelta(seconds=int(math.ceil(time.time() - execution_start)))))
    print("** Additional information and next steps at %s **\n" % documentationURL)
    log.info("zencheckdbstats completed in %1.2f seconds", time.time() - execution_start)
    log.info("############################################################")
    sys.exit(0)
Пример #12
0
def main():
    '''Performs reindex call on different DMD categories (used to be a part of zencatalogscan)'''

    execution_start = time.time()
    scriptName = os.path.basename(__file__).split('.')[0]
    parser = ZenToolboxUtils.parse_options(scriptVersion, scriptName + scriptSummary + documentationURL)
    # Add in any specific parser arguments for %scriptName
    parser.add_argument("-l", "--list", action="store_true", default=False,
                        help="output all supported reIndex() types")
    parser.add_argument("-t", "--type", action="store", default="",
                        help="specify which type to reIndex()")
    cli_options = vars(parser.parse_args())
    log, logFileName = ZenToolboxUtils.configure_logging(scriptName, scriptVersion, cli_options['tmpdir'])
    log.info("Command line options: %s" % (cli_options))
    if cli_options['debug']:
        log.setLevel(logging.DEBUG)

    print "\n[%s] Initializing %s v%s (detailed log at %s)" % \
          (time.strftime("%Y-%m-%d %H:%M:%S"), scriptName, scriptVersion, logFileName)

    # Attempt to get the zenoss.toolbox lock before any actions performed
    if not ZenToolboxUtils.get_lock("zenoss.toolbox", log):
        sys.exit(1)

    # Obtain dmd ZenScriptBase connection
    dmd = ZenScriptBase(noopts=True, connect=True).dmd
    log.debug("ZenScriptBase connection obtained")

    any_issue = False

    # Else build list of catalogs, then process catalog(s) and perform reindex if --fix
    types_to_reIndex = {
        'Devices': 'dmd.Devices',
        'Events': 'dmd.Events',
        'Manufacturers': 'dmd.Manufacturers',
        'Networks': 'dmd.Networks',
        'Services': 'dmd.Services',
        'DeviceSearch': ' dmd.Devices.deviceSearch'
        }

    if cli_options['list'] or not cli_options['type'] :
        # Output list of present catalogs to the UI, perform no further operations
        print "List of dmd types that support reIndex() calls from this script:\n"
        print "\n".join(types_to_reIndex.keys())
        log.info("Zenreindextool finished - list of supported types output to CLI")
        exit(1)

    if cli_options['type'] in types_to_reIndex.keys():
        any_issue = reindex_dmd_objects(cli_options['type'], types_to_reIndex[cli_options['type']], dmd, log)
    else:
        print("Type '%s' unrecognized - unable to reIndex()" % (cli_options['type']))
        log.error("CLI input '%s' doesn't match recognized types" % (cli_options['type']))
        exit(1)

    # Print final status summary, update log file with termination block
    print("\n[%s] Execution finished in %s\n" % (time.strftime("%Y-%m-%d %H:%M:%S"),
                                                 datetime.timedelta(seconds=int(time.time() - execution_start))))
    log.info("zenindextool completed in %1.2f seconds" % (time.time() - execution_start))
    log.info("############################################################")

    if any_issue:
        print("** WARNING ** Issues were encountered - Consult KB article at")
        print("      https://support.zenoss.com/hc/en-us/articles/203263689\n")
        sys.exit(1)

    sys.exit(0)
Пример #13
0
def main():
    '''Scans zodb objects for ZenRelations issues.  If --fix, attempts repair.'''

    execution_start = time.time()
    scriptName = os.path.basename(__file__).split('.')[0]
    parser = ZenToolboxUtils.parse_options(scriptVersion, scriptName + scriptSummary + documentationURL)
    # Add in any specific parser arguments for %scriptName
    parser.add_argument("-f", "--fix", action="store_true", default=False,
                        help="attempt to remove any invalid references")
    parser.add_argument("-n", "--cycles", action="store", default="2", type=int,
                        help="maximum times to cycle (with --fix)")
    parser.add_argument("-u", "--unlimitedram", action="store_true", default=False,
                        help="skip transaction.abort() - unbounded RAM, ~40%% faster")
    cli_options = vars(parser.parse_args())
    log, logFileName = ZenToolboxUtils.configure_logging(scriptName, scriptVersion, cli_options['tmpdir'])
    log.info("Command line options: %s" % (cli_options))
    if cli_options['debug']:
        log.setLevel(logging.DEBUG)

    print "\n[%s] Initializing %s v%s (detailed log at %s)" % \
          (time.strftime("%Y-%m-%d %H:%M:%S"), scriptName, scriptVersion, logFileName)

    # Attempt to get the zenoss.toolbox lock before any actions performed
    if not ZenToolboxUtils.get_lock("zenoss.toolbox", log):
        sys.exit(1)

    # Obtain dmd ZenScriptBase connection
    dmd = ZenScriptBase(noopts=True, connect=True).dmd
    log.debug("ZenScriptBase connection obtained")

    counters = {
        'item_count': ZenToolboxUtils.Counter(0),
        'error_count': ZenToolboxUtils.Counter(0),
        'repair_count': ZenToolboxUtils.Counter(0)
        }

    scan_relationships(cli_options['fix'], cli_options['cycles'], cli_options['unlimitedram'], dmd, log, counters)

    if not cli_options['skipEvents']:
        if counters['error_count'].value():
            eventSeverity = 4
            eventSummaryMsg = "%s encountered %d errors (took %1.2f seconds)" % \
                               (scriptName, counters['error_count'].value(), (time.time() - execution_start))
        else:
            eventSeverity = 2
            eventSummaryMsg = "%s completed without errors (took %1.2f seconds)" % \
                               (scriptName, (time.time() - execution_start))

        ZenToolboxUtils.send_summary_event(
            eventSummaryMsg, eventSeverity,
            scriptName, "executionStatus",
            documentationURL, dmd
        )

    # Print final status summary, update log file with termination block
    log.info("zenrelationscan examined %d objects, encountered %d errors, and attempted %d repairs",
             counters['item_count'].value(), counters['error_count'].value(), counters['repair_count'].value())
    print("\n[%s] Execution finished in %s\n" % (strftime("%Y-%m-%d %H:%M:%S", localtime()),
           datetime.timedelta(seconds=int(time.time() - execution_start))))
    log.info("zenrelationscan completed in %1.2f seconds" % (time.time() - execution_start))
    log.info("############################################################")

    if ((counters['error_count'].value() > 0) and not cli_options['fix']):
        print("** WARNING ** Issues were detected - Consult KB article at")
        print("      https://support.zenoss.com/hc/en-us/articles/203121165\n")
        sys.exit(1)
    else:
        sys.exit(0)
Пример #14
0
def main():
    """Scans catalogs for broken references.  If --fix, attempts to remove broken references."""

    executionStart = time.time()
    scriptName = os.path.basename(__file__).split('.')[0]
    parser = ZenToolboxUtils.parse_options(
        scriptVersion, scriptName + scriptSummary + documentationURL)
    # Add in any specific parser arguments for %scriptName
    parser.add_argument("-f",
                        "--fix",
                        action="store_true",
                        default=False,
                        help="attempt to remove any invalid references")
    parser.add_argument("-n",
                        "--cycles",
                        action="store",
                        default="12",
                        type=int,
                        help="maximum times to cycle (with --fix, <= 12)")
    parser.add_argument("-l",
                        "--list",
                        action="store_true",
                        default=False,
                        help="output all supported catalogs")
    parser.add_argument("-c",
                        "--catalog",
                        action="store",
                        default="",
                        help="only scan/fix specified catalog")
    cliOptions = vars(parser.parse_args())
    log, logFileName = ZenToolboxUtils.configure_logging(
        scriptName, scriptVersion, cliOptions['tmpdir'])
    log.info("Command line options: %s" % (cliOptions))
    if cliOptions['debug']:
        log.setLevel(logging.DEBUG)

    print "\n[%s] Initializing %s v%s (detailed log at %s)" % \
          (time.strftime("%Y-%m-%d %H:%M:%S"), scriptName, scriptVersion, logFileName)

    # Attempt to get the zenoss.toolbox lock before any actions performed
    if not ZenToolboxUtils.get_lock("zenoss.toolbox", log):
        sys.exit(1)

    # Obtain dmd ZenScriptBase connection
    dmd = ZenScriptBase(noopts=True, connect=True).dmd
    log.debug("ZenScriptBase connection obtained")

    anyIssue = False
    global maxCycles
    if cliOptions['fix']:
        if cliOptions['cycles'] > 12:
            maxCycles = 12
        else:
            maxCycles = cliOptions['cycles']
    else:
        maxCycles = 1

    validCatalogList = build_catalog_list(dmd, log)
    if cliOptions['list']:
        print "List of supported Zenoss catalogs to examine:\n"
        for item in validCatalogList:
            print item.prettyName
        log.info(
            "Zencatalogscan finished - list of supported catalogs output to CLI"
        )
    else:
        if cliOptions['catalog']:
            foundItem = False
            for item in validCatalogList:
                if cliOptions['catalog'] == item.prettyName:
                    foundItem = True
                    anyIssue = scan_catalog(item, cliOptions['fix'], dmd, log,
                                            not cliOptions['skipEvents'])
            if not foundItem:
                print("Catalog '%s' unrecognized - unable to scan" %
                      (cliOptions['catalog']))
                log.error("CLI input '%s' doesn't match recognized catalogs" %
                          (cliOptions['catalog']))
                exit(1)
        else:
            for item in validCatalogList:
                anyIssue = scan_catalog(
                    item, cliOptions['fix'], dmd, log,
                    not cliOptions['skipEvents']) or anyIssue

    # Print final status summary, update log file with termination block
    print("\n[%s] Execution finished in %s\n" %
          (time.strftime("%Y-%m-%d %H:%M:%S"),
           datetime.timedelta(seconds=int(time.time() - executionStart))))
    log.info("zencatalogscan completed in %1.2f seconds" %
             (time.time() - executionStart))
    log.info("############################################################")

    if not cliOptions['skipEvents']:
        if anyIssue:
            eventSummaryMsg = "%s encountered errors (took %1.2f seconds)" % (
                scriptName, (time.time() - executionStart))
            eventSeverity = 4
        else:
            eventSummaryMsg = "%s completed without errors (took %1.2f seconds)" % (
                scriptName, (time.time() - executionStart))
            eventSeverity = 2

        ZenToolboxUtils.send_summary_event(eventSummaryMsg, eventSeverity,
                                           scriptName, "executionStatus",
                                           documentationURL, dmd)

    if anyIssue and not cliOptions['fix']:
        print("** WARNING ** Issues were detected - Consult KB article at")
        print("      https://support.zenoss.com/hc/en-us/articles/203118075\n")
        sys.exit(1)
    else:
        sys.exit(0)
Пример #15
0
def main():
    """Scans catalogs for broken references.  If --fix, attempts to remove broken references."""

    executionStart = time.time()
    scriptName = os.path.basename(__file__).split('.')[0]
    parser = ZenToolboxUtils.parse_options(scriptVersion, scriptName + scriptSummary + documentationURL)
    # Add in any specific parser arguments for %scriptName
    parser.add_argument("-f", "--fix", action="store_true", default=False,
                        help="attempt to remove any invalid references")
    parser.add_argument("-n", "--cycles", action="store", default="12", type=int,
                        help="maximum times to cycle (with --fix, <= 12)")
    parser.add_argument("-l", "--list", action="store_true", default=False,
                        help="output all supported catalogs")
    parser.add_argument("-c", "--catalog", action="store", default="",
                        help="only scan/fix specified catalog")
    cliOptions = vars(parser.parse_args())
    log, logFileName = ZenToolboxUtils.configure_logging(scriptName, scriptVersion, cliOptions['tmpdir'])
    log.info("Command line options: %s" % (cliOptions))
    if cliOptions['debug']:
        log.setLevel(logging.DEBUG)

    print "\n[%s] Initializing %s v%s (detailed log at %s)" % \
          (time.strftime("%Y-%m-%d %H:%M:%S"), scriptName, scriptVersion, logFileName)

    # Attempt to get the zenoss.toolbox lock before any actions performed
    if not ZenToolboxUtils.get_lock("zenoss.toolbox", log):
        sys.exit(1)

    # Obtain dmd ZenScriptBase connection
    dmd = ZenScriptBase(noopts=True, connect=True).dmd
    log.debug("ZenScriptBase connection obtained")

    anyIssue = False
    global maxCycles
    if cliOptions['fix']:
        if cliOptions['cycles'] > 12:
            maxCycles = 12
        else:
            maxCycles = cliOptions['cycles']
    else:
        maxCycles = 1

    validCatalogList = build_catalog_list(dmd, log)
    if cliOptions['list']:
        print "List of supported Zenoss catalogs to examine:\n"
        for item in validCatalogList:
            print item.prettyName
        log.info("Zencatalogscan finished - list of supported catalogs output to CLI")
    else:
        if cliOptions['catalog']:
            foundItem = False
            for item in validCatalogList:
                if cliOptions['catalog'] == item.prettyName:
                    foundItem = True
                    anyIssue = scan_catalog(item, cliOptions['fix'],
                                            dmd, log, not cliOptions['skipEvents'])
            if not foundItem:
                print("Catalog '%s' unrecognized - unable to scan" % (cliOptions['catalog']))
                log.error("CLI input '%s' doesn't match recognized catalogs" % (cliOptions['catalog']))
                exit(1)
        else:
            for item in validCatalogList:
                anyIssue = scan_catalog(item, cliOptions['fix'],
                                        dmd, log, not cliOptions['skipEvents']) or anyIssue

    # Print final status summary, update log file with termination block
    print("\n[%s] Execution finished in %s\n" % (time.strftime("%Y-%m-%d %H:%M:%S"),
                                                 datetime.timedelta(seconds=int(time.time() - executionStart))))
    log.info("zencatalogscan completed in %1.2f seconds" % (time.time() - executionStart))
    log.info("############################################################")

    if not cliOptions['skipEvents']:
        if anyIssue:
            eventSummaryMsg = "%s encountered errors (took %1.2f seconds)" % (scriptName, (time.time() - executionStart))
            eventSeverity = 4
        else:
            eventSummaryMsg = "%s completed without errors (took %1.2f seconds)" % (scriptName, (time.time() - executionStart))
            eventSeverity = 2

        ZenToolboxUtils.send_summary_event(
            eventSummaryMsg, eventSeverity,
            scriptName, "executionStatus",
            documentationURL, dmd
        )

    if anyIssue and not cliOptions['fix']:
        print("** WARNING ** Issues were detected - Consult KB article at")
        print("      https://support.zenoss.com/hc/en-us/articles/203118075\n")
        sys.exit(1)
    else:
        sys.exit(0)
Пример #16
0
def global_catalog_paths_to_uids(catalogObject, fix, dmd, log, createEvents):
    """Scan through global_catalog verifying consistency of rids"""

    catalogReference = eval(catalogObject.dmdPath)._catalog
    catalogObject.initialSize = len(catalogReference.paths)

    if (catalogObject.initialSize > 50):
        progressBarChunkSize = (catalogObject.initialSize // 50) + 1
    else:
        progressBarChunkSize = 1

    log.info(
        "Examining global_catalog._catalog.paths for consistency against ._catalog.uids"
    )
    print("[%s] Examining %-35s (%d Objects)" %
          (time.strftime("%Y-%m-%d %H:%M:%S"),
           "global_catalog 'paths to uids'", catalogObject.initialSize))

    currentCycle = 0

    while (currentCycle < maxCycles):
        currentCycle += 1
        catalogObject.runResults[currentCycle] = {
            'itemCount': ZenToolboxUtils.Counter(0),
            'errorCount': ZenToolboxUtils.Counter(0),
            'repairCount': ZenToolboxUtils.Counter(0)
        }
        log.info("Beginning cycle %d for global_catalog 'paths to uids'" %
                 (currentCycle))
        scan_progress_message(False, fix, currentCycle,
                              "global_catalog 'paths to uids'", 0, 0, log)

        try:
            broken_rids = []
            for rid, path in catalogReference.paths.iteritems():
                catalogObject.runResults[currentCycle]['itemCount'].increment()
                if (catalogObject.runResults[currentCycle]
                    ['itemCount'].value() % progressBarChunkSize) == 0:
                    chunkNumber = catalogObject.runResults[currentCycle][
                        'itemCount'].value() // progressBarChunkSize
                    scan_progress_message(
                        False, fix, currentCycle,
                        "global_catalog 'paths to uids'",
                        catalogObject.runResults[currentCycle]
                        ['errorCount'].value(), chunkNumber, log)
                if path not in catalogReference.uids:
                    catalogObject.runResults[currentCycle][
                        'errorCount'].increment()
                    broken_rids.append(rid)

        except Exception, e:
            log.exception(e)

        scan_progress_message(
            True, fix, currentCycle,
            "global_catalog 'paths to uids' consistency",
            catalogObject.runResults[currentCycle]['errorCount'].value(),
            chunkNumber, log)

        if fix:
            if catalogObject.runResults[currentCycle]['errorCount'].value(
            ) > 0:
                log.info("Attempting to repair %d detected issues",
                         len(broken_rids))
                for item in broken_rids:
                    try:
                        catalogObject.runResults[currentCycle][
                            'repairCount'].increment()
                        catalogReference.paths.pop(item)
                        catalogReference.data.pop(item)
                        catalogReference._p_changed = True
                        transaction.commit()
                    except:
                        pass
            else:
                break
            if currentCycle > 1:
                if catalogObject.runResults[currentCycle]['errorCount'].value(
                ) == catalogObject.runResults[currentCycle -
                                              1]['errorCount'].value():
                    break
        # Final transaction.abort() to try and free up used memory
        log.debug("Calling transaction.abort() to minimize memory footprint")
        transaction.abort()
Пример #17
0
def main():
    """ Scans through zodb hierarchy (from user-supplied path, defaults to /,  checking for PKEs """

    execution_start = time.time()
    scriptName = os.path.basename(__file__).split('.')[0]
    parser = ZenToolboxUtils.parse_options(scriptVersion, scriptName + scriptSummary + documentationURL)
    # Add in any specific parser arguments for %scriptName
    parser.add_argument("-f", "--fix", action="store_true", default=False,
                        help="attempt to fix ZenRelationship objects")
    parser.add_argument("-n", "--cycles", action="store", default="2", type=int,
                        help="maximum times to cycle (with --fix)")
    parser.add_argument("-p", "--path", action="store", default="/", type=str,
                        help="base path to scan from (Devices.Server)?")
    parser.add_argument("-u", "--unlimitedram", action="store_true", default=False,
                        help="skip transaction.abort() - unbounded RAM, ~40%% faster")
    cli_options = vars(parser.parse_args())
    log, logFileName = ZenToolboxUtils.configure_logging(scriptName, scriptVersion, cli_options['tmpdir'])
    log.info("Command line options: %s" % (cli_options))
    if cli_options['debug']:
        log.setLevel(logging.DEBUG)

    print "\n[%s] Initializing %s v%s (detailed log at %s)" % \
          (time.strftime("%Y-%m-%d %H:%M:%S"), scriptName, scriptVersion, logFileName)

    # Attempt to get the zenoss.toolbox lock before any actions performed
    if not ZenToolboxUtils.get_lock("zenoss.toolbox", log):
        sys.exit(1)

    # Obtain dmd ZenScriptBase connection
    dmd = ZenScriptBase(noopts=True, connect=True).dmd
    log.debug("ZenScriptBase connection obtained")

    counters = {
        'item_count': ZenToolboxUtils.Counter(0),
        'error_count': ZenToolboxUtils.Counter(0),
        'repair_count': ZenToolboxUtils.Counter(0)
        }

    processed_path = re.split("[./]", cli_options['path'])
    if processed_path[0] == "app":
        processed_path = processed_path[1:]
    processed_path = '/'.join(processed_path) if processed_path else '/'

    try:
        folder = dmd.getObjByPath(processed_path)
    except KeyError:
        print "Invalid path: %s" % (cli_options['path'])
    else:
        print("[%s] Examining items under the '%s' path (%s):" %
              (strftime("%Y-%m-%d %H:%M:%S", localtime()), cli_options['path'], folder))
        log.info("Examining items under the '%s' path (%s)", cli_options['path'], folder)
        findPOSKeyErrors(folder, cli_options['fix'], cli_options['unlimitedram'], dmd, log, counters, cli_options['cycles'])
        print

    print("\n[%s] Execution finished in %s\n" %
          (strftime("%Y-%m-%d %H:%M:%S", localtime()),
           datetime.timedelta(seconds=int(time.time() - execution_start))))
    log.info("findposkeyerror completed in %1.2f seconds", time.time() - execution_start)
    log.info("############################################################")

    if not cli_options['skipEvents']:
        if counters['error_count'].value():
            eventSeverity = 4
            eventSummaryMsg = "%s encountered %d errors (took %1.2f seconds)" % \
                               (scriptName, counters['error_count'].value(), (time.time() - execution_start))
        else:
            eventSeverity = 2
            eventSummaryMsg = "%s completed without errors (took %1.2f seconds)" % \
                               (scriptName, (time.time() - execution_start))

        ZenToolboxUtils.send_summary_event(
            eventSummaryMsg, eventSeverity,
            scriptName, "executionStatus",
            documentationURL, dmd
        )

    if ((counters['error_count'].value() > 0) and not cli_options['fix']):
        print("** WARNING ** Issues were detected - Consult KB article at")
        print("      https://support.zenoss.com/hc/en-us/articles/203117795\n")
        sys.exit(1)
    else:
        sys.exit(0)