|
| 1 | +import yaml |
| 2 | +import argparse |
| 3 | +import json |
| 4 | +import os |
| 5 | + |
| 6 | + |
| 7 | +pseudo_params = ['AWS::AccountId', 'AWS::NotificationARNs', 'AWS::Partition', |
| 8 | + 'AWS::Region', 'AWS::StackId', 'AWS::StackName', 'AWS::URLSuffix'] |
| 9 | +none_param = 'AWS::NoValue' |
| 10 | +rules = [] |
| 11 | +ruleNames = [] |
| 12 | + |
| 13 | +def generate_config(input_path, input_format, output_format): |
| 14 | + files = (file for file in os.listdir(input_path) |
| 15 | + if os.path.isfile(os.path.join(input_path, file))) |
| 16 | + for file_name in files: |
| 17 | + if not file_name.endswith(input_format): |
| 18 | + continue |
| 19 | + with open(os.path.join(input_path, file_name)) as f: |
| 20 | + if input_format == 'yaml': |
| 21 | + data = yaml.load(f, Loader=yaml.FullLoader) |
| 22 | + generate_config_impl(data) |
| 23 | + |
| 24 | + with open(os.path.join(input_path, 'output', 'accel-config-rules.' + output_format), 'w') as writefile: |
| 25 | + print("Created Config Rules configuration in : %s" % |
| 26 | + os.path.join(input_path, 'output', 'accel-config-rules.' + output_format)) |
| 27 | + if output_format == 'json': |
| 28 | + json.dump(rules, writefile, indent=2) |
| 29 | + print(json.dumps(ruleNames)) |
| 30 | + else: |
| 31 | + yaml.dump(rules, writefile, indent=2) |
| 32 | + print(yaml.dump(ruleNames)) |
| 33 | + |
| 34 | + |
| 35 | +def generate_config_impl(data): |
| 36 | + parameters = data.get("Parameters", []) |
| 37 | + resources = data.get("Resources", {}) |
| 38 | + for name, props in resources.items(): |
| 39 | + rule = {} |
| 40 | + if props['Type'] != "AWS::Config::ConfigRule": |
| 41 | + continue |
| 42 | + if not props["Properties"]["Source"] or props["Properties"]["Source"]["Owner"] != 'AWS': |
| 43 | + continue |
| 44 | + rule['name'] = props["Properties"]["Source"]["SourceIdentifier"] |
| 45 | + ruleNames.append(props["Properties"]["Source"]["SourceIdentifier"]) |
| 46 | + for param_name, value in props["Properties"].get("InputParameters", {}).items(): |
| 47 | + if 'parameters' not in rule: |
| 48 | + rule['parameters'] = {} |
| 49 | + if not isinstance(value, dict): |
| 50 | + rule['parameters'][param_name] = value |
| 51 | + else: |
| 52 | + if 'Ref' in value: |
| 53 | + if parameters.get(value['Ref']) and parameters.get(value['Ref']).get('Default'): |
| 54 | + rule['parameters'][param_name] = parameters[value['Ref']]['Default'] |
| 55 | + elif 'Fn::If' in value: |
| 56 | + true_val = value['Fn::If'][1] |
| 57 | + false_val = value['Fn::If'][2] if len( |
| 58 | + value['Fn::If']) > 2 else None |
| 59 | + if isinstance(true_val, dict) and 'Ref' in true_val: |
| 60 | + if parameters.get(true_val['Ref']): |
| 61 | + if true_val['Ref'] in pseudo_params: |
| 62 | + rule['parameters'][param_name] = true_val['Ref'] |
| 63 | + elif parameters.get(true_val['Ref']).get('Default'): |
| 64 | + rule['parameters'][param_name] = parameters[true_val['Ref']]['Default'] |
| 65 | + elif isinstance(true_val, str): |
| 66 | + rule['parameters'][param_name] = true_val |
| 67 | + elif isinstance(false_val, dict): |
| 68 | + if parameters.get(false_val['Ref']): |
| 69 | + if false_val['Ref'] in pseudo_params: |
| 70 | + rule['parameters'][param_name] = false_val['Ref'] |
| 71 | + elif parameters.get(false_val['Ref']).get('Default'): |
| 72 | + rule['parameters'][param_name] = parameters[false_val['Ref']]['Default'] |
| 73 | + elif isinstance(false_val, str): |
| 74 | + rule['parameters'][param_name] = false_val |
| 75 | + if param_name not in rule["parameters"]: |
| 76 | + rule['parameters'][param_name] = "${REPLACE::%s}" % param_name |
| 77 | + rules.append(rule) |
| 78 | + return |
| 79 | + |
| 80 | + |
| 81 | +if __name__ == "__main__": |
| 82 | + parser = argparse.ArgumentParser(description='Generate Config Options') |
| 83 | + parser.add_argument('--path', required=True, |
| 84 | + help='Input File path', default=os.path.expanduser('~')) |
| 85 | + parser.add_argument('--outputFormat', required=False, |
| 86 | + choices=['json', 'yaml'], help='json/yaml', default='json') |
| 87 | + parser.add_argument('--inputFormat', required=False, |
| 88 | + choices=['json', 'yaml'], help='json/yaml', default='yaml') |
| 89 | + args = parser.parse_args() |
| 90 | + if not os.path.exists(os.path.join(args.path, 'output')): |
| 91 | + os.mkdir(os.path.join(args.path, 'output')) |
| 92 | + generate_config(args.path, args.inputFormat, args.outputFormat) |
0 commit comments