| #!/usr/bin/env python |
| |
| import argparse |
| import json |
| import sys |
| import jsonschema |
| |
| r""" |
| Validates the phosphor-regulators configuration file. Checks it against a JSON |
| schema as well as doing some extra checks that can't be encoded in the schema. |
| """ |
| |
| def handle_validation_error(): |
| sys.exit("Validation failed.") |
| |
| def check_duplicate_rule_id(config_json): |
| r""" |
| Check that there aren't any "rule" elements with the same 'id' field. |
| config_json: Configuration file JSON |
| """ |
| rule_ids = [] |
| for rule in config_json.get('rules', {}): |
| rule_id = rule['id'] |
| if rule_id in rule_ids: |
| sys.stderr.write("Error: Duplicate rule ID.\n"+\ |
| "Found multiple rules with the ID "+rule_id+'\n') |
| handle_validation_error() |
| else: |
| rule_ids.append(rule_id) |
| |
| def check_duplicate_chassis_number(config_json): |
| r""" |
| Check that there aren't any "chassis" elements with the same 'number' field. |
| config_json: Configuration file JSON |
| """ |
| numbers = [] |
| for chassis in config_json.get('chassis', {}): |
| number = chassis['number'] |
| if number in numbers: |
| sys.stderr.write("Error: Duplicate chassis number.\n"+\ |
| "Found multiple chassis with the number "+str(number)+'\n') |
| handle_validation_error() |
| else: |
| numbers.append(number) |
| |
| def check_duplicate_device_id(config_json): |
| r""" |
| Check that there aren't any "devices" with the same 'id' field. |
| config_json: Configuration file JSON |
| """ |
| device_ids = [] |
| for chassis in config_json.get('chassis', {}): |
| for device in chassis.get('devices', {}): |
| device_id = device['id'] |
| if device_id in device_ids: |
| sys.stderr.write("Error: Duplicate device ID.\n"+\ |
| "Found multiple devices with the ID "+device_id+'\n') |
| handle_validation_error() |
| else: |
| device_ids.append(device_id) |
| |
| def check_duplicate_rail_id(config_json): |
| r""" |
| Check that there aren't any "rails" with the same 'id' field. |
| config_json: Configuration file JSON |
| """ |
| rail_ids = [] |
| for chassis in config_json.get('chassis', {}): |
| for device in chassis.get('devices', {}): |
| for rail in device.get('rails', {}): |
| rail_id = rail['id'] |
| if rail_id in rail_ids: |
| sys.stderr.write("Error: Duplicate rail ID.\n"+\ |
| "Found multiple rails with the ID "+rail_id+'\n') |
| handle_validation_error() |
| else: |
| rail_ids.append(rail_id) |
| |
| def check_for_duplicates(config_json): |
| r""" |
| Check for duplicate ID. |
| """ |
| check_duplicate_rule_id(config_json) |
| |
| check_duplicate_chassis_number(config_json) |
| |
| check_duplicate_device_id(config_json) |
| |
| check_duplicate_rail_id(config_json) |
| |
| def validate_schema(config, schema): |
| r""" |
| Validates the specified config file using the specified |
| schema file. |
| |
| config: Path of the file containing the config JSON |
| schema: Path of the file containing the schema JSON |
| """ |
| |
| with open(config) as config_handle: |
| config_json = json.load(config_handle) |
| |
| with open(schema) as schema_handle: |
| schema_json = json.load(schema_handle) |
| |
| try: |
| jsonschema.validate(config_json, schema_json) |
| except jsonschema.ValidationError as e: |
| print(e) |
| handle_validation_error() |
| |
| return config_json |
| |
| if __name__ == '__main__': |
| |
| parser = argparse.ArgumentParser( |
| description='phosphor-regulators configuration file validator') |
| |
| parser.add_argument('-s', '--schema-file', dest='schema_file', |
| help='The phosphor-regulators schema file') |
| |
| parser.add_argument('-c', '--configuration-file', dest='configuration_file', |
| help='The phosphor-regulators configuration file') |
| |
| args = parser.parse_args() |
| |
| if not args.schema_file: |
| parser.print_help() |
| sys.exit("Error: Schema file is required.") |
| if not args.configuration_file: |
| parser.print_help() |
| sys.exit("Error: Configuration file is required.") |
| |
| config_json = validate_schema(args.configuration_file, args.schema_file) |
| check_for_duplicates(config_json) |