• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /**
2  * Copyright (c) 2025 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 
16 #include "internal_api.h"
17 #include "rename.h"
18 #include "public/public.h"
19 #include "script_element_kind.h"
20 #include "compiler/lowering/util.h"
21 
22 namespace ark::es2panda::lsp {
GetTargetTokenKindIfETSType(ir::AstNodeType type)23 std::tuple<bool, CompletionEntryKind> GetTargetTokenKindIfETSType(ir::AstNodeType type)
24 {
25     switch (type) {
26         case ir::AstNodeType::ETS_NULL_TYPE:
27         case ir::AstNodeType::ETS_UNDEFINED_TYPE:
28         case ir::AstNodeType::ETS_NEVER_TYPE:
29         case ir::AstNodeType::ETS_STRING_LITERAL_TYPE:
30             return std::make_tuple(true, CompletionEntryKind::VALUE);
31         case ir::AstNodeType::ETS_PRIMITIVE_TYPE:
32         case ir::AstNodeType::ETS_CLASS_LITERAL:
33         case ir::AstNodeType::ETS_KEYOF_TYPE:
34             return std::make_tuple(true, CompletionEntryKind::KEYWORD);
35         case ir::AstNodeType::ETS_NEW_ARRAY_INSTANCE_EXPRESSION:
36         case ir::AstNodeType::ETS_NEW_MULTI_DIM_ARRAY_INSTANCE_EXPRESSION:
37         case ir::AstNodeType::ETS_NEW_CLASS_INSTANCE_EXPRESSION:
38         case ir::AstNodeType::ETS_PARAMETER_EXPRESSION:
39         case ir::AstNodeType::ETS_TUPLE:
40             return std::make_tuple(true, CompletionEntryKind::OPERATOR);
41         case ir::AstNodeType::ETS_FUNCTION_TYPE:
42             return std::make_tuple(true, CompletionEntryKind::FUNCTION);
43         case ir::AstNodeType::ETS_PACKAGE_DECLARATION:
44         case ir::AstNodeType::ETS_IMPORT_DECLARATION:
45         case ir::AstNodeType::ETS_MODULE:
46             return std::make_tuple(true, CompletionEntryKind::MODULE);
47         case ir::AstNodeType::ETS_TYPE_REFERENCE:
48         case ir::AstNodeType::ETS_TYPE_REFERENCE_PART:
49             return std::make_tuple(true, CompletionEntryKind::REFERENCE);
50         case ir::AstNodeType::ETS_WILDCARD_TYPE:
51             return std::make_tuple(true, CompletionEntryKind::TEXT);
52         case ir::AstNodeType::ETS_UNION_TYPE:
53             return std::make_tuple(true, CompletionEntryKind::TYPE_PARAMETER);
54         default:
55             break;
56     }
57     return std::make_tuple(false, CompletionEntryKind::ALIAS_TYPE);
58 }
59 
IsTSParameterKind(ir::AstNodeType type)60 bool IsTSParameterKind(ir::AstNodeType type)
61 {
62     switch (type) {
63         case ir::AstNodeType::TS_ARRAY_TYPE:
64         case ir::AstNodeType::TS_UNION_TYPE:
65         case ir::AstNodeType::TS_INTERSECTION_TYPE:
66         case ir::AstNodeType::TS_LITERAL_TYPE:
67         case ir::AstNodeType::TS_MAPPED_TYPE:
68         case ir::AstNodeType::TS_THIS_TYPE:
69         case ir::AstNodeType::TS_TYPE_PARAMETER:
70         case ir::AstNodeType::TS_TYPE_PARAMETER_DECLARATION:
71         case ir::AstNodeType::TS_TYPE_PARAMETER_INSTANTIATION:
72         case ir::AstNodeType::TS_TYPE_PREDICATE:
73         case ir::AstNodeType::TS_TYPE_ALIAS_DECLARATION:
74         case ir::AstNodeType::TS_TYPE_REFERENCE:
75         case ir::AstNodeType::TS_INDEXED_ACCESS_TYPE:
76         case ir::AstNodeType::TS_TUPLE_TYPE:
77             return true;
78         default:
79             break;
80     }
81     return false;
82 }
83 
IsTSMoudleKind(ir::AstNodeType type)84 bool IsTSMoudleKind(ir::AstNodeType type)
85 {
86     switch (type) {
87         case ir::AstNodeType::TS_IMPORT_TYPE:
88         case ir::AstNodeType::TS_MODULE_BLOCK:
89         case ir::AstNodeType::TS_EXTERNAL_MODULE_REFERENCE:
90         case ir::AstNodeType::TS_MODULE_DECLARATION:
91         case ir::AstNodeType::TS_IMPORT_EQUALS_DECLARATION:
92             return true;
93         default:
94             break;
95     }
96     return false;
97 }
98 
GetTargetTokenKindIfTSType(ir::AstNodeType type)99 std::tuple<bool, CompletionEntryKind> GetTargetTokenKindIfTSType(ir::AstNodeType type)
100 {
101     auto reuslt = std::make_tuple(false, CompletionEntryKind::ALIAS_TYPE);
102     if (IsValidAncestorType(type)) {
103         reuslt = std::make_tuple(true, CompletionEntryKind::KEYWORD);
104     } else if (IsTSParameterKind(type)) {
105         reuslt = std::make_tuple(true, CompletionEntryKind::TYPE_PARAMETER);
106     } else if (IsTSMoudleKind(type)) {
107         reuslt = std::make_tuple(true, CompletionEntryKind::MODULE);
108     }
109     switch (type) {
110         case ir::AstNodeType::TS_ENUM_DECLARATION:
111             return std::make_tuple(true, CompletionEntryKind::ENUM);
112         case ir::AstNodeType::TS_ENUM_MEMBER:
113             return std::make_tuple(true, CompletionEntryKind::ENUM_MEMBER);
114         case ir::AstNodeType::TS_NON_NULL_EXPRESSION:
115         case ir::AstNodeType::TS_TYPE_OPERATOR:
116         case ir::AstNodeType::TS_AS_EXPRESSION:
117             return std::make_tuple(true, CompletionEntryKind::OPERATOR);
118         case ir::AstNodeType::TS_TYPE_LITERAL:
119             return std::make_tuple(true, CompletionEntryKind::VALUE);
120         case ir::AstNodeType::TS_PROPERTY_SIGNATURE:
121             return std::make_tuple(true, CompletionEntryKind::PROPERTY);
122         case ir::AstNodeType::TS_METHOD_SIGNATURE:
123             return std::make_tuple(true, CompletionEntryKind::METHOD);
124         case ir::AstNodeType::TS_FUNCTION_TYPE:
125             return std::make_tuple(true, CompletionEntryKind::FUNCTION);
126         case ir::AstNodeType::TS_CONSTRUCTOR_TYPE:
127             return std::make_tuple(true, CompletionEntryKind::CONSTRUCTOR);
128         case ir::AstNodeType::TS_NAMED_TUPLE_MEMBER:
129             return std::make_tuple(true, CompletionEntryKind::VALUE);
130         case ir::AstNodeType::TS_INTERFACE_DECLARATION:
131         case ir::AstNodeType::TS_INTERFACE_BODY:
132         case ir::AstNodeType::TS_INTERFACE_HERITAGE:
133             return std::make_tuple(true, CompletionEntryKind::INTERFACE);
134         case ir::AstNodeType::TS_SIGNATURE_DECLARATION:
135         case ir::AstNodeType::TS_PARENT_TYPE:
136         case ir::AstNodeType::TS_INFER_TYPE:
137         case ir::AstNodeType::TS_CONDITIONAL_TYPE:
138         case ir::AstNodeType::TS_PARAMETER_PROPERTY:
139         case ir::AstNodeType::TS_QUALIFIED_NAME:
140         case ir::AstNodeType::TS_INDEX_SIGNATURE:
141         case ir::AstNodeType::TS_TYPE_QUERY:
142         case ir::AstNodeType::TS_CLASS_IMPLEMENTS:
143         case ir::AstNodeType::TS_TYPE_ASSERTION:
144             return std::make_tuple(true, CompletionEntryKind::TEXT);
145         default:
146             break;
147     }
148     return reuslt;
149 }
150 
IsExpress(ir::AstNodeType type)151 bool IsExpress(ir::AstNodeType type)
152 {
153     switch (type) {
154         case ir::AstNodeType::ARROW_FUNCTION_EXPRESSION:
155         case ir::AstNodeType::AWAIT_EXPRESSION:
156         case ir::AstNodeType::BINARY_EXPRESSION:
157         case ir::AstNodeType::CALL_EXPRESSION:
158         case ir::AstNodeType::CHAIN_EXPRESSION:
159         case ir::AstNodeType::CLASS_EXPRESSION:
160         case ir::AstNodeType::CONDITIONAL_EXPRESSION:
161         case ir::AstNodeType::DIRECT_EVAL:
162         case ir::AstNodeType::FUNCTION_EXPRESSION:
163         case ir::AstNodeType::MEMBER_EXPRESSION:
164         case ir::AstNodeType::META_PROPERTY_EXPRESSION:
165         case ir::AstNodeType::NEW_EXPRESSION:
166         case ir::AstNodeType::OMITTED_EXPRESSION:
167         case ir::AstNodeType::PREFIX_ASSERTION_EXPRESSION:
168         case ir::AstNodeType::SEQUENCE_EXPRESSION:
169         case ir::AstNodeType::SUPER_EXPRESSION:
170         case ir::AstNodeType::TAGGED_TEMPLATE_EXPRESSION:
171         case ir::AstNodeType::THIS_EXPRESSION:
172         case ir::AstNodeType::TYPEOF_EXPRESSION:
173         case ir::AstNodeType::UNARY_EXPRESSION:
174         case ir::AstNodeType::UPDATE_EXPRESSION:
175         case ir::AstNodeType::YIELD_EXPRESSION:
176         case ir::AstNodeType::BLOCK_EXPRESSION:
177             return true;
178         default:
179             break;
180     }
181     return false;
182 }
183 
IsStatement(ir::AstNodeType type)184 bool IsStatement(ir::AstNodeType type)
185 {
186     switch (type) {
187         case ir::AstNodeType::ASSERT_STATEMENT:
188         case ir::AstNodeType::CONTINUE_STATEMENT:
189         case ir::AstNodeType::IF_STATEMENT:
190         case ir::AstNodeType::DEBUGGER_STATEMENT:
191         case ir::AstNodeType::DO_WHILE_STATEMENT:
192         case ir::AstNodeType::EMPTY_STATEMENT:
193         case ir::AstNodeType::EXPRESSION_STATEMENT:
194         case ir::AstNodeType::BLOCK_STATEMENT:
195         case ir::AstNodeType::BREAK_STATEMENT:
196         case ir::AstNodeType::CATCH_CLAUSE:
197         case ir::AstNodeType::FOR_IN_STATEMENT:
198         case ir::AstNodeType::FOR_OF_STATEMENT:
199         case ir::AstNodeType::FOR_UPDATE_STATEMENT:
200         case ir::AstNodeType::REEXPORT_STATEMENT:
201         case ir::AstNodeType::RETURN_STATEMENT:
202         case ir::AstNodeType::LABELLED_STATEMENT:
203         case ir::AstNodeType::SWITCH_CASE_STATEMENT:
204         case ir::AstNodeType::SWITCH_STATEMENT:
205         case ir::AstNodeType::THROW_STATEMENT:
206         case ir::AstNodeType::TRY_STATEMENT:
207         case ir::AstNodeType::WHILE_STATEMENT:
208             return true;
209         default:
210             break;
211     }
212     return false;
213 }
214 
IsLiteral(ir::AstNodeType type)215 bool IsLiteral(ir::AstNodeType type)
216 {
217     switch (type) {
218         case ir::AstNodeType::BIGINT_LITERAL:
219         case ir::AstNodeType::BOOLEAN_LITERAL:
220         case ir::AstNodeType::CHAR_LITERAL:
221         case ir::AstNodeType::NULL_LITERAL:
222         case ir::AstNodeType::UNDEFINED_LITERAL:
223         case ir::AstNodeType::NUMBER_LITERAL:
224         case ir::AstNodeType::REGEXP_LITERAL:
225         case ir::AstNodeType::STRING_LITERAL:
226         case ir::AstNodeType::TEMPLATE_LITERAL:
227             return true;
228         default:
229             break;
230     }
231     return false;
232 }
233 
IsModule(ir::AstNodeType type)234 bool IsModule(ir::AstNodeType type)
235 {
236     switch (type) {
237         case ir::AstNodeType::EXPORT_ALL_DECLARATION:
238         case ir::AstNodeType::EXPORT_DEFAULT_DECLARATION:
239         case ir::AstNodeType::EXPORT_NAMED_DECLARATION:
240         case ir::AstNodeType::EXPORT_SPECIFIER:
241         case ir::AstNodeType::IMPORT_DECLARATION:
242         case ir::AstNodeType::IMPORT_EXPRESSION:
243         case ir::AstNodeType::IMPORT_DEFAULT_SPECIFIER:
244         case ir::AstNodeType::IMPORT_NAMESPACE_SPECIFIER:
245         case ir::AstNodeType::IMPORT_SPECIFIER:
246             return true;
247         default:
248             break;
249     }
250     return false;
251 }
252 
GetTargetTokenKind(const ir::AstNode * node)253 CompletionEntryKind GetTargetTokenKind(const ir::AstNode *node)
254 {
255     CompletionEntryKind normalResult = CompletionEntryKind::ALIAS_TYPE;
256     if (node == nullptr) {
257         return normalResult;
258     }
259     auto type = node->Type();
260     if (IsExpress(type)) {
261         normalResult = CompletionEntryKind::OPERATOR;
262     } else if (IsStatement(type)) {
263         normalResult = CompletionEntryKind::SNIPPET;
264     } else if (IsLiteral(type)) {
265         normalResult = CompletionEntryKind::VALUE;
266     } else if (IsModule(type)) {
267         normalResult = CompletionEntryKind::MODULE;
268     }
269     switch (type) {
270         case ir::AstNodeType::CLASS_DEFINITION:
271         case ir::AstNodeType::CLASS_DECLARATION:
272             return CompletionEntryKind::CLASS;
273         case ir::AstNodeType::CLASS_PROPERTY:
274         case ir::AstNodeType::PROPERTY:
275             return CompletionEntryKind::FIELD;
276         case ir::AstNodeType::FUNCTION_DECLARATION:
277         case ir::AstNodeType::SCRIPT_FUNCTION:
278             return CompletionEntryKind::FUNCTION;
279         case ir::AstNodeType::METHOD_DEFINITION: {
280             auto kind = node->AsMethodDefinition()->Kind();
281             return (kind == ir::MethodDefinitionKind::CONSTRUCTOR) ? CompletionEntryKind::CONSTRUCTOR
282                                                                    : CompletionEntryKind::METHOD;
283         }
284         case ir::AstNodeType::NAMED_TYPE:
285             return CompletionEntryKind::TYPE_PARAMETER;
286         case ir::AstNodeType::STRUCT_DECLARATION:
287             return CompletionEntryKind::STRUCT;
288         case ir::AstNodeType::VARIABLE_DECLARATION:
289         case ir::AstNodeType::VARIABLE_DECLARATOR:
290             return CompletionEntryKind::VARIABLE;
291         default:
292             auto etsResult = GetTargetTokenKindIfETSType(type);
293             if (std::get<0>(etsResult)) {
294                 return std::get<1>(etsResult);
295             }
296             auto tsResult = GetTargetTokenKindIfTSType(type);
297             if (std::get<0>(tsResult)) {
298                 return std::get<1>(tsResult);
299             }
300     }
301     return normalResult;
302 }
303 
GetAliasDeclFromCurrentToken(const ir::AstNode * node)304 const ir::TSTypeAliasDeclaration *GetAliasDeclFromCurrentToken(const ir::AstNode *node)
305 {
306     if (node == nullptr) {
307         return nullptr;
308     }
309     const ir::TSTypeAliasDeclaration *aliasDecl = nullptr;
310     if (node->IsTSTypeAliasDeclaration()) {
311         aliasDecl = node->AsTSTypeAliasDeclaration();
312     } else if (node->IsIdentifier()) {
313         auto decl = compiler::DeclarationFromIdentifier(node->AsIdentifier());
314         if (decl == nullptr) {
315             return nullptr;
316         }
317         aliasDecl = decl->AsTSTypeAliasDeclaration();
318     }
319     return aliasDecl;
320 }
321 
GetAliasScriptElementKindImpl(es2panda_Context * context,size_t position)322 CompletionEntryKind GetAliasScriptElementKindImpl(es2panda_Context *context, size_t position)
323 {
324     auto touchingToken = GetTouchingToken(context, position, false);
325     auto aliasDecl = GetAliasDeclFromCurrentToken(touchingToken);
326     if (aliasDecl == nullptr) {
327         return CompletionEntryKind::TEXT;
328     }
329     auto typeAnnotation = aliasDecl->TypeAnnotation();
330     if (typeAnnotation == nullptr) {
331         return CompletionEntryKind::ALIAS_TYPE;
332     }
333     if (typeAnnotation->IsETSTypeReference()) {
334         auto part = typeAnnotation->AsETSTypeReference()->Part()->AsETSTypeReferencePart();
335         if (part == nullptr) {
336             return CompletionEntryKind::ALIAS_TYPE;
337         }
338         auto targetIdent = part->GetIdent();
339         auto decl = compiler::DeclarationFromIdentifier(targetIdent);
340         if (compiler::ClassDefinitionIsEnumTransformed(decl)) {
341             return CompletionEntryKind::ENUM;
342         }
343         return GetTargetTokenKind(decl);
344     }
345     return GetTargetTokenKind(typeAnnotation);
346 }
347 }  // namespace ark::es2panda::lsp
348