1#!/usr/bin/env python3 2# 3# Copyright 2018 - The Android Open Source Project 4# 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 17"""Unittests for project_file_gen.""" 18 19import copy 20import os 21import shutil 22import unittest 23 24from unittest import mock 25 26from aidegen import constant 27from aidegen import unittest_constants 28from aidegen.lib import project_file_gen 29from atest import module_info 30 31 32# pylint: disable=protected-access 33class AidegenProjectFileGenUnittest(unittest.TestCase): 34 """Unit tests for project_file_gen.py.""" 35 36 maxDiff = None 37 _TEST_DATA_PATH = unittest_constants.TEST_DATA_PATH 38 _ANDROID_PROJECT_PATH = os.path.join(_TEST_DATA_PATH, 'android_project') 39 _PROJECT_PATH = os.path.join(_TEST_DATA_PATH, 'project') 40 _ANDROID_FACET_SAMPLE = os.path.join(_TEST_DATA_PATH, 'android_facet.iml') 41 _PROJECT_FACET_SAMPLE = os.path.join(_TEST_DATA_PATH, 'project_facet.iml') 42 _MODULE_DEP_SAMPLE = os.path.join(_TEST_DATA_PATH, 'module_dependency.iml') 43 _IML_SAMPLE = os.path.join(_TEST_DATA_PATH, 'test.iml') 44 _CLASSPATH_SAMPLE = os.path.join(_TEST_DATA_PATH, 'eclipse.classpath') 45 _DEPENDENCIES_IML_SAMPLE = os.path.join(_TEST_DATA_PATH, 'dependencies.iml') 46 _MODULE_XML_SAMPLE = os.path.join(_TEST_DATA_PATH, 'modules.xml') 47 _VCS_XML_SAMPLE = os.path.join(_TEST_DATA_PATH, 'vcs.xml') 48 _IML_PATH = os.path.join(_ANDROID_PROJECT_PATH, 'android_project.iml') 49 _DEPENDENCIES_IML_PATH = os.path.join(_ANDROID_PROJECT_PATH, 50 'dependencies.iml') 51 _IDEA_PATH = os.path.join(_ANDROID_PROJECT_PATH, '.idea') 52 _MODULE_PATH = os.path.join(_IDEA_PATH, 'modules.xml') 53 _VCS_PATH = os.path.join(_IDEA_PATH, 'vcs.xml') 54 _SOURCE_SAMPLE = os.path.join(_TEST_DATA_PATH, 'source.iml') 55 _LOCAL_PATH_TOKEN = '@LOCAL_PATH@' 56 _AOSP_FOLDER = '/aosp' 57 _JAR_DEP_LIST = ['test1.jar', 'test2.jar'] 58 _TEST_SOURCE_LIST = [ 59 'a/b/c/d', 'a/b/c/d/e', 'a/b/c/d/e/f', 'a/b/c/d/f', 'e/f/a', 'e/f/b/c', 60 'e/f/g/h' 61 ] 62 _ANDROID_SOURCE_DICT = { 63 'test_data/project/level11/level21': True, 64 'test_data/project/level11/level22/level31': False, 65 'test_data/project/level12/level22': False, 66 } 67 _ANDROID_SOURCE_RELATIVE_PATH = 'test_data/project' 68 _SAMPLE_CONTENT_LIST = ['a/b/c/d', 'e/f'] 69 _SAMPLE_TRIMMED_SOURCE_LIST = ['a/b/c/d', 'e/f/a', 'e/f/b/c', 'e/f/g/h'] 70 71 def test_handle_facet_for_android(self): 72 """Test _handle_facet with android project.""" 73 template = project_file_gen._read_file_content( 74 project_file_gen._TEMPLATE_IML_PATH) 75 android_facet = project_file_gen._handle_facet( 76 template, self._ANDROID_PROJECT_PATH) 77 sample_android_facet = project_file_gen._read_file_content( 78 self._ANDROID_FACET_SAMPLE) 79 self.assertEqual(android_facet, sample_android_facet) 80 81 def test_handle_facet_for_normal(self): 82 """Test _handle_facet with normal module.""" 83 template = project_file_gen._read_file_content( 84 project_file_gen._TEMPLATE_IML_PATH) 85 project_facet = project_file_gen._handle_facet(template, 86 self._PROJECT_PATH) 87 sample_project_facet = project_file_gen._read_file_content( 88 self._PROJECT_FACET_SAMPLE) 89 self.assertEqual(project_facet, sample_project_facet) 90 91 def test_handle_module_dependency(self): 92 """Test _module_dependency.""" 93 module_dependency = project_file_gen._read_file_content( 94 project_file_gen._TEMPLATE_IML_PATH) 95 module_dependency = module_dependency.replace( 96 project_file_gen._MODULE_DEP_TOKEN, '') 97 correct_module_dep = project_file_gen._read_file_content( 98 self._MODULE_DEP_SAMPLE) 99 self.assertEqual(correct_module_dep, module_dependency) 100 101 def test_trim_same_root_source(self): 102 """Test _trim_same_root_source.""" 103 url_list = project_file_gen._trim_same_root_source( 104 self._TEST_SOURCE_LIST[:]) 105 self.assertEqual(url_list, self._SAMPLE_TRIMMED_SOURCE_LIST) 106 107 def test_handle_source_folder(self): 108 """Test _handle_source_folder.""" 109 template = project_file_gen._read_file_content( 110 project_file_gen._TEMPLATE_IML_PATH) 111 source = project_file_gen._handle_source_folder( 112 self._AOSP_FOLDER, template, 113 copy.deepcopy(self._ANDROID_SOURCE_DICT), True, 114 self._ANDROID_SOURCE_RELATIVE_PATH) 115 sample_source = project_file_gen._read_file_content(self._SOURCE_SAMPLE) 116 self.assertEqual(source, sample_source) 117 118 def test_generate_iml(self): 119 """Test _generate_iml.""" 120 try: 121 iml_path, dependencies_iml_path = project_file_gen._generate_iml( 122 self._AOSP_FOLDER, self._ANDROID_PROJECT_PATH, 123 copy.deepcopy(self._ANDROID_SOURCE_DICT), self._JAR_DEP_LIST, 124 self._ANDROID_SOURCE_RELATIVE_PATH) 125 test_iml = project_file_gen._read_file_content(iml_path) 126 sample_iml = project_file_gen._read_file_content(self._IML_SAMPLE) 127 finally: 128 os.remove(iml_path) 129 os.remove(dependencies_iml_path) 130 self.assertEqual(test_iml, sample_iml) 131 132 def test_generate_modules_xml(self): 133 """Test _generate_modules_xml.""" 134 try: 135 project_file_gen._generate_modules_xml(self._ANDROID_PROJECT_PATH) 136 test_module = project_file_gen._read_file_content(self._MODULE_PATH) 137 finally: 138 shutil.rmtree(self._IDEA_PATH) 139 sample_module = project_file_gen._read_file_content( 140 self._MODULE_XML_SAMPLE) 141 self.assertEqual(test_module, sample_module) 142 143 def test_generate_vcs_xml(self): 144 """Test _generate_vcs_xml.""" 145 try: 146 git_path = os.path.join(self._ANDROID_PROJECT_PATH, 147 project_file_gen._GIT_FOLDER_NAME) 148 os.mkdir(git_path) 149 project_file_gen._generate_vcs_xml(self._ANDROID_PROJECT_PATH) 150 test_vcs = project_file_gen._read_file_content(self._VCS_PATH) 151 finally: 152 shutil.rmtree(self._IDEA_PATH) 153 shutil.rmtree(git_path) 154 sample_vcs = project_file_gen._read_file_content(self._VCS_XML_SAMPLE) 155 # The sample must base on the real path. 156 sample_vcs = sample_vcs.replace(self._LOCAL_PATH_TOKEN, 157 self._ANDROID_PROJECT_PATH) 158 self.assertEqual(test_vcs, sample_vcs) 159 160 def test_get_uniq_iml_name(self): 161 """Test the unique name cache mechanism. 162 163 By using the path data in module info json as input, if the count of 164 name data set is the same as sub folder path count, then it means 165 there's no duplicated name, the test PASS. 166 """ 167 # Add following test path 168 test_paths = { 169 'cts/tests/tests/app', 170 'cts/tests/app', 171 'cts/tests/app/app1/../app', 172 'cts/tests/app/app2/../app', 173 'cts/tests/app/app3/../app', 174 'frameworks/base/tests/xxxxxxxxxxxx/base', 175 'frameworks/base', 176 'external/xxxxx-xxx/robolectric', 177 'external/robolectric', 178 } 179 mod_info = module_info.ModuleInfo() 180 test_paths.update(mod_info._get_path_to_module_info( 181 mod_info.name_to_module_info).keys()) 182 print('\n{} {}.'.format('Test_paths length:', len(test_paths))) 183 184 path_list = [] 185 for k in test_paths: 186 path_list.append(k) 187 print('{} {}.'.format('path list with length:', len(path_list))) 188 189 names = [project_file_gen.get_unique_iml_name(f) for f in path_list] 190 print('{} {}.'.format('Names list with length:', len(names))) 191 192 self.assertEqual(len(names), len(path_list)) 193 dic = {} 194 for i, path in enumerate(path_list): 195 dic[names[i]] = path 196 print('{} {}.'.format('The size of name set is:', len(dic))) 197 self.assertEqual(len(dic), len(path_list)) 198 199 def test_copy_project_files(self): 200 """Test _copy_constant_project_files.""" 201 project_file_gen._copy_constant_project_files( 202 self._ANDROID_PROJECT_PATH) 203 self.assertTrue( 204 os.path.isfile( 205 os.path.join(self._IDEA_PATH, 206 project_file_gen._CODE_STYLE_FOLDER, 207 'codeStyleConfig.xml'))) 208 self.assertTrue( 209 os.path.isfile( 210 os.path.join(self._IDEA_PATH, 211 project_file_gen._COPYRIGHT_FOLDER, 212 'Apache_2.xml'))) 213 self.assertTrue( 214 os.path.isfile( 215 os.path.join(self._IDEA_PATH, 216 project_file_gen._COPYRIGHT_FOLDER, 217 'profiles_settings.xml'))) 218 shutil.rmtree(self._IDEA_PATH) 219 220 def test_generate_classpath(self): 221 """Test _generate_classpath.""" 222 try: 223 classpath = project_file_gen._generate_classpath( 224 self._ANDROID_PROJECT_PATH, 225 copy.deepcopy(list(sorted(self._ANDROID_SOURCE_DICT))), 226 self._JAR_DEP_LIST) 227 test_iml = project_file_gen._read_file_content(classpath) 228 sample_iml = project_file_gen._read_file_content( 229 self._CLASSPATH_SAMPLE) 230 finally: 231 os.remove(classpath) 232 self.assertEqual(test_iml, sample_iml) 233 234 @mock.patch('os.symlink') 235 @mock.patch.object(os.path, 'exists') 236 def test_generate_git_ignore(self, mock_path_exist, mock_link): 237 """Test _generate_git_ignore.""" 238 mock_path_exist.return_value = True 239 project_file_gen._generate_git_ignore(constant.AIDEGEN_ROOT_PATH) 240 self.assertFalse(mock_link.called) 241 242 243if __name__ == '__main__': 244 unittest.main() 245