Browse Source

feat: collect refs to generic types in service schematics

pull/5137/head
Arman Ozak 6 years ago
parent
commit
c6a4a3a62d
  1. 3
      npm/ng-packs/packages/schematics/src/models/import.ts
  2. 76
      npm/ng-packs/packages/schematics/src/utils/service.ts

3
npm/ng-packs/packages/schematics/src/models/import.ts

@ -5,6 +5,7 @@ export class Import {
alias?: string; alias?: string;
keyword = eImportKeyword.Default; keyword = eImportKeyword.Default;
path: string; path: string;
refs: string[] = [];
specifiers: string[] = []; specifiers: string[] = [];
constructor(options: ImportOptions) { constructor(options: ImportOptions) {
@ -12,4 +13,4 @@ export class Import {
} }
} }
export type ImportOptions = Omissible<Import, 'keyword' | 'specifiers'>; export type ImportOptions = Omissible<Import, 'keyword' | 'refs' | 'specifiers'>;

76
npm/ng-packs/packages/schematics/src/utils/service.ts

@ -1,17 +1,8 @@
import { eImportKeyword } from '../enums'; import { eImportKeyword } from '../enums';
import { import { Action, Body, Controller, Import, Method, Parameter, Service, Signature } from '../models';
Action,
Body,
Controller,
Import,
Method,
Parameter,
Service,
Signature,
TypeDef,
} from '../models';
import { parseNamespace } from './namespace'; import { parseNamespace } from './namespace';
import { relativePathFromServiceToModel } from './path'; import { relativePathFromServiceToModel } from './path';
import { parseGenerics } from './tree';
export function serializeParameters(parameters: Parameter[]) { export function serializeParameters(parameters: Parameter[]) {
return parameters.map(p => p.name + p.optional + ': ' + p.type + p.default, '').join(', '); return parameters.map(p => p.name + p.optional + ': ' + p.type + p.default, '').join(', ');
@ -31,13 +22,13 @@ export function createControllerToServiceMapper(solution: string, apiName: strin
} }
export function createActionToImportsReducer(solution: string, namespace: string) { export function createActionToImportsReducer(solution: string, namespace: string) {
const mapTypeDefToImport = createTypeDefToImportMapper(solution, namespace); const mapTypeToImport = createTypeToImportMapper(solution, namespace);
return (imports: Import[], action: Action) => { return (imports: Import[], action: Action) => {
const typeDefs = getTypeDefsFromAction(action); const types = getTypesFromAction(action);
typeDefs.forEach(typeDef => { types.forEach(type => {
const def = mapTypeDefToImport(typeDef); const def = mapTypeToImport(type);
if (!def) return; if (!def) return;
const existingImport = imports.find( const existingImport = imports.find(
@ -45,6 +36,7 @@ export function createActionToImportsReducer(solution: string, namespace: string
); );
if (!existingImport) return imports.push(def); if (!existingImport) return imports.push(def);
existingImport.refs = [...new Set([...existingImport.refs, ...def.refs])];
existingImport.specifiers = [ existingImport.specifiers = [
...new Set([...existingImport.specifiers, ...def.specifiers]), ...new Set([...existingImport.specifiers, ...def.specifiers]),
].sort(); ].sort();
@ -53,17 +45,20 @@ export function createActionToImportsReducer(solution: string, namespace: string
}; };
} }
export function createTypeDefToImportMapper(solution: string, namespace: string) { export function createTypeToImportMapper(solution: string, namespace: string) {
const adaptType = createTypeAdapter(solution); const adaptType = createTypeAdapter(solution);
return ({ type, typeSimple }: TypeDef) => { return (type: string) => {
if (type.startsWith('System')) return; if (type.startsWith('System')) return;
const modelNamespace = parseNamespace(solution, type); const modelNamespace = parseNamespace(solution, type);
const path = type.startsWith('Volo.Abp.Application.Dtos') const path = type.startsWith('Volo.Abp.Application.Dtos')
? '@abp/ng.core' ? '@abp/ng.core'
: relativePathFromServiceToModel(namespace, modelNamespace); : relativePathFromServiceToModel(namespace, modelNamespace);
const specifiers = [adaptType(typeSimple.split('<')[0])]; const refs = [type];
return new Import({ keyword: eImportKeyword.Type, path, specifiers }); const specifiers = [adaptType(type.split('<')[0])];
return new Import({ keyword: eImportKeyword.Type, path, refs, specifiers });
}; };
} }
@ -114,36 +109,35 @@ function getMethodNameFromAction(action: Action): string {
} }
function createTypeAdapter(solution: string) { function createTypeAdapter(solution: string) {
const optionalRegex = /\?/g; const removeNamespace = createNamespaceRemover(solution);
const solutionRegex = new RegExp(solution.replace(/\./g, `\.`) + `\.`);
const voloRegex = /^Volo\.(Abp\.?)(Application\.?)/;
return (typeSimple: string) => { return (typeSimple: string) => {
if (typeSimple === 'System.Void') return 'void'; if (typeSimple === 'System.Void') return 'void';
return parseGenerics(typeSimple).reduceRight((acc, type) => { return parseGenerics(typeSimple, node => removeNamespace(node.data)).toString();
type = type.replace(voloRegex, '');
type = type.replace(solutionRegex, '');
type = type.replace(optionalRegex, '');
type = type.split('.').pop()!;
return acc ? `${type}<${acc}>` : type;
}, '');
}; };
} }
function parseGenerics(type: string) { function createNamespaceRemover(solution: string) {
return type.replace(/>+$/, '').split('<'); const optionalRegex = /\?/g;
} const solutionRegex = new RegExp(solution.replace(/\./g, `\.`) + `\.`);
const voloRegex = /^Volo\.(Abp\.?)(Application\.?)/;
function getTypeDefsFromAction({ parametersOnMethod, returnValue }: Action) {
const typeDefs: TypeDef[] = [];
[returnValue, ...parametersOnMethod].forEach(({ type, typeSimple }) => { return (type: string) => {
const types = parseGenerics(type); type = type.replace(voloRegex, '');
const simpleTypes = parseGenerics(typeSimple); type = type.replace(solutionRegex, '');
type = type.replace(optionalRegex, '');
type = type.split('.').pop()!;
return type;
};
}
types.forEach((type, i) => typeDefs.push({ type, typeSimple: simpleTypes[i] })); function getTypesFromAction({ parametersOnMethod, returnValue }: Action) {
}); return [returnValue, ...parametersOnMethod].reduce((types: string[], { type }) => {
parseGenerics(type)
.toGenerics()
.forEach(t => types.push(t));
return typeDefs; return types;
}, []);
} }

Loading…
Cancel
Save