def test_section_config(_file, network_os, get_text_data, get_python_data):  # pylint: disable=redefined-outer-name
    truncate_file = os.path.join(MOCK_DIR, _file[: -len(TXT_FILE)])

    device_cfg = get_text_data(os.path.join(MOCK_DIR, _file))
    received_data = get_text_data(truncate_file + "_received.txt")
    feature = get_python_data(truncate_file + "_feature.py", "feature")
    assert compliance.section_config(feature, device_cfg, network_os) == received_data
Exemple #2
0
def run_compliance(  # pylint: disable=too-many-arguments,too-many-locals
    task: Task,
    logger,
    global_settings,
    backup_root_path,
    intended_root_folder,
    features,
) -> Result:
    """Prepare data for compliance task.

    Args:
        task (Task): Nornir task individual object

    Returns:
        result (Result): Result from Nornir task
    """
    obj = task.host.data["obj"]

    compliance_obj = GoldenConfig.objects.filter(device=obj).first()
    if not compliance_obj:
        compliance_obj = GoldenConfig.objects.create(device=obj)
    compliance_obj.compliance_last_attempt_date = task.host.defaults.data[
        "now"]
    compliance_obj.save()

    intended_path_template_obj = check_jinja_template(
        obj, logger, global_settings.intended_path_template)

    intended_file = os.path.join(intended_root_folder,
                                 intended_path_template_obj)

    if not os.path.exists(intended_file):
        logger.log_failure(
            obj,
            f"Unable to locate intended file for device at {intended_file}")
        raise NornirNautobotException()

    backup_template = check_jinja_template(
        obj, logger, global_settings.backup_path_template)
    backup_file = os.path.join(backup_root_path, backup_template)

    if not os.path.exists(backup_file):
        logger.log_failure(
            obj, f"Unable to locate backup file for device at {backup_file}")
        raise NornirNautobotException()

    platform = obj.platform.slug
    if not features.get(platform):
        logger.log_failure(
            obj,
            f"There is no `user` defined feature mapping for platform slug {platform}."
        )
        raise NornirNautobotException()

    if get_platform(platform) not in parser_map.keys():
        logger.log_failure(
            obj,
            f"There is currently no parser support for platform slug {get_platform(platform)}."
        )
        raise NornirNautobotException()

    backup_cfg = _open_file_config(backup_file)
    intended_cfg = _open_file_config(intended_file)

    # TODO: Make this atomic with compliance_obj step.
    for feature in features[obj.platform.slug]:
        # using update_or_create() method to conveniently update actual obj or create new one.
        ConfigCompliance.objects.update_or_create(
            device=obj,
            rule=feature["obj"],
            defaults={
                "actual":
                section_config(feature, backup_cfg, get_platform(platform)),
                "intended":
                section_config(feature, intended_cfg, get_platform(platform)),
                "missing":
                "",
                "extra":
                "",
            },
        )

    compliance_obj.compliance_last_success_date = task.host.defaults.data[
        "now"]
    compliance_obj.compliance_config = "\n".join(
        diff_files(backup_file, intended_file))
    compliance_obj.save()
    logger.log_success(obj, "Successfully tested compliance.")

    return Result(host=task.host)