|  | #!/usr/bin/env python3 | 
|  |  | 
|  | # Pre-generates the expected output subset files (via fonttools) for | 
|  | # specified subset test suite(s). | 
|  |  | 
|  | import os | 
|  | import sys | 
|  | import shutil | 
|  | import io | 
|  | import re | 
|  | import tempfile | 
|  |  | 
|  | from difflib import unified_diff | 
|  | from fontTools.ttLib import TTFont | 
|  |  | 
|  | from subprocess import check_call | 
|  | from subset_test_suite import SubsetTestSuite | 
|  |  | 
|  |  | 
|  | def usage(): | 
|  | print("Usage: generate-expected-outputs.py hb-subset <test suite file> ...") | 
|  |  | 
|  |  | 
|  | def strip_check_sum (ttx_string): | 
|  | return re.sub ('checkSumAdjustment value=["]0x([0-9a-fA-F])+["]', | 
|  | 'checkSumAdjustment value="0x00000000"', | 
|  | ttx_string, count=1) | 
|  |  | 
|  |  | 
|  | def generate_expected_output(input_file, unicodes, profile_flags, instance_flags, output_directory, font_name): | 
|  | input_path = input_file | 
|  | if instance_flags: | 
|  | instance_path = os.path.join(tempfile.mkdtemp (), font_name) | 
|  | args = ["fonttools", "varLib.instancer", | 
|  | "--no-overlap-flag", | 
|  | "--no-recalc-bounds", | 
|  | "--no-recalc-timestamp", | 
|  | "--output=%s" % instance_path, | 
|  | input_file] | 
|  | args.extend(instance_flags) | 
|  | check_call(args) | 
|  | input_path = instance_path | 
|  |  | 
|  | fonttools_path = os.path.join(tempfile.mkdtemp (), font_name) | 
|  | args = ["fonttools", "subset", input_path] | 
|  | args.extend(["--drop-tables+=DSIG", | 
|  | "--drop-tables-=sbix", | 
|  | "--no-harfbuzz-repacker", # disable harfbuzz repacker so we aren't comparing to ourself. | 
|  | "--unicodes=%s" % unicodes, | 
|  | "--output-file=%s" % fonttools_path]) | 
|  | args.extend(profile_flags) | 
|  | check_call(args) | 
|  |  | 
|  | with io.StringIO () as fp: | 
|  | with TTFont (fonttools_path) as font: | 
|  | font.saveXML (fp) | 
|  | fonttools_ttx = strip_check_sum (fp.getvalue ()) | 
|  |  | 
|  | harfbuzz_path = os.path.join(tempfile.mkdtemp (), font_name) | 
|  | args = [ | 
|  | hb_subset, | 
|  | "--font-file=" + input_file, | 
|  | "--output-file=" + harfbuzz_path, | 
|  | "--unicodes=%s" % unicodes, | 
|  | "--drop-tables+=DSIG", | 
|  | "--drop-tables-=sbix"] | 
|  | args.extend(profile_flags) | 
|  | if instance_flags: | 
|  | args.extend(["--instance=%s" % ','.join(instance_flags)]) | 
|  | check_call(args) | 
|  |  | 
|  | with io.StringIO () as fp: | 
|  | with TTFont (harfbuzz_path) as font: | 
|  | font.saveXML (fp) | 
|  | harfbuzz_ttx = strip_check_sum (fp.getvalue ()) | 
|  |  | 
|  | if harfbuzz_ttx != fonttools_ttx: | 
|  | for line in unified_diff (fonttools_ttx.splitlines (1), harfbuzz_ttx.splitlines (1), fonttools_path, harfbuzz_path): | 
|  | sys.stdout.write (line) | 
|  | sys.stdout.flush () | 
|  | raise Exception ('ttx for fonttools and harfbuzz does not match.') | 
|  |  | 
|  | output_path = os.path.join(output_directory, font_name) | 
|  | shutil.copy(harfbuzz_path, output_path) | 
|  |  | 
|  |  | 
|  | args = sys.argv[1:] | 
|  | if not args: | 
|  | usage() | 
|  | hb_subset, args = args[0], args[1:] | 
|  | if not args: | 
|  | usage() | 
|  |  | 
|  | for path in args: | 
|  | with open(path, mode="r", encoding="utf-8") as f: | 
|  | test_suite = SubsetTestSuite(path, f.read()) | 
|  | output_directory = test_suite.get_output_directory() | 
|  |  | 
|  | print("Generating output files for %s" % output_directory) | 
|  | for test in test_suite.tests(): | 
|  | unicodes = test.unicodes() | 
|  | font_name = test.get_font_name() | 
|  | print("Creating subset %s/%s" % (output_directory, font_name)) | 
|  | generate_expected_output(test.font_path, unicodes, test.get_profile_flags(), | 
|  | test.get_instance_flags(), output_directory, font_name) |