Files
sigma-rules/tests/test_toml_formatter.py
T
Ross Wolf c0af222e7e Move Rule into a dataclass (#1029)
* WIP: Convert Rule to a dataclass
* Fix make release
* Lint fixes
* Remove dead code
* Fix lint and tests
* Use Python 3.8 in GitHub actions
* Update README to 3.8+
* Add Python 3.8 assertion
* Fix is_dirty property
* Remove incorrect pop from contents
* Add mixin with from_dict() and to_dict() methods
* Bypass validation for deprecated rules
* Fix rule_prompt
* Fix dict_hash usage
* Fix rule_event_search
* Switch to definitions.Date
* Fix toml-lint command, ignoring 'unneeded defaults'
* Moved severity Literal to definitions.Severity
* Remove BaseMarshmallowDataclass
* Fix lint and tests
* Add maturity to metadata for rule prompt loop
* Fix typo in devtools
* Use rule loader to load single rule in toml-lint
* Add Schema hint to __schema method
* Add MITREAttackURL definition
* Fix is_dirty to compare sha<-->sha
* Normalize the autoformatted rule output for API and toml-lint
* Make the package hash match
* Make the rule object mutable but not rule contents
* Restore the rules
2021-03-24 10:24:32 -06:00

79 lines
2.9 KiB
Python

# Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
# or more contributor license agreements. Licensed under the Elastic License
# 2.0; you may not use this file except in compliance with the Elastic License
# 2.0.
import copy
import json
import os
import unittest
import pytoml
from detection_rules.rule_formatter import nested_normalize, toml_write
from detection_rules.utils import get_etc_path
tmp_file = 'tmp_file.toml'
class TestRuleTomlFormatter(unittest.TestCase):
"""Test that the cutom toml formatting is not compromising the integrity of the data."""
with open(get_etc_path('test_toml.json'), 'r') as f:
test_data = json.load(f)
def compare_formatted(self, data, callback=None, kwargs=None):
"""Compare formatted vs expected."""
try:
toml_write(copy.deepcopy(data), tmp_file)
with open(tmp_file, 'r') as f:
formatted_contents = pytoml.load(f)
# callbacks such as nested normalize leave in line breaks, so this must be manually done
query = data.get('rule', {}).get('query')
if query:
data['rule']['query'] = query.strip()
original = json.dumps(copy.deepcopy(data), sort_keys=True)
if callback:
kwargs = kwargs or {}
formatted_contents = callback(formatted_contents, **kwargs)
# callbacks such as nested normalize leave in line breaks, so this must be manually done
query = formatted_contents.get('rule', {}).get('query')
if query:
formatted_contents['rule']['query'] = query.strip()
formatted = json.dumps(formatted_contents, sort_keys=True)
self.assertEqual(original, formatted, 'Formatting may be modifying contents')
finally:
os.remove(tmp_file)
def compare_test_data(self, test_dicts, callback=None):
"""Compare test data against expected."""
for data in test_dicts:
self.compare_formatted(data, callback=callback)
def test_normalization(self):
"""Test that normalization does not change the rule contents."""
self.compare_test_data([nested_normalize(self.test_data[0])], callback=nested_normalize)
def test_formatter_rule(self):
"""Test that formatter and encoder do not change the rule contents."""
self.compare_test_data([self.test_data[0]])
def test_formatter_deep(self):
"""Test that the data remains unchanged from formatting."""
self.compare_test_data(self.test_data[1:])
#
# def test_format_of_all_rules(self):
# """Test all rules."""
# rules = rule_loader.load_rules().values()
#
# for rule in rules:
# is_eql_rule = isinstance(rule.contents.data, EQLRuleData)
# self.compare_formatted(
# rule.rule_format(formatted_query=False), callback=nested_normalize, kwargs={'eql_rule': is_eql_rule})