From bb268eb27f2effcdc2f5623f779c728e3f8b8d02 Mon Sep 17 00:00:00 2001 From: Mark Reynolds Date: Thu, 28 Sep 2017 16:53:42 -0400 Subject: [PATCH] Ticket 100 - Add ENV var for preserving core files Description: We need a way to tell lib389 to preserve cores files in the finalizer function for each topology. https://pagure.io/lib389/issue/100 Reviewed by: ? --- lib389/topologies.py | 73 ++++++++++++++++++++++++++++++++++++++++++++-------- 1 file changed, 62 insertions(+), 11 deletions(-) diff --git a/lib389/topologies.py b/lib389/topologies.py index 674f1d0..071a9a8 100644 --- a/lib389/topologies.py +++ b/lib389/topologies.py @@ -9,15 +9,16 @@ import os import logging import time - +import glob import pytest - +from shutil import copyfile from lib389 import DirSrv from lib389.utils import generate_ds_params from lib389.replica import Replicas from lib389._constants import (args_instance, SER_HOST, SER_PORT, SER_SERVERID_PROP, SER_CREATION_SUFFIX, ReplicaRole, DEFAULT_SUFFIX, REPLICA_ID) +PRESERVE_CORES = os.getenv('PRESERVE_CORES', default=False) DEBUGGING = os.getenv('DEBUGGING', default=False) if DEBUGGING: logging.getLogger(__name__).setLevel(logging.DEBUG) @@ -49,7 +50,7 @@ def create_topology(topo_dict): # Create instances for role in topo_dict.keys(): - for inst_num in range(1, topo_dict[role]+1): + for inst_num in range(1, topo_dict[role] + 1): instance_data = generate_ds_params(inst_num, role) if DEBUGGING: instance = DirSrv(verbose=True) @@ -93,11 +94,11 @@ def create_topology(topo_dict): continue # Create agreements: master -> masters, consumers - for inst_num_from in range(1, topo_dict[role_from]+1): + for inst_num_from in range(1, topo_dict[role_from] + 1): roles_to = [ReplicaRole.MASTER, ReplicaRole.CONSUMER] for role_to in [role for role in topo_dict if role in roles_to]: - for inst_num_to in range(1, topo_dict[role_to]+1): + for inst_num_to in range(1, topo_dict[role_to] + 1): # Exclude the instance we created it from if role_from != role_to or inst_num_from != inst_num_to: inst_from_id = "{}{}".format(role_from.name.lower(), inst_num_from) @@ -129,36 +130,69 @@ def create_topology(topo_dict): return TopologyMain(standalones=ins, masters=ms, consumers=cs) +def preserve_core_files(instances): + """Check the logs directory of every instance, and rename and copy all + core files to the preservation location + + @param instances - dictionary of instances to look for cores + """ + + # Validate preservation directory + try: + os.path.exists(PRESERVE_CORES) + except: + log.fatal("The preservation directory does not exist: {}".format(PRESERVE_CORES)) + return + + # Look for core files from all the instances + for inst in instances.values(): + svr_core_pattern = "{}/*core*".format(inst.ds_paths.error_log.replace('/errors', '')) + for core in glob.glob(svr_core_pattern): + # Found a core file, rename/copy it + timestamp = time.strftime("%Y-%m-%d--%H:%M:%S", time.gmtime()) + new_core = "{}/{}-{}.core".format(PRESERVE_CORES, inst.serverid, timestamp) + copyfile(core, new_core) + time.sleep(1) # Sleep to make sure our timestamp advances + log.info("Found core file for instance: " + + "{} - core: {} moved to: {}".format(inst.serverid, core, new_core)) + + class TopologyMain(object): def __init__(self, standalones=None, masters=None, consumers=None, hubs=None): + self.all_replicas = {} self.all_insts = {} + self.standalone = {} + self.ins = {} if standalones: if isinstance(standalones, dict): self.ins = standalones + self.all_insts.update(self.ins) else: self.standalone = standalones + self.all_insts.update({self.standalone.serverid: self.standalone}) if masters: self.ms = masters - self.all_insts.update(self.ms) + self.all_replicas.update(self.ms) if consumers: self.cs = consumers - self.all_insts.update(self.cs) + self.all_replicas.update(self.cs) if hubs: self.hs = hubs - self.all_insts.update(self.hs) + self.all_replicas.update(self.hs) + self.all_insts.update(self.all_replicas) def pause_all_replicas(self): """Pause all agreements in the class instance""" - for inst in self.all_insts.values(): + for inst in self.all_replicas.values(): for agreement in inst.agreement.list(suffix=DEFAULT_SUFFIX): inst.agreement.pause(agreement.dn) def resume_all_replicas(self): """Resume all agreements in the class instance""" - for inst in self.all_insts.values(): + for inst in self.all_replicas.values(): for agreement in inst.agreement.list(suffix=DEFAULT_SUFFIX): inst.agreement.resume(agreement.dn) @@ -170,6 +204,8 @@ def topology_st(request): topology = create_topology({ReplicaRole.STANDALONE: 1}) def fin(): + if PRESERVE_CORES: + preserve_core_files(topology.all_insts) if DEBUGGING: topology.standalone.stop() else: @@ -186,6 +222,8 @@ def topology_i2(request): topology = create_topology({ReplicaRole.STANDALONE: 2}) def fin(): + if PRESERVE_CORES: + preserve_core_files(topology.all_insts) if DEBUGGING: map(lambda inst: inst.stop(), topology.all_insts.values()) else: @@ -202,6 +240,8 @@ def topology_i3(request): topology = create_topology({ReplicaRole.STANDALONE: 3}) def fin(): + if PRESERVE_CORES: + preserve_core_files(topology.all_insts) if DEBUGGING: map(lambda inst: inst.stop(), topology.all_insts.values()) else: @@ -221,6 +261,8 @@ def topology_m1c1(request): replicas.test(DEFAULT_SUFFIX, topology.cs["consumer1"]) def fin(): + if PRESERVE_CORES: + preserve_core_files(topology.all_insts) if DEBUGGING: map(lambda inst: inst.stop(), topology.all_insts.values()) else: @@ -239,6 +281,8 @@ def topology_m2(request): replicas.test(DEFAULT_SUFFIX, topology.ms["master2"]) def fin(): + if PRESERVE_CORES: + preserve_core_files(topology.all_insts) if DEBUGGING: map(lambda inst: inst.stop(), topology.all_insts.values()) else: @@ -257,6 +301,8 @@ def topology_m3(request): replicas.test(DEFAULT_SUFFIX, topology.ms["master3"]) def fin(): + if PRESERVE_CORES: + preserve_core_files(topology.all_insts) if DEBUGGING: map(lambda inst: inst.stop(), topology.all_insts.values()) else: @@ -275,6 +321,8 @@ def topology_m4(request): replicas.test(DEFAULT_SUFFIX, topology.ms["master4"]) def fin(): + if PRESERVE_CORES: + preserve_core_files(topology.all_insts) if DEBUGGING: map(lambda inst: inst.stop(), topology.all_insts.values()) else: @@ -294,6 +342,8 @@ def topology_m2c2(request): replicas.test(DEFAULT_SUFFIX, topology.cs["consumer1"]) def fin(): + if PRESERVE_CORES: + preserve_core_files(topology.all_insts) if DEBUGGING: map(lambda inst: inst.stop(), topology.all_insts.values()) else: @@ -309,7 +359,6 @@ def topology_m1h1c1(request): roles = (ReplicaRole.MASTER, ReplicaRole.HUB, ReplicaRole.CONSUMER) instances = [] - replica_dict = {} # Create instances for role in roles: @@ -372,6 +421,8 @@ def topology_m1h1c1(request): master.clearTmpDir(__file__) def fin(): + if PRESERVE_CORES: + preserve_core_files(instances) if DEBUGGING: map(lambda inst: inst.stop(), instances) else: -- 2.9.5