Пример #1
0
def check_secrets(docker_compose_path: str, no_prompt: bool = False):
    log.info("Checking Coral secrets...")
    required_secrets = swarmadmin.get_objs_from_compose(
        "secret", docker_compose_path)
    missing_secrets = list(
        filter(lambda x: not swarmadmin.obj_exists("secret", x),
               required_secrets))

    if len(missing_secrets) > 0:
        log.info("Some required secrets are missing")

        if no_prompt:
            raise Exception(
                "When running in test mode, all secrets must be manually created beforehand."
            )
        else:
            prompt_secrets(missing_secrets)
    else:
        if not no_prompt:
            question = "All required secrets are defined. Do you wish to redefine them? (y/n) "
            answer = fish.valid_answer_from_prompt(
                question, valid_answers=settings.get("prompt_boolean_answers"))
            log_file.info(question + answer)

            if fish.user_prompt_yes(answer):
                manage.remove_coral_objects("secret",
                                            silent=True,
                                            list_found_objs=False,
                                            prompt=False)
                prompt_secrets(required_secrets)
Пример #2
0
def remove_coral_objects(obj_type: str,
                         silent: bool = False,
                         list_found_objs: bool = True,
                         prompt: bool = True,
                         is_dep: bool = False):
    if not silent:
        log.info(
            f"Removing{' dependent ' if is_dep else ' '}Coral {obj_type}s...")

    cleanup_params = settings.get("cleanup_params")[obj_type]
    rm_confirmation_msg, all_, quiet, format_, filters, force = [
        value for value in cleanup_params.values()
    ]

    obj_list = get_coral_objs(obj_type,
                              all_=all_,
                              quiet=quiet,
                              format_=f"\"{format_}\"",
                              filters=filters)

    if obj_list:
        bullets_obj_list = "\n".join(
            [f"- {line}" for line in obj_list.split("\n")])

        if list_found_objs and not silent:
            log.info(
                f"The following Coral {obj_type}s were found:\n{bullets_obj_list}"
            )
            log_stdout.info("")

        if prompt:
            question = f"{rm_confirmation_msg}\nAre you sure you want to remove these {obj_type}s? (y/n) "
            answer = fish.valid_answer_from_prompt(
                question, valid_answers=settings.get("prompt_boolean_answers"))
            log_file.info(question.replace("\n", " ") + answer)

        if not prompt or fish.user_prompt_yes(answer):
            remove_coral_obj_dependencies(obj_type, silent=silent)

            obj_ids = [
                i for i, j in (obj.split("\t") for obj in obj_list.split("\n"))
            ]
            if not silent: log.info(f"Removing {obj_type}s...")
            res = swarmadmin.rm(obj_type,
                                obj_ids,
                                force=force,
                                suppress_stdout=silent)
            fish.handle(res)
            if not silent: log.info(f"Done!")
    else:
        if not silent:
            log.info(f"No Coral {obj_type}s were found. Skipping...")
Пример #3
0
def update():
    question = "Coral will be stopped in order to perform the update. Do you wish to continue? (y/n) "
    answer = fish.valid_answer_from_prompt(
        question, valid_answers=settings.get("prompt_boolean_answers"))
    log_file.info(question + answer)

    if fish.user_prompt_yes(answer):
        docker_compose_path = settings.get("compose_path")
        original_compose_file = None

        log.info("Updating Coral Docker images...")

        # check if a current deployment is using dev images
        curr_depl_conf = deploy.get_curr_depl_config()
        if curr_depl_conf is not None:
            original_compose_file = fish.read_file(docker_compose_path)
            dev = curr_depl_conf["advanced"]["dev_images"]
            if dev:
                deploy.switch_to_dev_images(
                    docker_compose_path)  # switch to dev images

        try:
            registry_login()
            pull_coral_images(docker_compose_path)
        finally:
            if original_compose_file is not None:
                fish.write_file(original_compose_file, docker_compose_path)

        log_stdout.info("")
        log.info("Coral Docker images successfully updated!")

        curr_depl_conf = deploy.get_curr_depl_config()

        if (curr_depl_conf is None):
            log.info("Cannot start Coral. Please deploy first.")
        else:
            domain = curr_depl_conf["basic"][
                "domain"]  # needed for logs after deployment
            deploy.prepare(skip_depl_config=True,
                           is_update=True,
                           docker_compose_path=docker_compose_path,
                           domain=domain,
                           email=None,
                           cert_type=None,
                           stack_name=None,
                           no_prompt=True)
Пример #4
0
def check_skip_depl_config(no_prompt: bool = False):
    curr_depl_conf = get_curr_depl_config()

    if curr_depl_conf is None: return False

    curr_depl_conf = json.dumps(curr_depl_conf, indent=2)
    log.info(
        "Previous deployment configuration found:\n{0}".format(curr_depl_conf))

    if no_prompt:
        return True
    else:
        question = f"Do you wish to reuse the configuration above? (y/n) "
        answer = fish.valid_answer_from_prompt(
            question, valid_answers=settings.get("prompt_boolean_answers"))
        log_file.info(question + answer)

        return fish.user_prompt_yes(answer)
Пример #5
0
def check_central_mon(env_file_path: str, no_prompt: bool = False):
    log.info("Checking for central monitoring configuration...")
    central_mon_url = get_central_monitor_url()

    if (len(central_mon_url["value"]) == 0):
        log.warn(
            f"A central monitoring URL has not been defined in {env_file_path}, line {str(central_mon_url['index'] + 1)}.\nThe monitoring features described in the 'Coral Monitor Stack' section of README.md will be disabled."
        )

        if not no_prompt:
            question = "Do you wish to continue? (y/n) "
            answer = fish.valid_answer_from_prompt(
                question, valid_answers=settings.get("prompt_boolean_answers"))
            log_file.info(question + answer)

            if fish.user_prompt_no(answer):
                sys.exit(0)

        return False
    else:
        log.info(f"Using {central_mon_url['value']} for central monitoring...")
        return True
Пример #6
0
def exec_cmd_live(cmd, print_stdout=True, print_stderr=False, filter_stdout=False, overlay_keyword=None, timeout=None):
  # use file as pipe to allow for live printing of stdout/stderr
  with io.open("stdout.tmp", 'wb') as stdout_writer,\
    io.open("stderr.tmp", 'wb') as stderr_writer,\
    io.open("stdout.tmp", 'rb', 1) as stdout_reader,\
    io.open("stderr.tmp", 'rb', 1) as stderr_reader:

    prev_stdout = ""

    process = subprocess.Popen(cmd.split(" "), stdout=stdout_writer, stderr=stderr_writer)
    exit_code = None
    time_step = 0.5
    elapsed_time = 0

    while process.poll() is None:
      stdout = stdout_reader.read().decode('utf-8')
      stderr = stderr_reader.read().decode('utf-8')

      # filter out empty or duplicate lines
      if print_stdout and filter_stdout:
        if "\n" in stdout:
          stdout = list(filter(lambda x: x not in ["", "\n"], stdout.split("\n")))

        if stdout and stdout[0] != prev_stdout:
          stdout = stdout[0]
          prev_stdout = stdout

          if overlay_keyword is not None and overlay_keyword in stdout:
            sys.stdout.write(stdout + "\r") # overlay on top of previous line
          else:
            sys.stdout.write(stdout + "\n")

          # log stdout to file (excluding overlayed lines)
          if overlay_keyword not in stdout:
            log_file.info(stdout)
      else:
        if print_stdout: sys.stdout.write(stdout)
        if print_stderr: sys.stdout.write(stderr)

      time.sleep(time_step)
      elapsed_time += time_step

      if timeout and elapsed_time >= timeout:
        exit_code = 124
        break
    else:
      exit_code = process.returncode
      # read any remaining outpout
      if print_stdout: sys.stdout.write(stdout_reader.read().decode('utf-8'))

    result = {
      "cmd": cmd,
      "exit_code": exit_code,
      "stdout": stdout_reader.read().decode('utf-8'),
      "stderr": stderr_reader.read().decode('utf-8')
    }

  for file_ in glob.glob("*.tmp"):
    os.remove(file_)

  return result
Пример #7
0
def signal_handler(sig, frame):
    msg = "Cancelled by user. Exiting..."
    log_stdout.info("\n" + msg)
    log_file.info(msg)

    sys.exit(0)
Пример #8
0
            status = manage.start()
        elif parsed_args.stop:
            status = manage.stop()
        elif parsed_args.restart:
            status = manage.restart()

    if status == 1:
        log.info(
            "No Coral services were found (Coral stack is not currently deployed)"
        )


if __name__ == "__main__":
    try:
        log_stdout.info(settings.get_intro())
        log_file.info("EXEC: [ {0} ]".format(", ".join(sys.argv)))

        signal.signal(signal.SIGINT, signal_handler)

        skip_depl_config = False
        if "--deploy" in sys.argv:
            skip_depl_config = deploy.check_skip_depl_config(
                "--test" in sys.argv)
        parser = config_arg_parser()
        parsed_args = parse_args(parser, skip_depl_config)
        main(parsed_args, skip_depl_config)
    except (Exception, SystemExit) as e:
        e_name = type(e).__name__
        if e_name == "SystemExit":
            if e == 1: log_file.exception(e_name)
        else: