diff --git a/ets2panda/linter/.gitignore b/ets2panda/linter/.gitignore index 26590e3ca2b7477484ae2e04eb3e74159801e0bc..a9bcf7139e0c7bd0544a9b4a29435292ad9b21e8 100644 --- a/ets2panda/linter/.gitignore +++ b/ets2panda/linter/.gitignore @@ -3,6 +3,7 @@ bundle bundle-2.1.0.tgz dist node_modules +migration-results-statistics.json package-lock.json panda-tslinter-1.0.0.tgz coverage/ diff --git a/ets2panda/linter/src/lib/TypeScriptLinter.ts b/ets2panda/linter/src/lib/TypeScriptLinter.ts index 9a0f958dd60d3038f55a62e81d0ad1584875003d..00bfb125f3cd984f666238b7fbf488f5c0a1b536 100644 --- a/ets2panda/linter/src/lib/TypeScriptLinter.ts +++ b/ets2panda/linter/src/lib/TypeScriptLinter.ts @@ -87,7 +87,12 @@ import { BUILTIN_GENERIC_CONSTRUCTORS } from './utils/consts/BuiltinGenericConst import { DEFAULT_DECORATOR_WHITE_LIST } from './utils/consts/DefaultDecoratorWhitelist'; import { INVALID_IDENTIFIER_KEYWORDS } from './utils/consts/InValidIndentifierKeywords'; import { WORKER_MODULES, WORKER_TEXT } from './utils/consts/WorkerAPI'; -import { COLLECTIONS_TEXT, COLLECTIONS_MODULES } from './utils/consts/CollectionsAPI'; +import { + COLLECTIONS_TEXT, + COLLECTIONS_MODULES, + BIT_VECTOR, + ARKTS_COLLECTIONS_MODULE +} from './utils/consts/CollectionsAPI'; import { ASON_TEXT, ASON_MODULES, ARKTS_UTILS_TEXT, JSON_TEXT, ASON_WHITE_SET } from './utils/consts/ArkTSUtilsAPI'; import { interanlFunction } from './utils/consts/InternalFunction'; import { ETS_PART, PATH_SEPARATOR } from './utils/consts/OhmUrl'; @@ -8052,6 +8057,29 @@ export class TypeScriptLinter extends BaseTypeScriptLinter { } } + private checkCollectionsForPropAccess(node: ts.Node, ident: ts.Node): void { + if (!ts.isIdentifier(ident)) { + return; + } + const importBitVectorAutofix = this.checkBitVector(ident); + const replace = this.autofixer?.replaceNode(node, ident.getText()); + let autofix: Autofix[] | undefined = []; + + if (replace) { + autofix = replace; + } + + if (importBitVectorAutofix) { + autofix.push(importBitVectorAutofix); + } + + if (autofix.length === 0) { + autofix = undefined; + } + + this.incrementCounters(node, FaultID.NoNeedStdLibSendableContainer, autofix); + } + private checkCollectionsSymbol(node: ts.Node): void { if (!this.options.arkts2) { return; @@ -8062,14 +8090,17 @@ export class TypeScriptLinter extends BaseTypeScriptLinter { if (!parent) { return; } + if (ts.isPropertyAccessExpression(parent)) { - const autofix = this.autofixer?.replaceNode(parent, parent.name.text); - this.incrementCounters(node, FaultID.NoNeedStdLibSendableContainer, autofix); + this.checkCollectionsForPropAccess(parent, parent.name); + + return; } if (ts.isQualifiedName(parent)) { - const autofix = this.autofixer?.replaceNode(parent, parent.right.text); - this.incrementCounters(node, FaultID.NoNeedStdLibSendableContainer, autofix); + this.checkCollectionsForPropAccess(parent, parent.right); + + return; } if (ts.isImportSpecifier(parent) && ts.isIdentifier(node)) { @@ -8142,6 +8173,64 @@ export class TypeScriptLinter extends BaseTypeScriptLinter { } } + private checkBitVector(ident: ts.Identifier): Autofix | undefined { + if (!this.isBitVector(ident)) { + return undefined; + } + + let lastImportDeclaration: ts.Node | undefined; + let bitVectorImported: boolean = false; + for (const node of this.sourceFile.statements) { + if (!ts.isImportDeclaration(node)) { + continue; + } + lastImportDeclaration = node; + + if (this.checkImportDeclarationForBitVector(node)) { + bitVectorImported = true; + } + } + + if (bitVectorImported) { + return undefined; + } + + return this.autofixer?.importBitVector(ident, lastImportDeclaration); + } + + private isBitVector(ident: ts.Identifier): boolean { + void this; + + return ident.text === BIT_VECTOR; + } + + private checkImportDeclarationForBitVector(node: ts.ImportDeclaration): boolean { + const importSpecifier = node.moduleSpecifier; + if (!ts.isStringLiteral(importSpecifier)) { + return false; + } + const importSpecifierText = importSpecifier.text; + + const importClause = node.importClause; + if (!importClause) { + return false; + } + + const namedBindings = importClause.namedBindings; + if (!namedBindings || !ts.isNamedImports(namedBindings)) { + return false; + } + + let bitVectorImported = false; + for (const specifier of namedBindings.elements) { + if (this.isBitVector(specifier.name) && importSpecifierText === ARKTS_COLLECTIONS_MODULE) { + bitVectorImported = true; + } + } + + return bitVectorImported; + } + interfacesNeedToAlarm: ts.Identifier[] = []; interfacesNeedToImport: Set = new Set(); interfacesAlreadyImported: Set = new Set(); diff --git a/ets2panda/linter/src/lib/autofixes/Autofixer.ts b/ets2panda/linter/src/lib/autofixes/Autofixer.ts index 6c0a96ff547a2811936705f49ccca19ffc4b3383..a93089519d95b0876b3085d18ffc4770798328d7 100644 --- a/ets2panda/linter/src/lib/autofixes/Autofixer.ts +++ b/ets2panda/linter/src/lib/autofixes/Autofixer.ts @@ -64,6 +64,7 @@ import { import path from 'node:path'; import { isStdLibrarySymbol } from '../utils/functions/IsStdLibrary'; import { propertyAccessReplacements, identifierReplacements } from '../utils/consts/DeprecatedApi'; +import { ARKTS_COLLECTIONS_MODULE, BIT_VECTOR } from '../utils/consts/CollectionsAPI'; const UNDEFINED_NAME = 'undefined'; @@ -797,9 +798,9 @@ export class Autofixer { propAccessExpr ); // Create statement for the assignment expression, with or without parentheses based on the flag - const statement = needParentheses[index] ? - ts.factory.createExpressionStatement(ts.factory.createParenthesizedExpression(assignmentExpr)) : - ts.factory.createExpressionStatement(assignmentExpr); + const statement = needParentheses[index] + ? ts.factory.createExpressionStatement(ts.factory.createParenthesizedExpression(assignmentExpr)) + : ts.factory.createExpressionStatement(assignmentExpr); // Append the generated text for the destructuring assignment destructElementText += @@ -1090,7 +1091,7 @@ export class Autofixer { const moduleName = TsUtils.getModuleName(importDeclNode); const newPathParts = [moduleName ?? DEFAULT_MODULE_NAME, SRC_AND_MAIN, ...parts]; const newPath = newPathParts.join(PATH_SEPARATOR); - const newPathString = '\'' + newPath + '\''; + const newPathString = "'" + newPath + "'"; return [{ start: moduleSpecifier.getStart(), end: moduleSpecifier.getEnd(), replacementText: newPathString }]; } @@ -1104,7 +1105,7 @@ export class Autofixer { const newPathParts = [...beforeEts, SRC_AND_MAIN, ...afterEts]; const newPath = newPathParts.join(PATH_SEPARATOR); - const newPathString = '\'' + newPath + '\''; + const newPathString = "'" + newPath + "'"; return [{ start: moduleSpecifier.getStart(), end: moduleSpecifier.getEnd(), replacementText: newPathString }]; } @@ -1403,9 +1404,9 @@ export class Autofixer { fixVarDeclaration(node: ts.VariableDeclarationList): Autofix[] | undefined { const newNode = ts.factory.createVariableDeclarationList(node.declarations, ts.NodeFlags.Let); const text = this.printer.printNode(ts.EmitHint.Unspecified, newNode, node.getSourceFile()); - return this.canAutofixNoVar(node) ? - [{ start: node.getStart(), end: node.getEnd(), replacementText: text }] : - undefined; + return this.canAutofixNoVar(node) + ? [{ start: node.getStart(), end: node.getEnd(), replacementText: text }] + : undefined; } private getFixReturnTypeArrowFunction(funcLikeDecl: ts.FunctionLikeDeclaration, typeNode: ts.TypeNode): string { @@ -1526,15 +1527,14 @@ export class Autofixer { private static getReturnTypePosition(funcLikeDecl: ts.FunctionLikeDeclaration): number { if (funcLikeDecl.body) { - /* * Find position of the first node or token that follows parameters. * After that, iterate over child nodes in reverse order, until found * first closing parenthesis. */ - const postParametersPosition = ts.isArrowFunction(funcLikeDecl) ? - funcLikeDecl.equalsGreaterThanToken.getStart() : - funcLikeDecl.body.getStart(); + const postParametersPosition = ts.isArrowFunction(funcLikeDecl) + ? funcLikeDecl.equalsGreaterThanToken.getStart() + : funcLikeDecl.body.getStart(); const children = funcLikeDecl.getChildren(); for (let i = children.length - 1; i >= 0; i--) { @@ -1559,8 +1559,8 @@ export class Autofixer { ts.isTypeOfExpression(parent) || ts.isVoidExpression(parent) || ts.isAwaitExpression(parent) || - ts.isCallExpression(parent) && node === parent.expression || - ts.isBinaryExpression(parent) && !isAssignmentOperator(parent.operatorToken) + (ts.isCallExpression(parent) && node === parent.expression) || + (ts.isBinaryExpression(parent) && !isAssignmentOperator(parent.operatorToken)) ); } @@ -1896,7 +1896,6 @@ export class Autofixer { objectLiteralType: ts.Type | undefined ): Autofix[] | undefined { if (objectLiteralType) { - /* * Special case for object literal of Record type: fix object's property names * by replacing identifiers with string literals. @@ -2028,7 +2027,6 @@ export class Autofixer { newInterfaceName: string, objectLiteralExpr: ts.ObjectLiteralExpression ): Autofix { - /* * If object literal is initializing a variable or property, * then simply add new 'contextual' type to the declaration. @@ -2229,9 +2227,9 @@ export class Autofixer { return undefined; } - const heritageTypeExpression = typeNode ? - Autofixer.entityNameToExpression(typeNode.typeName) : - ts.factory.createIdentifier(typeDecl.name.text); + const heritageTypeExpression = typeNode + ? Autofixer.entityNameToExpression(typeNode.typeName) + : ts.factory.createIdentifier(typeDecl.name.text); return [ ts.factory.createHeritageClause( @@ -2297,7 +2295,7 @@ export class Autofixer { } const typeDecl = TsUtils.getDeclaration(objectLiteralType.getSymbol()); - if (!typeDecl || !ts.isClassDeclaration(typeDecl) && !ts.isInterfaceDeclaration(typeDecl) || !typeDecl.name) { + if (!typeDecl || (!ts.isClassDeclaration(typeDecl) && !ts.isInterfaceDeclaration(typeDecl)) || !typeDecl.name) { return undefined; } @@ -3408,7 +3406,7 @@ export class Autofixer { replacement = ts.factory.createCallExpression( ts.factory.createPropertyAccessExpression(callee.expression, ts.factory.createIdentifier(INVOKE_METHOD)), undefined, - [ts.factory.createStringLiteral(callee.name.getText()), ...args || []] + [ts.factory.createStringLiteral(callee.name.getText()), ...(args || [])] ); } else if (ts.isIdentifier(callee)) { // For expressions like foo() or bar(123) => foo.invoke(...) or bar.invoke(...) @@ -3620,11 +3618,11 @@ export class Autofixer { collectExistingNames(parentEnum: ts.EnumDeclaration, tsEnumMember: ts.EnumMember): Set { void this; return new Set( - parentEnum.members. - filter((m) => { + parentEnum.members + .filter((m) => { return m !== tsEnumMember; - }). - map((m) => { + }) + .map((m) => { const nameNode = m.name; if (ts.isStringLiteral(nameNode)) { const fix = this.fixLiteralAsPropertyNamePropertyName(nameNode); @@ -3729,11 +3727,11 @@ export class Autofixer { }); if (items.length > 1) { - const formattedList = items. - map((item) => { + const formattedList = items + .map((item) => { return ` ${item.trim()},`; - }). - join('\n'); + }) + .join('\n'); return `{\n${formattedList}\n}`; } return `{${importList}}`; @@ -4150,7 +4148,7 @@ export class Autofixer { return undefined; } - private static findParentVariableDeclaration(node: ts.Node): ts.VariableDeclaration | undefined { + private static findParentVariableDeclaration(node: ts.Node): ts.VariableDeclaration | undefined { while (node) { if (ts.isVariableDeclaration(node)) { return node; @@ -4240,7 +4238,7 @@ export class Autofixer { const propertyAccessExpr = node.expression as ts.PropertyAccessExpression; const newCallExpr = this.createJSInvokeCallExpression(propertyAccessExpr.expression, INVOKE_METHOD, [ ts.factory.createStringLiteral(propertyAccessExpr.name.text), - ...newArgs || [] + ...(newArgs || []) ]); if (!newCallExpr) { @@ -4249,7 +4247,7 @@ export class Autofixer { return this.printer.printNode(ts.EmitHint.Unspecified, newCallExpr, node.getSourceFile()); } default: { - const callExpr = this.createJSInvokeCallExpression(node.expression, INVOKE, [...newArgs || []]); + const callExpr = this.createJSInvokeCallExpression(node.expression, INVOKE, [...(newArgs || [])]); if (!callExpr) { return undefined; @@ -4267,7 +4265,7 @@ export class Autofixer { return `${base}.${GET_PROPERTY}('${propName}')`; } else if (ts.isNewExpression(node)) { const newArgs = this.createArgs(node.arguments); - const newCallExpr = this.createJSInvokeCallExpression(node.expression, INSTANTIATE, [...newArgs || []]); + const newCallExpr = this.createJSInvokeCallExpression(node.expression, INSTANTIATE, [...(newArgs || [])]); if (!newCallExpr) { return undefined; @@ -4322,9 +4320,9 @@ export class Autofixer { private createInsertStatementsFix(importDecl: ts.ImportDeclaration, statements: string[]): Autofix { const joinedStatements = statements.join(this.getNewLine()); - const replacementText = this.detectNeedsLeadingNewline(importDecl) ? - this.getNewLine() + joinedStatements : - joinedStatements; + const replacementText = this.detectNeedsLeadingNewline(importDecl) + ? this.getNewLine() + joinedStatements + : joinedStatements; return { start: importDecl.getEnd(), @@ -4339,7 +4337,7 @@ export class Autofixer { private detectNeedsLeadingNewline(importDecl: ts.ImportDeclaration): boolean { const prevToken = ts.getLeadingCommentRanges(this.sourceFile.text, importDecl.getFullStart())?.[0]; - return !!prevToken && !(/^\s*$/).test(this.sourceFile.text.slice(prevToken.end, importDecl.getStart())); + return !!prevToken && !/^\s*$/.test(this.sourceFile.text.slice(prevToken.end, importDecl.getStart())); } private getStatementForInterOpImportJsOnNamedBindings( @@ -4736,9 +4734,9 @@ export class Autofixer { const expr = callExpr.expression; const hasOptionalChain = !!callExpr.questionDotToken; - const replacementText = hasOptionalChain ? - `${expr.getText()}${callExpr.questionDotToken.getText()}unsafeCall` : - `${expr.getText()}.unsafeCall`; + const replacementText = hasOptionalChain + ? `${expr.getText()}${callExpr.questionDotToken.getText()}unsafeCall` + : `${expr.getText()}.unsafeCall`; return [ { @@ -4780,18 +4778,18 @@ export class Autofixer { } private static createExactObjectInitializer(type: ts.TypeLiteralNode): ts.ObjectLiteralExpression { - const properties = type.members. - filter((member): member is ts.PropertySignature => { + const properties = type.members + .filter((member): member is ts.PropertySignature => { return ts.isPropertySignature(member); - }). - map((member) => { + }) + .map((member) => { const initializer = Autofixer.createInitializerForPropertySignature(member); if (initializer) { return ts.factory.createPropertyAssignment(member.name, initializer); } return null; - }). - filter((property): property is ts.PropertyAssignment => { + }) + .filter((property): property is ts.PropertyAssignment => { return property !== null; }); @@ -4869,7 +4867,7 @@ export class Autofixer { if (ts.isBlock(fn.body)) { const statements = fn.body.statements; const lastExpr = statements.length > 0 ? statements[statements.length - 1] : undefined; - if (hasReturn && lastExpr && !ts.isReturnStatement(lastExpr) || !hasReturn) { + if ((hasReturn && lastExpr && !ts.isReturnStatement(lastExpr)) || !hasReturn) { const text = this.createUndefinedReturnStatement(fn, lastExpr); fixes.push({ start: lastExpr ? lastExpr.getEnd() : fn.body.getEnd() - 1, @@ -4994,11 +4992,11 @@ export class Autofixer { ) { return undefined; } - return `<${typeArg. - map((arg) => { + return `<${typeArg + .map((arg) => { return this.nonCommentPrinter.printNode(ts.EmitHint.Unspecified, arg, sourceFile); - }). - join(', ')}>`; + }) + .join(', ')}>`; } if (!typeArg || !this.isTypeArgumentAccessible(sourceFile, typeArg as ts.TypeNode)) { return undefined; @@ -5150,7 +5148,7 @@ export class Autofixer { const newCallExpr = this.createJSInvokeCallExpression(accessedProperty, INVOKE_METHOD, [ ts.factory.createStringLiteral(ident.text), - ...newArgs || [] + ...(newArgs || []) ]); if (!newCallExpr) { @@ -5240,6 +5238,37 @@ export class Autofixer { return [{ start: node.getStart(), end: node.getEnd(), replacementText: text }]; } + importBitVector(node: ts.Node, lastImportDeclaration: ts.Node | undefined): Autofix | undefined { + const importDeclaration = ts.factory.createImportDeclaration( + undefined, + ts.factory.createImportClause( + false, + undefined, + ts.factory.createNamedImports([ + ts.factory.createImportSpecifier(false, undefined, ts.factory.createIdentifier(BIT_VECTOR)) + ]) + ), + ts.factory.createStringLiteral(ARKTS_COLLECTIONS_MODULE), + undefined + ); + // find the last import statement; + + let replacementText: string = this.nonCommentPrinter.printNode( + ts.EmitHint.Unspecified, + importDeclaration, + node.getSourceFile() + ); + let start: number = 0; + let end: number = 0; + + if (lastImportDeclaration) { + start = end = lastImportDeclaration.getEnd(); + replacementText = this.getNewLine() + replacementText + this.getNewLine(); + } + + return { start, end, replacementText }; + } + fixRepeat(stmt: ts.ExpressionStatement): Autofix[] { const newExpr = ts.factory.createCallExpression(ts.factory.createIdentifier(VIRTUAL_SCROLL_IDENTIFIER), undefined, [ ts.factory.createObjectLiteralExpression( @@ -5362,11 +5391,9 @@ export class Autofixer { } fixSideEffectImport(importDeclNode: ts.ImportDeclaration): Autofix[] { - const initModuleCall = ts.factory.createCallExpression( - ts.factory.createIdentifier("initModule"), - undefined, - [importDeclNode.moduleSpecifier] - ); + const initModuleCall = ts.factory.createCallExpression(ts.factory.createIdentifier('initModule'), undefined, [ + importDeclNode.moduleSpecifier + ]); const expressionStatement = ts.factory.createExpressionStatement(initModuleCall); const replacedText = this.printer.printNode( ts.EmitHint.Unspecified, @@ -5374,10 +5401,12 @@ export class Autofixer { importDeclNode.getSourceFile() ); - return [{ - start: importDeclNode.getStart(), - end: importDeclNode.getEnd(), - replacementText: replacedText - }]; + return [ + { + start: importDeclNode.getStart(), + end: importDeclNode.getEnd(), + replacementText: replacedText + } + ]; } } diff --git a/ets2panda/linter/src/lib/utils/consts/CollectionsAPI.ts b/ets2panda/linter/src/lib/utils/consts/CollectionsAPI.ts index a7c1698e3ba00a285e16df6ee6b1c418f3832d4b..331a36bb29639f47336a980fbe78db1f32e6ab0f 100644 --- a/ets2panda/linter/src/lib/utils/consts/CollectionsAPI.ts +++ b/ets2panda/linter/src/lib/utils/consts/CollectionsAPI.ts @@ -14,4 +14,6 @@ */ export const COLLECTIONS_TEXT = 'collections'; +export const ARKTS_COLLECTIONS_MODULE = '@arkts.collections'; +export const BIT_VECTOR = 'BitVector'; export const COLLECTIONS_MODULES = ['@arkts.collections', '@kit.ArkTS']; diff --git a/ets2panda/linter/test/main/collections_module.ets b/ets2panda/linter/test/main/collections_module.ets index 0d73282ec64470e2564c0681afdf0ec6ee331414..f61a5a5a4d52d648c5a17b1166ade1c58a424468 100644 --- a/ets2panda/linter/test/main/collections_module.ets +++ b/ets2panda/linter/test/main/collections_module.ets @@ -40,3 +40,7 @@ function tesCollectionsUsage() { function test(array: collections.Array) { const map = collections.Map(); } + +function testBitVector(bv: collections.BitVector) { + const bitVector = new collections.BitVector(); +} diff --git a/ets2panda/linter/test/main/collections_module.ets.arkts2.json b/ets2panda/linter/test/main/collections_module.ets.arkts2.json index 7286b3c366e4d8b32395b1830bd48e1ac22a1207..6fb86f244dfc3ed0b8908ed97460eb09399ffc6b 100644 --- a/ets2panda/linter/test/main/collections_module.ets.arkts2.json +++ b/ets2panda/linter/test/main/collections_module.ets.arkts2.json @@ -48,7 +48,7 @@ "line": 26, "column": 23, "endLine": 26, - "endColumn": 34, + "endColumn": 40, "problem": "NoNeedStdLibSendableContainer", "suggest": "", "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", @@ -58,7 +58,7 @@ "line": 26, "column": 55, "endLine": 26, - "endColumn": 66, + "endColumn": 72, "problem": "NoNeedStdLibSendableContainer", "suggest": "", "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", @@ -68,7 +68,7 @@ "line": 28, "column": 28, "endLine": 28, - "endColumn": 44, + "endColumn": 50, "problem": "NoNeedStdLibSendableContainer", "suggest": "", "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", @@ -78,7 +78,7 @@ "line": 30, "column": 28, "endLine": 30, - "endColumn": 42, + "endColumn": 48, "problem": "NoNeedStdLibSendableContainer", "suggest": "", "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", @@ -88,7 +88,7 @@ "line": 32, "column": 21, "endLine": 32, - "endColumn": 37, + "endColumn": 43, "problem": "NoNeedStdLibSendableContainer", "suggest": "", "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", @@ -98,7 +98,7 @@ "line": 34, "column": 23, "endLine": 34, - "endColumn": 39, + "endColumn": 45, "problem": "NoNeedStdLibSendableContainer", "suggest": "", "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", @@ -108,7 +108,7 @@ "line": 34, "column": 60, "endLine": 34, - "endColumn": 76, + "endColumn": 82, "problem": "NoNeedStdLibSendableContainer", "suggest": "", "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", @@ -118,7 +118,7 @@ "line": 40, "column": 22, "endLine": 40, - "endColumn": 33, + "endColumn": 39, "problem": "NoNeedStdLibSendableContainer", "suggest": "", "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", @@ -138,7 +138,7 @@ "line": 41, "column": 17, "endLine": 41, - "endColumn": 28, + "endColumn": 32, "problem": "NoNeedStdLibSendableContainer", "suggest": "", "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", @@ -153,6 +153,46 @@ "suggest": "", "rule": "Classes cannot be used as objects (arkts-no-classes-as-obj)", "severity": "ERROR" + }, + { + "line": 44, + "column": 28, + "endLine": 44, + "endColumn": 49, + "problem": "NoNeedStdLibSendableContainer", + "suggest": "", + "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", + "severity": "ERROR" + }, + { + "line": 45, + "column": 11, + "endLine": 45, + "endColumn": 58, + "problem": "AnyType", + "suggest": "", + "rule": "Use explicit types instead of \"any\", \"unknown\" (arkts-no-any-unknown)", + "severity": "ERROR" + }, + { + "line": 45, + "column": 27, + "endLine": 45, + "endColumn": 48, + "problem": "DynamicCtorCall", + "suggest": "", + "rule": "\"new\" expression with dynamic constructor type is not supported (arkts-no-dynamic-ctor-call)", + "severity": "ERROR" + }, + { + "line": 45, + "column": 27, + "endLine": 45, + "endColumn": 48, + "problem": "NoNeedStdLibSendableContainer", + "suggest": "", + "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", + "severity": "ERROR" } ] } diff --git a/ets2panda/linter/test/main/collections_module.ets.autofix.json b/ets2panda/linter/test/main/collections_module.ets.autofix.json index 1d3cd393a428875374beb8c8f466ccfb77fa4307..9be897f59e5ec888e5fcf18f65ebcbdab3e3da2b 100644 --- a/ets2panda/linter/test/main/collections_module.ets.autofix.json +++ b/ets2panda/linter/test/main/collections_module.ets.autofix.json @@ -81,7 +81,7 @@ "line": 26, "column": 23, "endLine": 26, - "endColumn": 34, + "endColumn": 40, "problem": "NoNeedStdLibSendableContainer", "autofix": [ { @@ -91,7 +91,7 @@ "line": 26, "column": 23, "endLine": 26, - "endColumn": 34 + "endColumn": 40 } ], "suggest": "", @@ -102,7 +102,7 @@ "line": 26, "column": 55, "endLine": 26, - "endColumn": 66, + "endColumn": 72, "problem": "NoNeedStdLibSendableContainer", "autofix": [ { @@ -112,7 +112,7 @@ "line": 26, "column": 55, "endLine": 26, - "endColumn": 66 + "endColumn": 72 } ], "suggest": "", @@ -123,7 +123,7 @@ "line": 28, "column": 28, "endLine": 28, - "endColumn": 44, + "endColumn": 50, "problem": "NoNeedStdLibSendableContainer", "autofix": [ { @@ -133,7 +133,7 @@ "line": 28, "column": 28, "endLine": 28, - "endColumn": 44 + "endColumn": 50 } ], "suggest": "", @@ -144,7 +144,7 @@ "line": 30, "column": 28, "endLine": 30, - "endColumn": 42, + "endColumn": 48, "problem": "NoNeedStdLibSendableContainer", "autofix": [ { @@ -154,7 +154,7 @@ "line": 30, "column": 28, "endLine": 30, - "endColumn": 42 + "endColumn": 48 } ], "suggest": "", @@ -165,7 +165,7 @@ "line": 32, "column": 21, "endLine": 32, - "endColumn": 37, + "endColumn": 43, "problem": "NoNeedStdLibSendableContainer", "autofix": [ { @@ -175,7 +175,7 @@ "line": 32, "column": 21, "endLine": 32, - "endColumn": 37 + "endColumn": 43 } ], "suggest": "", @@ -186,7 +186,7 @@ "line": 34, "column": 23, "endLine": 34, - "endColumn": 39, + "endColumn": 45, "problem": "NoNeedStdLibSendableContainer", "autofix": [ { @@ -196,7 +196,7 @@ "line": 34, "column": 23, "endLine": 34, - "endColumn": 39 + "endColumn": 45 } ], "suggest": "", @@ -207,7 +207,7 @@ "line": 34, "column": 60, "endLine": 34, - "endColumn": 76, + "endColumn": 82, "problem": "NoNeedStdLibSendableContainer", "autofix": [ { @@ -217,7 +217,7 @@ "line": 34, "column": 60, "endLine": 34, - "endColumn": 76 + "endColumn": 82 } ], "suggest": "", @@ -228,7 +228,7 @@ "line": 40, "column": 22, "endLine": 40, - "endColumn": 33, + "endColumn": 39, "problem": "NoNeedStdLibSendableContainer", "autofix": [ { @@ -238,7 +238,7 @@ "line": 40, "column": 22, "endLine": 40, - "endColumn": 33 + "endColumn": 39 } ], "suggest": "", @@ -259,7 +259,7 @@ "line": 41, "column": 17, "endLine": 41, - "endColumn": 28, + "endColumn": 32, "problem": "NoNeedStdLibSendableContainer", "autofix": [ { @@ -269,7 +269,7 @@ "line": 41, "column": 17, "endLine": 41, - "endColumn": 28 + "endColumn": 32 } ], "suggest": "", @@ -285,6 +285,86 @@ "suggest": "", "rule": "Classes cannot be used as objects (arkts-no-classes-as-obj)", "severity": "ERROR" + }, + { + "line": 44, + "column": 28, + "endLine": 44, + "endColumn": 49, + "problem": "NoNeedStdLibSendableContainer", + "autofix": [ + { + "start": 1514, + "end": 1535, + "replacementText": "BitVector", + "line": 44, + "column": 28, + "endLine": 44, + "endColumn": 49 + }, + { + "start": 919, + "end": 919, + "replacementText": "\nimport { BitVector } from \"@arkts.collections\";\n", + "line": 44, + "column": 28, + "endLine": 44, + "endColumn": 49 + } + ], + "suggest": "", + "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", + "severity": "ERROR" + }, + { + "line": 45, + "column": 11, + "endLine": 45, + "endColumn": 58, + "problem": "AnyType", + "suggest": "", + "rule": "Use explicit types instead of \"any\", \"unknown\" (arkts-no-any-unknown)", + "severity": "ERROR" + }, + { + "line": 45, + "column": 27, + "endLine": 45, + "endColumn": 48, + "problem": "DynamicCtorCall", + "suggest": "", + "rule": "\"new\" expression with dynamic constructor type is not supported (arkts-no-dynamic-ctor-call)", + "severity": "ERROR" + }, + { + "line": 45, + "column": 27, + "endLine": 45, + "endColumn": 48, + "problem": "NoNeedStdLibSendableContainer", + "autofix": [ + { + "start": 1573, + "end": 1594, + "replacementText": "BitVector", + "line": 45, + "column": 27, + "endLine": 45, + "endColumn": 48 + }, + { + "start": 919, + "end": 919, + "replacementText": "\nimport { BitVector } from \"@arkts.collections\";\n", + "line": 45, + "column": 27, + "endLine": 45, + "endColumn": 48 + } + ], + "suggest": "", + "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", + "severity": "ERROR" } ] } diff --git a/ets2panda/linter/test/main/collections_module.ets.json b/ets2panda/linter/test/main/collections_module.ets.json index c85948ef43d15c11df4ea2642653f1aa07028852..927ff202214f3a1090827f0856d16510b65298d6 100644 --- a/ets2panda/linter/test/main/collections_module.ets.json +++ b/ets2panda/linter/test/main/collections_module.ets.json @@ -33,6 +33,16 @@ "suggest": "", "rule": "Classes cannot be used as objects (arkts-no-classes-as-obj)", "severity": "WARNING" + }, + { + "line": 45, + "column": 11, + "endLine": 45, + "endColumn": 58, + "problem": "AnyType", + "suggest": "", + "rule": "Use explicit types instead of \"any\", \"unknown\" (arkts-no-any-unknown)", + "severity": "ERROR" } ] } diff --git a/ets2panda/linter/test/main/collections_module.ets.migrate.ets b/ets2panda/linter/test/main/collections_module.ets.migrate.ets index 81cfa37dfc52720a009fc7648421b1f1158efd5a..9915905ea53f6be768dfe0ad9871dd9059a031a9 100644 --- a/ets2panda/linter/test/main/collections_module.ets.migrate.ets +++ b/ets2panda/linter/test/main/collections_module.ets.migrate.ets @@ -19,7 +19,9 @@ -import { collections as definedCollections } from './ignore_files/user_defined_collections'; //legal +import { collections as definedCollections } from './ignore_files/user_defined_collections'; +import { BitVector } from "@arkts.collections"; + //legal function tesCollectionsUsage() { @@ -40,3 +42,7 @@ function tesCollectionsUsage() { function test(array: Array) { const map = Map(); } + +function testBitVector(bv: BitVector) { + const bitVector = new BitVector(); +} diff --git a/ets2panda/linter/test/main/collections_module.ets.migrate.json b/ets2panda/linter/test/main/collections_module.ets.migrate.json index dd7b500c7435da5e5cbdc0a12e60930e24375f66..e3768540dc783f9b6fe11d045ce1217df7aaff07 100644 --- a/ets2panda/linter/test/main/collections_module.ets.migrate.json +++ b/ets2panda/linter/test/main/collections_module.ets.migrate.json @@ -15,14 +15,34 @@ ], "result": [ { - "line": 41, + "line": 43, "column": 11, - "endLine": 41, + "endLine": 43, "endColumn": 38, "problem": "AnyType", "suggest": "", "rule": "Use explicit types instead of \"any\", \"unknown\" (arkts-no-any-unknown)", "severity": "ERROR" + }, + { + "line": 47, + "column": 11, + "endLine": 47, + "endColumn": 46, + "problem": "AnyType", + "suggest": "", + "rule": "Use explicit types instead of \"any\", \"unknown\" (arkts-no-any-unknown)", + "severity": "ERROR" + }, + { + "line": 47, + "column": 27, + "endLine": 47, + "endColumn": 36, + "problem": "DynamicCtorCall", + "suggest": "", + "rule": "\"new\" expression with dynamic constructor type is not supported (arkts-no-dynamic-ctor-call)", + "severity": "ERROR" } ] } diff --git a/ets2panda/linter/test/main/property_access_by_index.ets.arkts2.json b/ets2panda/linter/test/main/property_access_by_index.ets.arkts2.json index 2247b1cc2e70af1c1a076519ab7bedee45e4528e..d53752ee4808099169beec98c3ba007c4bf70fef 100644 --- a/ets2panda/linter/test/main/property_access_by_index.ets.arkts2.json +++ b/ets2panda/linter/test/main/property_access_by_index.ets.arkts2.json @@ -868,7 +868,7 @@ "line": 177, "column": 23, "endLine": 177, - "endColumn": 34, + "endColumn": 44, "problem": "NoNeedStdLibSendableContainer", "suggest": "", "rule": "Sendable containers are not supported (arkts-no-need-stdlib-sendable-containers)", @@ -995,4 +995,4 @@ "severity": "ERROR" } ] -} \ No newline at end of file +} diff --git a/ets2panda/linter/test/main/property_access_by_index.ets.autofix.json b/ets2panda/linter/test/main/property_access_by_index.ets.autofix.json index c63d81f2b66aa51101a405779bdcbd7b1e26967f..efd13151c42adb61ca4eccc3c89d3658bcbe0239 100644 --- a/ets2panda/linter/test/main/property_access_by_index.ets.autofix.json +++ b/ets2panda/linter/test/main/property_access_by_index.ets.autofix.json @@ -1,6 +1,6 @@ { "copyright": [ - "Copyright (c) 2023-2024 Huawei Device Co., Ltd.", + "Copyright (c) 2024-2025 Huawei Device Co., Ltd.", "Licensed under the Apache License, Version 2.0 (the 'License');", "you may not use this file except in compliance with the License.", "You may obtain a copy of the License at", @@ -1374,7 +1374,7 @@ "line": 177, "column": 23, "endLine": 177, - "endColumn": 34, + "endColumn": 44, "problem": "NoNeedStdLibSendableContainer", "autofix": [ { @@ -1384,7 +1384,16 @@ "line": 177, "column": 23, "endLine": 177, - "endColumn": 34 + "endColumn": 44 + }, + { + "start": 713, + "end": 713, + "replacementText": "\nimport { BitVector } from \"@arkts.collections\";\n", + "line": 177, + "column": 23, + "endLine": 177, + "endColumn": 44 } ], "suggest": "", @@ -1600,4 +1609,4 @@ "severity": "ERROR" } ] -} \ No newline at end of file +} diff --git a/ets2panda/linter/test/main/property_access_by_index.ets.migrate.ets b/ets2panda/linter/test/main/property_access_by_index.ets.migrate.ets index 9d61b8611db3da19dc0cfbad2104808d626dda2c..6a3cbe36afb397b39f328e127c7b0533ce69429e 100644 --- a/ets2panda/linter/test/main/property_access_by_index.ets.migrate.ets +++ b/ets2panda/linter/test/main/property_access_by_index.ets.migrate.ets @@ -13,6 +13,8 @@ * limitations under the License. */ import {OhosInterface} from './oh_modules/ohos_lib'; +import { BitVector } from "@arkts.collections"; + // #14071 class A { diff --git a/ets2panda/linter/test/main/property_access_by_index.ets.migrate.json b/ets2panda/linter/test/main/property_access_by_index.ets.migrate.json index e2746dde008b85a1c320af9f8162e34e82dd1c34..12bd72ca456622b4c439c477985f0c361bcf2c04 100644 --- a/ets2panda/linter/test/main/property_access_by_index.ets.migrate.json +++ b/ets2panda/linter/test/main/property_access_by_index.ets.migrate.json @@ -15,9 +15,9 @@ ], "result": [ { - "line": 22, + "line": 24, "column": 3, - "endLine": 22, + "endLine": 24, "endColumn": 14, "problem": "PropertyAccessByIndex", "suggest": "", @@ -25,9 +25,9 @@ "severity": "ERROR" }, { - "line": 25, + "line": 27, "column": 10, - "endLine": 25, + "endLine": 27, "endColumn": 21, "problem": "PropertyAccessByIndex", "suggest": "", @@ -35,9 +35,9 @@ "severity": "ERROR" }, { - "line": 37, + "line": 39, "column": 1, - "endLine": 37, + "endLine": 39, "endColumn": 7, "problem": "RuntimeArrayCheck", "suggest": "", @@ -45,9 +45,9 @@ "severity": "ERROR" }, { - "line": 38, + "line": 40, "column": 1, - "endLine": 38, + "endLine": 40, "endColumn": 7, "problem": "RuntimeArrayCheck", "suggest": "", @@ -55,9 +55,9 @@ "severity": "ERROR" }, { - "line": 39, + "line": 41, "column": 1, - "endLine": 39, + "endLine": 41, "endColumn": 7, "problem": "RuntimeArrayCheck", "suggest": "", @@ -65,9 +65,9 @@ "severity": "ERROR" }, { - "line": 46, + "line": 48, "column": 3, - "endLine": 46, + "endLine": 48, "endColumn": 9, "problem": "PropertyAccessByIndex", "suggest": "", @@ -75,9 +75,9 @@ "severity": "ERROR" }, { - "line": 50, + "line": 52, "column": 3, - "endLine": 50, + "endLine": 52, "endColumn": 9, "problem": "PropertyAccessByIndex", "suggest": "", @@ -85,9 +85,9 @@ "severity": "ERROR" }, { - "line": 57, + "line": 59, "column": 5, - "endLine": 57, + "endLine": 59, "endColumn": 29, "problem": "AnyType", "suggest": "", @@ -95,35 +95,15 @@ "severity": "ERROR" }, { - "line": 57, + "line": 59, "column": 14, - "endLine": 57, + "endLine": 59, "endColumn": 29, "problem": "GenericCallNoTypeArgs", "suggest": "", "rule": "Type inference in case of generic function calls is limited (arkts-no-inferred-generic-params)", "severity": "ERROR" }, - { - "line": 70, - "column": 1, - "endLine": 70, - "endColumn": 10, - "problem": "RuntimeArrayCheck", - "suggest": "", - "rule": "Array bound not checked. (arkts-runtime-array-check)", - "severity": "ERROR" - }, - { - "line": 71, - "column": 1, - "endLine": 71, - "endColumn": 10, - "problem": "RuntimeArrayCheck", - "suggest": "", - "rule": "Array bound not checked. (arkts-runtime-array-check)", - "severity": "ERROR" - }, { "line": 72, "column": 1, @@ -198,7 +178,7 @@ "line": 79, "column": 1, "endLine": 79, - "endColumn": 11, + "endColumn": 10, "problem": "RuntimeArrayCheck", "suggest": "", "rule": "Array bound not checked. (arkts-runtime-array-check)", @@ -208,7 +188,7 @@ "line": 80, "column": 1, "endLine": 80, - "endColumn": 11, + "endColumn": 10, "problem": "RuntimeArrayCheck", "suggest": "", "rule": "Array bound not checked. (arkts-runtime-array-check)", @@ -265,9 +245,29 @@ "severity": "ERROR" }, { - "line": 97, + "line": 86, "column": 1, - "endLine": 97, + "endLine": 86, + "endColumn": 11, + "problem": "RuntimeArrayCheck", + "suggest": "", + "rule": "Array bound not checked. (arkts-runtime-array-check)", + "severity": "ERROR" + }, + { + "line": 87, + "column": 1, + "endLine": 87, + "endColumn": 11, + "problem": "RuntimeArrayCheck", + "suggest": "", + "rule": "Array bound not checked. (arkts-runtime-array-check)", + "severity": "ERROR" + }, + { + "line": 99, + "column": 1, + "endLine": 99, "endColumn": 18, "problem": "UnsupportPropNameFromValue", "suggest": "", @@ -275,9 +275,9 @@ "severity": "ERROR" }, { - "line": 98, + "line": 100, "column": 1, - "endLine": 98, + "endLine": 100, "endColumn": 17, "problem": "UnsupportPropNameFromValue", "suggest": "", @@ -285,9 +285,9 @@ "severity": "ERROR" }, { - "line": 99, + "line": 101, "column": 1, - "endLine": 99, + "endLine": 101, "endColumn": 17, "problem": "UnsupportPropNameFromValue", "suggest": "", @@ -295,9 +295,9 @@ "severity": "ERROR" }, { - "line": 107, + "line": 109, "column": 24, - "endLine": 107, + "endLine": 109, "endColumn": 39, "problem": "ArrayIndexExprType", "suggest": "", @@ -305,9 +305,9 @@ "severity": "ERROR" }, { - "line": 107, + "line": 109, "column": 24, - "endLine": 107, + "endLine": 109, "endColumn": 39, "problem": "BuiltinSymbolIterator", "suggest": "", @@ -315,9 +315,9 @@ "severity": "ERROR" }, { - "line": 108, + "line": 110, "column": 5, - "endLine": 108, + "endLine": 110, "endColumn": 40, "problem": "AnyType", "suggest": "", @@ -325,9 +325,9 @@ "severity": "ERROR" }, { - "line": 117, + "line": 119, "column": 20, - "endLine": 117, + "endLine": 119, "endColumn": 35, "problem": "ArrayIndexExprType", "suggest": "", @@ -335,9 +335,9 @@ "severity": "ERROR" }, { - "line": 117, + "line": 119, "column": 20, - "endLine": 117, + "endLine": 119, "endColumn": 35, "problem": "BuiltinSymbolIterator", "suggest": "", @@ -345,9 +345,9 @@ "severity": "ERROR" }, { - "line": 118, + "line": 120, "column": 5, - "endLine": 118, + "endLine": 120, "endColumn": 36, "problem": "AnyType", "suggest": "", @@ -355,9 +355,9 @@ "severity": "ERROR" }, { - "line": 139, + "line": 141, "column": 12, - "endLine": 139, + "endLine": 141, "endColumn": 31, "problem": "CreatingPrimitiveTypes", "suggest": "", @@ -365,9 +365,9 @@ "severity": "ERROR" }, { - "line": 159, + "line": 161, "column": 3, - "endLine": 159, + "endLine": 161, "endColumn": 9, "problem": "PropertyAccessByIndex", "suggest": "", @@ -375,9 +375,9 @@ "severity": "ERROR" }, { - "line": 172, + "line": 174, "column": 1, - "endLine": 172, + "endLine": 174, "endColumn": 9, "problem": "PropertyAccessByIndex", "suggest": "", @@ -385,9 +385,9 @@ "severity": "ERROR" }, { - "line": 173, + "line": 175, "column": 1, - "endLine": 173, + "endLine": 175, "endColumn": 13, "problem": "PropertyAccessByIndex", "suggest": "", @@ -395,9 +395,9 @@ "severity": "ERROR" }, { - "line": 174, + "line": 176, "column": 1, - "endLine": 174, + "endLine": 176, "endColumn": 13, "problem": "PropertyAccessByIndex", "suggest": "", @@ -405,9 +405,9 @@ "severity": "ERROR" }, { - "line": 181, + "line": 183, "column": 7, - "endLine": 181, + "endLine": 183, "endColumn": 14, "problem": "PropertyAccessByIndex", "suggest": "", @@ -415,9 +415,9 @@ "severity": "ERROR" }, { - "line": 192, + "line": 194, "column": 1, - "endLine": 192, + "endLine": 194, "endColumn": 5, "problem": "PropertyAccessByIndex", "suggest": "", @@ -425,9 +425,9 @@ "severity": "ERROR" }, { - "line": 193, + "line": 195, "column": 1, - "endLine": 193, + "endLine": 195, "endColumn": 7, "problem": "PropertyAccessByIndex", "suggest": "", @@ -435,9 +435,9 @@ "severity": "ERROR" }, { - "line": 196, + "line": 198, "column": 1, - "endLine": 196, + "endLine": 198, "endColumn": 23, "problem": "PropertyAccessByIndex", "suggest": "", @@ -445,9 +445,9 @@ "severity": "ERROR" }, { - "line": 208, + "line": 210, "column": 1, - "endLine": 208, + "endLine": 210, "endColumn": 20, "problem": "PropertyAccessByIndex", "suggest": "", @@ -455,4 +455,4 @@ "severity": "ERROR" } ] -} \ No newline at end of file +}