1#!/usr/bin/env python3 2# -*- coding: utf-8 -*- 3# 4# Copyright (c) 2024 Huawei Device Co., Ltd. 5# Licensed under the Apache License, Version 2.0 (the "License"); 6# you may not use this file except in compliance with the License. 7# You may obtain a copy of the License at 8# 9# http://www.apache.org/licenses/LICENSE-2.0 10# 11# Unless required by applicable law or agreed to in writing, software 12# distributed under the License is distributed on an "AS IS" BASIS, 13# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14# See the License for the specific language governing permissions and 15# limitations under the License. 16 17import argparse 18import datetime 19import os 20import subprocess 21import shutil 22from config import JS_FILE, API_VERSION_MAP, Color 23 24 25def parse_args(): 26 parser = argparse.ArgumentParser(description="Version compatibility testing for Verifier.") 27 parser.add_argument( 28 "--verifier-dir", required=True, help="Path to the ark_verifier.") 29 parser.add_argument( 30 "--es2abc-dir", required=True, help="Path to the es2abc.") 31 parser.add_argument( 32 "--keep-files", action="store_true", help="Keep the diff_version_abcs directory.") 33 return parser.parse_args() 34 35 36def create_output_dir(): 37 output_dir = os.path.join(os.path.dirname(os.path.realpath(__file__)), "diff_version_abcs") 38 if os.path.exists(output_dir): 39 shutil.rmtree(output_dir) 40 os.makedirs(output_dir) 41 return output_dir 42 43 44def split_api_version(version_str): 45 if not version_str.startswith("API"): 46 raise ValueError(f"Invalid version string format: {version_str}") 47 48 parts = version_str.split("API")[1].split("beta") 49 main_part = parts[0] 50 # Create "beta*" if there is a beta part; otherwise, set to empty string 51 beta_part = f"beta{parts[1]}" if len(parts) > 1 else "" 52 53 return (main_part, beta_part) 54 55 56def compile_abc(es2abc_path, js_file, output_file, target_api_version, target_api_sub_version): 57 cmd = [ 58 es2abc_path, 59 "--module", js_file, 60 "--output", output_file, 61 f"--target-api-version={target_api_version}", 62 ] 63 64 if target_api_sub_version: 65 cmd.append(f"--target-api-sub-version={target_api_sub_version}") 66 67 result = subprocess.run(cmd, capture_output=True, text=True) 68 69 print(f"Executing command: {' '.join(cmd)}") 70 71 if result.returncode != 0: 72 print(f"Error in compiling {output_file}: {result.stderr}") 73 raise subprocess.CalledProcessError(result.returncode, cmd) 74 else: 75 print(f"Compiled {output_file}: {result.stdout}") 76 77 78def verify_abcs(verifier_dir, output_dir): 79 input_files = [os.path.join(output_dir, f) for f in os.listdir(output_dir) if f.endswith(".abc")] 80 passed_count = 0 81 failed_count = 0 82 failed_files = [] 83 84 for abc_file in input_files: 85 cmd = [os.path.join(verifier_dir, "ark_verifier"), "--input_file", abc_file] 86 result = subprocess.run(cmd, capture_output=True, text=True) 87 88 if result.returncode == 0: 89 print(f"Verification passed for {abc_file}: {result.stdout}") 90 passed_count += 1 91 else: 92 print(f"Verification failed for {abc_file}: {result.stderr}") 93 failed_count += 1 94 failed_files.append(abc_file) 95 96 total_count = passed_count + failed_count 97 return passed_count, failed_count, total_count, failed_files 98 99 100def report_results(passed, failed, total, failed_files): 101 timestamp = datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S") 102 103 print(Color.apply(Color.WHITE, f"Total ABC files: {total}")) 104 print(Color.apply(Color.GREEN, f"Passed: {passed}")) 105 print(Color.apply(Color.RED, f"Failed: {failed}")) 106 print(f"Report generated at: {timestamp}") 107 if failed > 0: 108 print("Failed files:") 109 for file in failed_files: 110 print(f" - {file}") 111 112 113def main(): 114 args = parse_args() 115 116 verifier_dir = args.verifier_dir 117 es2abc_dir = args.es2abc_dir 118 119 script_dir = os.path.dirname(os.path.realpath(__file__)) 120 js_file = os.path.join(script_dir, "js", JS_FILE) 121 122 if not os.path.exists(js_file): 123 raise FileNotFoundError(f"{js_file} not found.") 124 125 output_dir = create_output_dir() 126 127 es2abc_path = os.path.join(es2abc_dir, "es2abc") 128 if not os.path.exists(es2abc_path): 129 raise FileNotFoundError(f"{es2abc_path} not found.") 130 131 for api_key in API_VERSION_MAP.keys(): 132 target_api_version, target_api_sub_version = split_api_version(api_key) 133 134 output_file = os.path.join(output_dir, f"{api_key}.abc") 135 compile_abc( 136 es2abc_path, js_file, output_file, target_api_version, 137 target_api_sub_version if target_api_version == "12" else "" 138 ) 139 140 passed, failed, total, failed_files = verify_abcs(verifier_dir, output_dir) 141 report_results(passed, failed, total, failed_files) 142 143 if failed == 0 and not args.keep_files: 144 shutil.rmtree(output_dir) 145 print(f"Deleted {output_dir} as all verifications passed.") 146 else: 147 print(f"Verification failed or keep-files flag is set, keeping {output_dir} for inspection.") 148 149 150if __name__ == "__main__": 151 main() 152