• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1#!/usr/bin/env python3
2# -*- coding: utf-8 -*-
3# Copyright (c) 2022 Huawei Device Co., Ltd.
4# Licensed under the Apache License, Version 2.0 (the "License");
5# you may not use this file except in compliance with the License.
6# You may obtain a copy of the License at
7#
8#     http://www.apache.org/licenses/LICENSE-2.0
9#
10# Unless required by applicable law or agreed to in writing, software
11# distributed under the License is distributed on an "AS IS" BASIS,
12# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13# See the License for the specific language governing permissions and
14# limitations under the License.
15
16# This file is for get the mapping relationship of subsystem_name/component_name
17# and their directory. The code is from Yude Chen.
18
19import argparse
20import os
21import json
22import logging
23
24g_subsystem_path_error = list()  # subsystem path exist in subsystem_config.json
25# bundle.json path which cant get component path.
26g_component_path_empty = list()
27g_component_abs_path = list()  # destPath can't be absolute path.
28
29
30def get_subsystem_components(ohos_path: str):
31    subsystem_json_path = os.path.join(
32        ohos_path, r"build/subsystem_config.json")
33    subsystem_item = {}
34
35    with open(subsystem_json_path, 'rb') as f:
36        subsystem_json = json.load(f)
37    # get sunsystems
38    for i in subsystem_json:
39        subsystem_name = subsystem_json[i]["name"]
40        subsystem_path = os.path.join(ohos_path, subsystem_json[i]["path"])
41        if not os.path.exists(subsystem_path):
42            g_subsystem_path_error.append(subsystem_path)
43            continue
44        cmd = 'find {} -name bundle.json'.format(subsystem_path)
45        bundle_json_list = os.popen(cmd).readlines()
46        # get components
47        component_list = []
48        for j in bundle_json_list:
49            bundle_path = j.strip()
50            with open(bundle_path, 'rb') as bundle_file:
51                bundle_json = json.load(bundle_file)
52            component_item = {}
53            if 'segment' in bundle_json and 'destPath' in bundle_json["segment"]:
54                destpath = bundle_json["segment"]["destPath"]
55                component_item[bundle_json["component"]["name"]] = destpath
56                if os.path.isabs(destpath):
57                    g_component_abs_path.append(destpath)
58            else:
59                component_item[bundle_json["component"]["name"]
60                               ] = "Unknow. Please check {}".format(bundle_path)
61                g_component_path_empty.append(bundle_path)
62            component_list.append(component_item)
63        subsystem_item[subsystem_name] = component_list
64    return subsystem_item
65
66
67def get_subsystem_components_modified(ohos_root) -> dict:
68    ret = dict()
69    subsystem_info = get_subsystem_components(ohos_root)
70    if subsystem_info is None:
71        return None
72    for subsystem_k, subsystem_v in subsystem_info.items():
73        for component in subsystem_v:
74            for k, v in component.items():
75                ret.update({v: {'subsystem': subsystem_k, 'component': k}})
76    return ret
77
78
79def export_to_json(subsystem_item: dict, output_filename: str):
80    subsystem_item_json = json.dumps(
81        subsystem_item, indent=4, separators=(', ', ': '))
82    with open(output_filename, 'w') as f:
83        f.write(subsystem_item_json)
84    logging.info("output path: {}".format(output_filename))
85
86
87def parse_args():
88    parser = argparse.ArgumentParser()
89    parser.add_argument("project", help="project root path.", type=str)
90    parser.add_argument("-o", "--outpath",
91                        help="specify an output path.", type=str)
92    args = parser.parse_args()
93
94    ohos_path = os.path.abspath(args.project)
95    if not is_project(ohos_path):
96        logging.error("'{}' is not a valid project path.".format(ohos_path))
97        exit(1)
98
99    output_path = r'.'
100    if args.outpath:
101        output_path = args.outpath
102
103    return ohos_path, output_path
104
105
106def is_project(path: str) -> bool:
107    '''
108    @func: 判断是否源码工程。
109    @note: 通过是否含有 .repo/manifests 目录粗略判断。
110    '''
111    p = os.path.normpath(path)
112    return os.path.exists('{}/.repo/manifests'.format(p))
113
114
115def print_warning_info():
116    '''@func: 打印一些异常信息。
117    '''
118    if g_component_path_empty or g_component_abs_path:
119        logging.warning("------------ warning info ------------------")
120
121    if g_component_path_empty:
122        logging.warning("can't find destPath in:")
123        logging.warning(g_component_path_empty)
124
125    if g_component_abs_path:
126        logging.warning("destPath can't be absolute path:")
127        logging.warning(g_component_abs_path)
128
129
130class SC:
131    @classmethod
132    def run(cls, project_path: str, output_path: str = None, save_result: bool = True):
133        info = get_subsystem_components_modified(
134            os.path.abspath(os.path.expanduser(project_path)))
135        if save_result and output_path:
136            export_to_json(info, output_path)
137        print_warning_info()
138        return info
139
140
141__all__ = ["SC"]
142