UNPKG

ui5plugin-parser

Version:
212 lines (211 loc) 9.43 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.CustomTSObject = void 0; const path = require("path"); const ts_morph_1 = require("ts-morph"); const ParserPool_1 = require("../../../../parser/pool/ParserPool"); const AbstractCustomClass_1 = require("../AbstractCustomClass"); class CustomTSObject extends AbstractCustomClass_1.AbstractCustomClass { _fillIsAbstract() { throw new Error("Method not implemented."); } _getUIDefine() { throw new Error("Method not implemented."); } // eslint-disable-next-line @typescript-eslint/no-empty-function _fillParentClassName() { } constructor(objectLiteralExpression, parser, typeChecker) { const sourceFile = objectLiteralExpression.getSourceFile(); const className = parser.fileReader.getClassNameFromPath(sourceFile.compilerNode.fileName); super(className ?? "", parser); this.parentClassNameDotNotation = ""; this.methods = []; this.fields = []; this.UIDefine = []; this.typeChecker = typeChecker; this.classText = sourceFile.getFullText(); this._sourceFile = sourceFile; this.fsPath = path.resolve(sourceFile.compilerNode.fileName); this.node = objectLiteralExpression; this._fillUI5Metadata(undefined, false); } loadTypes() { this._fillUI5Metadata(undefined, true); } _fillUIDefine() { const importStatements = this._sourceFile.getImportDeclarations(); this.UIDefine = importStatements.map(importStatement => { const modulePath = importStatement.getModuleSpecifier().getLiteralText(); return { path: modulePath, className: modulePath.split("/").pop() ?? "", classNameDotNotation: this._generateClassNameDotNotationFor(modulePath), start: importStatement.getStart(), end: importStatement.getEnd(), acornNode: importStatement }; }); } _generateClassNameDotNotationFor(moduleNameSlash) { let className = moduleNameSlash.replace(/\//g, "."); if (moduleNameSlash?.startsWith(".")) { const manifest = ParserPool_1.default.getManifestForClass(this.className); if (manifest && this.fsPath) { const normalizedManifestPath = path.normalize(manifest.fsPath); const importClassPath = path.resolve(path.dirname(this.fsPath), moduleNameSlash); const relativeToManifest = path.relative(normalizedManifestPath, importClassPath); const pathRelativeToManifestDotNotation = relativeToManifest.split(path.sep).join("."); className = `${manifest.componentName}.${pathRelativeToManifestDotNotation}`; } } if (className.endsWith(".controller")) { className = className.substring(0, className.length - ".controller".length); } return className; } _fillFields(metadata, fillTypes = false) { const properties = this.node.getProperties(); const propertyAssignments = properties .filter(field => field.isKind(ts_morph_1.ts.SyntaxKind.PropertyAssignment)) // eslint-disable-next-line @typescript-eslint/no-non-null-assertion .map(field => field.asKind(ts_morph_1.ts.SyntaxKind.PropertyAssignment)); const fields = propertyAssignments.filter(field => !field.getInitializer()?.isKind(ts_morph_1.ts.SyntaxKind.FunctionExpression) && !field.getInitializer()?.isKind(ts_morph_1.ts.SyntaxKind.ArrowFunction)); const UIFields = fields.map(field => { const positionStart = this._sourceFile.getLineAndColumnAtPos(field.getNameNode().getStart()); const positionEnd = this._sourceFile.getLineAndColumnAtPos(field.getNameNode().getEnd()); let type = fillTypes ? field.getType().getText() : "any"; type = this._modifyType(type); return { ui5ignored: false, owner: this.className, static: true, abstract: false, type: type, visibility: "public", name: field.getName(), deprecated: false, description: "", isEventHandler: false, node: field, mentionedInTheXMLDocument: false, loc: { start: { line: positionStart.line, column: positionStart.column - 1 }, end: { line: positionEnd.line, column: positionEnd.column - 1 } } }; }); return UIFields; } _fillMethods(metadata, fillTypes = false) { const properties = this.node.getProperties(); const propertyAssignments = properties .filter(field => field.isKind(ts_morph_1.ts.SyntaxKind.PropertyAssignment)) // eslint-disable-next-line @typescript-eslint/no-non-null-assertion .map(field => field.asKind(ts_morph_1.ts.SyntaxKind.PropertyAssignment)); const functions = propertyAssignments.filter(field => field.getInitializer()?.isKind(ts_morph_1.ts.SyntaxKind.FunctionExpression) || field.getInitializer()?.isKind(ts_morph_1.ts.SyntaxKind.ArrowFunction)); const methods = properties .filter(field => field.isKind(ts_morph_1.ts.SyntaxKind.MethodDeclaration)) // eslint-disable-next-line @typescript-eslint/no-non-null-assertion .map(field => field.asKind(ts_morph_1.ts.SyntaxKind.MethodDeclaration)); const UIMethods = [...methods, ...functions].map(method => { const positionStart = this._sourceFile.getLineAndColumnAtPos(method.getNameNode().getStart()); const positionEnd = this._sourceFile.getLineAndColumnAtPos(method.getNameNode().getEnd()); let returnType = "void"; let parameters = []; if (method.isKind(ts_morph_1.ts.SyntaxKind.MethodDeclaration)) { returnType = fillTypes ? method.getReturnType().getText() : "void"; parameters = method.getParameters(); } else if (method.isKind(ts_morph_1.ts.SyntaxKind.PropertyAssignment)) { const myFunction = method.getInitializer()?.asKind(ts_morph_1.ts.SyntaxKind.FunctionExpression) ?? method.getInitializer()?.asKind(ts_morph_1.ts.SyntaxKind.ArrowFunction); parameters = myFunction?.getParameters() ?? []; returnType = fillTypes ? myFunction?.getReturnType().getText() ?? "void" : "void"; } returnType = this._modifyType(returnType); return { ui5ignored: false, owner: this.className, static: true, abstract: false, returnType: returnType, visibility: "public", params: parameters.map(param => { return { name: param.getName(), type: fillTypes ? this._modifyType(param.getType().getText()) ?? "any" : "any", description: "", isOptional: false }; }), name: method.getName(), position: method.getStart(), deprecated: false, description: "", isEventHandler: false, node: method, loc: { start: { line: positionStart.line, column: positionStart.column - 1 }, end: { line: positionEnd.line, column: positionEnd.column - 1 } }, mentionedInTheXMLDocument: false }; }); return UIMethods; } _modifyType(returnType) { if (/import\(".*?"\).default/.test(returnType)) { const path = /(?<=import\(").*?(?="\).default)/.exec(returnType)?.[0]; const UI5Type = path?.startsWith("sap/") ? path.replace(/\//g, ".") : path ? this.parser.fileReader.getClassNameFromPath(path) : undefined; if (UI5Type) { returnType = UI5Type; } } if (/import\(".*?"\)\.[a-zA-Z|$]*/.test(returnType)) { const className = /(?<=import\(".*?"\)\.)[a-zA-Z|$]*/.exec(returnType)?.[0]; if (className) { returnType = className; } } return returnType; } _fillUI5Metadata(classInfo, fillTypes = false) { this._fillUIDefine(); this.methods = this._fillMethods(undefined, fillTypes); this.fields = this._fillFields(undefined, fillTypes); } _fillInterfaces() { return []; } _fillAggregations() { return []; } _fillEvents() { return []; } _fillProperties() { return []; } _fillAssociations() { return []; } } exports.CustomTSObject = CustomTSObject;