• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1/*
2 * Copyright (c) 2024 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 *     http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16import {
17  Identifier,
18  isComputedPropertyName,
19  isConstructorDeclaration,
20  isFunctionDeclaration,
21  isFunctionExpression,
22  isIdentifier,
23  isMethodDeclaration,
24  isNumericLiteral,
25  isParameter,
26  isStringLiteralLike,
27  isTypeParameterDeclaration,
28} from 'typescript';
29import type {
30  Declaration,
31  Node,
32  NumericLiteral,
33  PropertyName,
34  SourceFile,
35  StringLiteral,
36  StringLiteralLike,
37  Symbol,
38  TypeChecker,
39} from 'typescript';
40import type { INameObfuscationOption } from '../configs/INameObfuscationOption';
41import { NodeUtils } from './NodeUtils';
42import { isReservedProperty } from './TransformUtil';
43import type { MangledSymbolInfo } from '../common/type';
44import { nodeSymbolMap } from './ScopeAnalyzer';
45
46// Determine that the current file is a declaration file and that the option to keep parameters is enabled
47export function shouldKeepCurFileParamerters(sourceFile: SourceFile, config: INameObfuscationOption): boolean {
48  return !!(sourceFile.isDeclarationFile && config.mKeepParameterNames);
49}
50
51// Determine whether the current parameter name needs to be obfuscated.
52export function shouldKeepParameter(decl: Declaration | undefined, config: INameObfuscationOption, mangledSymbolNames: Map<Symbol, MangledSymbolInfo>,
53  checker: TypeChecker): boolean {
54  if (!decl || (!isParameter(decl) && !isTypeParameterDeclaration(decl)) || !isIdentifier(decl.name) || !decl.parent) {
55    return false;
56  }
57  const parentNode: Node = decl.parent;
58
59  if ((isFunctionDeclaration(parentNode) || isFunctionExpression(parentNode))) {
60    const functionName: Identifier | undefined = parentNode.name;
61    return !!functionName && !isObfuscatedName(functionName, mangledSymbolNames, checker);
62  }
63
64  if (isMethodDeclaration(parentNode)) {
65    if (!config.mRenameProperties) {
66      return true;
67    }
68    let methodName: Identifier | NumericLiteral | StringLiteralLike | undefined = getPropertyNameOfMethod(parentNode.name);
69    return !!methodName && NodeUtils.isPropertyNameType(methodName) && isReservedProperty(methodName.text);
70  }
71
72  if (isConstructorDeclaration(parentNode)) {
73    const className: Identifier | undefined = parentNode.parent.name;
74    return !!className && !isObfuscatedName(className, mangledSymbolNames, checker);
75  }
76
77  return false;
78}
79
80function isObfuscatedName(name: Identifier, mangledSymbolNames: Map<Symbol, MangledSymbolInfo>, checker: TypeChecker): boolean {
81  const sym: Symbol | undefined = NodeUtils.findSymbolOfIdentifier(checker, name, nodeSymbolMap);
82  const symbolInfo: MangledSymbolInfo | undefined = mangledSymbolNames.get(sym);
83  if (symbolInfo && symbolInfo.mangledName !== name.text) {
84    return true;
85  }
86  return false;
87}
88
89function getPropertyNameOfMethod(propertyName: PropertyName): Identifier | NumericLiteral | StringLiteralLike | undefined {
90  if (isComputedPropertyName(propertyName)) {
91    if (isStringLiteralLike(propertyName.expression) || isNumericLiteral(propertyName.expression) || isIdentifier(propertyName.expression)) {
92      return propertyName.expression;
93    }
94    return undefined;
95  }
96  return propertyName as Identifier | NumericLiteral | StringLiteral;
97}