Revision control
Copy as Markdown
Other Tools
# This script creates Rust test cases from the common uritemplate-test data
# files. The path of the JSON file should be passed in as a command line
# argument.
#
# Example usage:
# python generate_tests.py uritemplate-test/extended-tests.json > ../tests/extended_tests.rs
import json
import sys
import hashlib
def compute_md5(s):
m = hashlib.md5()
m.update(s.encode('utf-8'))
return m.hexdigest()
TEST_NAMES = {
'Level 1 Examples': 'test_level_1',
'Level 2 Examples': 'test_level_2',
'Level 3 Examples': 'test_level_3',
'Level 4 Examples': 'test_level_4',
'3.2.1 Variable Expansion': 'test_321_variable_expansion',
'3.2.2 Simple String Expansion': 'test_322_simple_string_expansion',
'3.2.3 Reserved Expansion': 'test_323_reserved_expansion',
'3.2.4 Fragment Expansion': 'test_324_fragment_expansion',
'3.2.5 Label Expansion with Dot-Prefix': 'test_325_label_expansion_with_dot_prefix',
'3.2.6 Path Segment Expansion': 'test_326_path_segment_expansion',
'3.2.7 Path-Style Parameter Expansion': 'test_327_path_style_parameter_expansion',
'3.2.8 Form-Style Query Expansion': 'test_328_form_style_query_expansion',
'3.2.9 Form-Style Query Continuation': 'test_329_form_style_query_continuation',
'Additional Examples 1': 'test_additional_examples_1',
'Additional Examples 2': 'test_additional_examples_2',
'Additional Examples 3: Empty Variables': 'test_additional_examples_3',
'Additional Examples 4: Numeric Keys': 'test_additional_examples_4'
}
# Load JSON file from command line argument
file_path = sys.argv[1]
with open(file_path) as json_file:
data = json.load(json_file)
# Print headers
print('// File autogenerated with /scripts/generate_tests.py\n')
print('extern crate uritemplate;')
print('use uritemplate::UriTemplate;\n')
# Create tests from JSON file
for (idx, title) in enumerate(sorted(data)):
# Write function header
test_name = TEST_NAMES.get(title, 'test_' + compute_md5(title))
print('// %s' % title)
print('#[test]')
print('fn %s() {' % test_name)
# Create list of URI Templates
print(' let mut templates = [')
for template in (x[0] for x in data[title]['testcases']):
print(' UriTemplate::new("%s"),' % template)
print(' ];\n')
# Set variables for all templates
print(' for i in 0..templates.len() {')
for var in data[title]['variables']:
val = data[title]['variables'][var]
if isinstance(val, str) or isinstance(val, int) or isinstance(val, float):
val = '"%s"' % val
elif isinstance(val, list):
val = '&[%s] as &[&str]' % ", ".join('"%s"' % x for x in val)
elif isinstance(val, dict):
val = '&[%s] as &[(&str, &str)]' % ", ".join('("%s", "%s")' % (k, v) for (k, v) in val.items())
elif val == None:
continue
else:
raise Exception('Variable value is not a string, list, dictionary, or false')
print(' templates[i].set("%s", %s);' % (var, val))
print(' }\n')
# Write assertions
num_tests = len(data[title]['testcases'])
for i in range(num_tests):
answer = data[title]['testcases'][i][1]
if isinstance(answer, str):
print(' assert_eq!(templates[%d].build(), "%s");' % (i, answer))
elif isinstance(answer, list):
print(' let template_%d_answers = vec![' % i)
for s in answer:
print(' "%s",' % s)
print(' ];')
print(' assert!(template_%d_answers.contains(&templates[%d].build().as_ref()));' % (i, i))
else:
raise Exception('Test answer is neither a string nor a list')
# Close out function
print('}')
if idx != len(data) - 1:
print()