diff --git a/packages/angular-demo/src/app/app.component.ts b/packages/angular-demo/src/app/app.component.ts
index 2644de9..1aa87cd 100644
--- a/packages/angular-demo/src/app/app.component.ts
+++ b/packages/angular-demo/src/app/app.component.ts
@@ -1,12 +1,14 @@
import { Component, Input } from '@angular/core';
+import { ChildComponent } from './child.component';
import { getLibraryAuthor } from './other-utils';
-import { getProductNumber, Product, UndocumentedSecret } from './types';
+import { RaceCar, getProductNumber, Product, UndocumentedSecret } from './types';
import { ENVIRONMENT, IS_STANDALONE, isNumber, isString, LIB_NAME, VERSION } from './utils';
@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.scss'],
+ imports: [ChildComponent],
})
export class AppComponent {
@Input() testInput = '';
@@ -26,6 +28,14 @@ export class AppComponent {
hiddenProperty: '',
};
+ raceCar: RaceCar = {
+ brand: 'Ferrari',
+ model: '812 Superfast',
+ maxSpeed: 320,
+ price: 1500000,
+ numberOfWheels: 4,
+ };
+
/**
* @exclude-docs
*/
diff --git a/packages/angular-demo/src/app/stories/interface.mdx b/packages/angular-demo/src/app/stories/interface.mdx
index 468abc2..eb91920 100644
--- a/packages/angular-demo/src/app/stories/interface.mdx
+++ b/packages/angular-demo/src/app/stories/interface.mdx
@@ -56,6 +56,10 @@ export interface Price {
+### RaceCar
+
+
+
## Without @include-docs
Interfaces without the `@include-docs` annotation are ignored.
diff --git a/packages/angular-demo/src/app/types.ts b/packages/angular-demo/src/app/types.ts
index c949318..129de0f 100644
--- a/packages/angular-demo/src/app/types.ts
+++ b/packages/angular-demo/src/app/types.ts
@@ -1,3 +1,5 @@
+import { PricedItem } from '@scope/entrypoint'; // eslint-disable-line @nx/enforce-module-boundaries
+
export interface UndocumentedSecret {
secret: string;
}
@@ -7,11 +9,6 @@ export interface UndocumentedSecret {
*/
export interface Product extends Item {
price: Price;
-
- /**
- * @exclude-docs
- */
- hiddenProperty?: unknown;
}
export interface Item {
@@ -76,3 +73,38 @@ export interface Price {
export function getProductNumber(product: Product) {
return `${product.id}X${product.itemNumber}`;
}
+
+/**
+ * @include-docs
+ */
+export interface RaceCar extends Car, Vehicle, PricedItem {
+ /**
+ * Maximum speed in km/h.
+ */
+ maxSpeed: number;
+}
+
+export interface Car {
+ /**
+ * Model name
+ *
+ * This is a property from an extended interface.
+ */
+ model: string;
+
+ /**
+ * Brand name
+ *
+ * This is a property from an extended interface.
+ */
+ brand: string;
+}
+
+export interface Vehicle {
+ /**
+ * Number of wheels
+ *
+ * This is a property from another extended interface.
+ */
+ numberOfWheels: number;
+}
diff --git a/packages/angular-demo/src/entrypoint/index.ts b/packages/angular-demo/src/entrypoint/index.ts
index 5cb4cba..4bb8458 100644
--- a/packages/angular-demo/src/entrypoint/index.ts
+++ b/packages/angular-demo/src/entrypoint/index.ts
@@ -1 +1,2 @@
export { GreatGrandParentDirective } from './great-grand-parent.directive';
+export { PricedItem } from './types';
diff --git a/packages/angular-demo/src/entrypoint/types.ts b/packages/angular-demo/src/entrypoint/types.ts
new file mode 100644
index 0000000..60fb08a
--- /dev/null
+++ b/packages/angular-demo/src/entrypoint/types.ts
@@ -0,0 +1,9 @@
+export interface PricedItem {
+ /**
+ * Price of the product
+ *
+ * This is a property from an extended interface imported from a
+ * secondary entry point.
+ */
+ price: number;
+}
diff --git a/packages/storybook-webpack-angular-types-plugin/src/lib/extract-args-types/extract-arg-types.ts b/packages/storybook-webpack-angular-types-plugin/src/lib/extract-args-types/extract-arg-types.ts
index 23e456b..a1bc3d1 100644
--- a/packages/storybook-webpack-angular-types-plugin/src/lib/extract-args-types/extract-arg-types.ts
+++ b/packages/storybook-webpack-angular-types-plugin/src/lib/extract-args-types/extract-arg-types.ts
@@ -1,5 +1,5 @@
import { STORYBOOK_ANGULAR_ARG_TYPES, STORYBOOK_COMPONENT_ID } from '../constants';
-import { EntitiesByCategory, Entity, JsDocParam } from '../types';
+import { Category, EntitiesByCategory, Entity, JsDocParam } from '../types';
import { Conditional } from 'storybook/internal/types';
/**
@@ -80,7 +80,13 @@ const mapEntityToArgsTableProp = (entity: Entity, category: string): ExtendedArg
const mapEntitiesToArgsTableProps = (entitiesByCategory: EntitiesByCategory): ExtendedArgType[] => {
const argsTableProps: ExtendedArgType[] = [];
- for (const [categoryKey, entities] of Object.entries(entitiesByCategory)) {
+ const categoriesToEntities = Object.entries(entitiesByCategory).sort((entry1, entry2) => {
+ const category1 = entry1[0] as Category;
+ const category2 = entry2[0] as Category;
+ return getCategoryPriority(category1) - getCategoryPriority(category2);
+ });
+
+ for (const [categoryKey, entities] of categoriesToEntities) {
const sortedEntities = entities.sort((a: Entity, b: Entity) =>
(a.alias ?? a.name).localeCompare(b.alias ?? b.name),
);
@@ -92,6 +98,25 @@ const mapEntitiesToArgsTableProps = (entitiesByCategory: EntitiesByCategory): Ex
return argsTableProps;
};
+function getCategoryPriority(category: Category) {
+ switch (category) {
+ case 'inputs':
+ return 0;
+ case 'outputs':
+ return 1;
+ case 'properties':
+ return 2;
+ case 'methods':
+ return 3;
+ case 'constants':
+ return 4;
+ case 'functions':
+ return 5;
+ default:
+ return 6;
+ }
+}
+
export const extractArgTypes = (type: Type): ArgType[] | undefined => {
const entities =
typeof type === 'string'
diff --git a/packages/storybook-webpack-angular-types-plugin/src/lib/types.ts b/packages/storybook-webpack-angular-types-plugin/src/lib/types.ts
index dd6f070..49304c0 100644
--- a/packages/storybook-webpack-angular-types-plugin/src/lib/types.ts
+++ b/packages/storybook-webpack-angular-types-plugin/src/lib/types.ts
@@ -20,7 +20,7 @@ export interface WebpackAngularTypesPluginOptions {
}
export type EntityModifier = 'getter' | 'setter';
-export type EntityKind = 'input' | 'output' | 'property' | 'method';
+export type EntityKind = 'input' | 'output' | 'property' | 'method' | 'constant' | 'function';
export interface JsDocParam {
name: string;
@@ -41,10 +41,17 @@ export interface Entity {
modifier?: EntityModifier;
}
-export const _Categories = ['inputs', 'outputs', 'properties', 'methods'] as const;
-export type Categories = (typeof _Categories)[number];
+export const _Categories = [
+ 'inputs',
+ 'outputs',
+ 'properties',
+ 'methods',
+ 'functions',
+ 'constants',
+] as const;
+export type Category = (typeof _Categories)[number];
export type EntitiesByCategory = {
- [category in Categories]: Entity[];
+ [category in Category]: Entity[];
};
export type ClassInformation = CommonClassLikeInformation;
diff --git a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/grouping/group-export-information.ts b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/grouping/group-export-information.ts
deleted file mode 100644
index 958817d..0000000
--- a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/grouping/group-export-information.ts
+++ /dev/null
@@ -1,102 +0,0 @@
-import {
- ConstantInformation,
- ExportsInformation,
- FunctionInformation,
- GroupedExportInformation,
-} from 'storybook-webpack-angular-types-plugin';
-
-/**
- * Functions and constants can be annotated with "@include-docs" to collect them into a
- * single ArgsTable. Returns information grouped by the "groupBy" property.
- *
- * @param functionsInformation list of all functions
- * @param constantsInformation list of all constants
- */
-export function groupExportInformation(
- functionsInformation: FunctionInformation[],
- constantsInformation: ConstantInformation[],
-): GroupedExportInformation[] {
- const exportsInformationMap = new Map();
-
- for (const functionInformation of functionsInformation) {
- addFunctionInformationToGroupedExports(exportsInformationMap, functionInformation);
- }
-
- for (const constantInformation of constantsInformation) {
- addConstantInformationToGroupedExports(exportsInformationMap, constantInformation);
- }
-
- const groupedExportsInformation: GroupedExportInformation[] = [];
- for (const [name, exportsInformation] of exportsInformationMap) {
- groupedExportsInformation.push({
- name,
- functionsInformation: exportsInformation.functionsInformation,
- constantsInformation: exportsInformation.constantsInformation,
- });
- }
- return groupedExportsInformation;
-}
-
-function addFunctionInformationToGroupedExports(
- exportsInformationMap: Map,
- functionInformation: FunctionInformation,
-) {
- addConstantLikeInformationToGroupedExports(
- exportsInformationMap,
- functionInformation,
- 'functionsInformation',
- );
-}
-
-function addConstantInformationToGroupedExports(
- exportsInformationMap: Map,
- functionInformation: ConstantInformation,
-) {
- addConstantLikeInformationToGroupedExports(
- exportsInformationMap,
- functionInformation,
- 'constantsInformation',
- );
-}
-
-function addConstantLikeInformationToGroupedExports(
- exportsInformationMap: Map,
- constantLikeInformation: FunctionInformation | ConstantInformation,
- entryKey: 'functionsInformation' | 'constantsInformation',
-) {
- const name = constantLikeInformation.name;
-
- exportsInformationMap.set(
- name,
- getNewExportsInformationMapEntry(constantLikeInformation, entryKey),
- );
-
- const groupBys = constantLikeInformation.groupBy;
-
- for (const groupBy of groupBys) {
- const groupByEntry = exportsInformationMap.get(groupBy);
- if (groupByEntry) {
- if (groupByEntry[entryKey].length) {
- groupByEntry[entryKey].push(constantLikeInformation);
- } else {
- groupByEntry[entryKey] = [constantLikeInformation];
- }
- } else {
- exportsInformationMap.set(
- groupBy,
- getNewExportsInformationMapEntry(constantLikeInformation, entryKey),
- );
- }
- }
-}
-
-function getNewExportsInformationMapEntry(
- constantLikeInformation: FunctionInformation | ConstantInformation,
- entryKey: 'functionsInformation' | 'constantsInformation',
-): ExportsInformation {
- return {
- functionsInformation: [],
- constantsInformation: [],
- [entryKey]: [constantLikeInformation],
- };
-}
diff --git a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/plugin.ts b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/plugin.ts
index 64e4e5e..1ab3599 100644
--- a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/plugin.ts
+++ b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/plugin.ts
@@ -8,6 +8,7 @@ import { DEFAULT_TS_CONFIG_PATH, PLUGIN_NAME } from '../constants';
import {
ClassInformation,
ConstantInformation,
+ ExportsInformation,
FunctionInformation,
GroupedExportInformation,
InterfaceInformation,
@@ -15,7 +16,6 @@ import {
WebpackAngularTypesPluginOptions,
} from '../types';
import { getGlobalUniqueId } from './class-id-registry';
-import { groupExportInformation } from './grouping/group-export-information';
import { CodeDocDependency, CodeDocDependencyTemplate } from './templating/code-doc-dependency';
import {
getClassArgCodeBlock,
@@ -66,9 +66,8 @@ export class WebpackAngularTypesPlugin {
.map((module) => this.getProcessableModule(module))
.filter((module): module is ModuleInformation => !!module);
- const collectedFunctionsInformation: FunctionInformation[] = [];
- const collectedConstantsInformation: ConstantInformation[] = [];
- const modulesWithFunctionsOrConstants: Module[] = [];
+ const modulePathToGroupBysMap = new Map();
+ const groupByToExportsInformationMap = new Map();
for (const { path } of modulesToProcess) {
smallTsProject.addSourceFileAtPath(path);
@@ -79,37 +78,125 @@ export class WebpackAngularTypesPlugin {
const {
classesInformation,
interfacesInformation,
- functionsInformation,
constantsInformation,
+ functionsInformation,
} = generateTypeInformation(
path,
smallTsProject,
this.options.excludeProperties,
);
+
for (const classInformation of classesInformation) {
this.addClassCodeDocDependency(classInformation, module);
}
for (const interfaceInformation of interfacesInformation) {
this.addInterfaceCodeDocDependency(interfaceInformation, module);
}
- if (functionsInformation.length || constantsInformation.length) {
- modulesWithFunctionsOrConstants.push(module);
+ for (const constantInformation of constantsInformation) {
+ this.addConstantCodeDocDependency(constantInformation, module);
+ }
+ for (const functionInformation of functionsInformation) {
+ this.addFunctionCodeDocDependency(functionInformation, module);
}
- collectedFunctionsInformation.push(...functionsInformation);
- collectedConstantsInformation.push(...constantsInformation);
- }
- for (const moduleWithFunctionsOrConstants of modulesWithFunctionsOrConstants) {
- const groupedExportsInformation = groupExportInformation(
- collectedFunctionsInformation,
- collectedConstantsInformation,
+ const constantsAndFunctionsInformation = functionsInformation.concat(
+ ...constantsInformation,
);
- for (const groupedExportInformation of groupedExportsInformation) {
- this.addGroupedExportsCodeDocDependency(
- groupedExportInformation,
- moduleWithFunctionsOrConstants,
- );
+ // If there are no constantsInformation and no functionsInformation in the current
+ // module, we don't have to do anything more for the current module.
+ if (!constantsAndFunctionsInformation.length) {
+ continue;
+ }
+
+ /*
+ Multiple constants and functions information from multiple source files
+ can be grouped into the same ArgTypes table via groupBy.
+
+ "groupBys" are aliases added via the @include-docs tags in the JSDoc,
+ e.g. "@include-docs Alias1, Alias2".
+ Information for all constants and functions annotated with "Alias1" will
+ appear in the same ArgTypes table, same for "Alias2".
+
+ For this to work, we need to add a CodeDocDependency with all exports
+ that contain a specific groupBy alias to all modules that also have an
+ export with the same groupBy alias.
+ */
+
+ // For that, we first collect all aliases that occur in the current module.
+ const groupBys = Array.from(
+ new Set(constantsAndFunctionsInformation.flatMap((info) => info.groupBy)),
+ );
+
+ // We store all groupBy aliases of the current module in a map we can
+ // access later when adding the CodeDocDependencies.
+ modulePathToGroupBysMap.set(path, groupBys);
+
+ for (const groupBy of groupBys) {
+ // If an entry for the current groupBy alias already exists,
+ // return the existing, otherwise create a new empty
+ // ExportsInformation object.
+ let currentExportsInformation = groupByToExportsInformationMap.get(
+ groupBy,
+ ) || {
+ constantsInformation: [],
+ functionsInformation: [],
+ };
+
+ for (const constantInformation of constantsInformation) {
+ if (constantInformation.groupBy.includes(groupBy)) {
+ // Add the current constantInformation and avoid multiple entries with
+ // the same name.
+ currentExportsInformation = {
+ ...currentExportsInformation,
+ constantsInformation:
+ currentExportsInformation.constantsInformation
+ .filter((ci) => ci.name !== ci.name)
+ .concat(constantInformation),
+ };
+ }
+ }
+
+ for (const functionInformation of functionsInformation) {
+ if (functionInformation.groupBy.includes(groupBy)) {
+ // Add the current functionInformation and avoid multiple entries with
+ // the same name.
+ currentExportsInformation = {
+ ...currentExportsInformation,
+ functionsInformation:
+ currentExportsInformation.functionsInformation
+ .filter((fi) => fi.name !== functionInformation.name)
+ .concat(functionInformation),
+ };
+ }
+ }
+
+ // After adding all new constantsInformation and functionsInformation,
+ // update the ExportsInformation map entry.
+ groupByToExportsInformationMap.set(groupBy, currentExportsInformation);
+ }
+ }
+
+ // Now, iterate over all modules a second time and add CodeDocDependencies
+ // for the grouped exports.
+ for (const { module, path } of modulesToProcess) {
+ const groupBys = modulePathToGroupBysMap.get(path) || [];
+ // Nothing to do if there are no groupBy aliases in the current module
+ if (!groupBys.length) {
+ continue;
+ }
+
+ for (const groupBy of groupBys) {
+ const exportsInformation = groupByToExportsInformationMap.get(groupBy);
+ if (!exportsInformation) {
+ continue;
+ }
+ const groupedExportInformation: GroupedExportInformation = {
+ name: groupBy,
+ constantsInformation: exportsInformation.constantsInformation,
+ functionsInformation: exportsInformation.functionsInformation,
+ };
+ this.addGroupedExportsCodeDocDependency(groupedExportInformation, module);
}
}
@@ -147,6 +234,36 @@ export class WebpackAngularTypesPlugin {
}
}
+ // noinspection JSMethodCanBeStatic
+ private addFunctionCodeDocDependency(
+ functionInformation: FunctionInformation,
+ module: Module,
+ ): void {
+ const name = functionInformation.name;
+ const uniqueId = getGlobalUniqueId(module.identifier(), name);
+ const codeDocDependency = new CodeDocDependency(
+ name,
+ uniqueId,
+ getNonClassArgCodeBlock(name, { functions: [functionInformation.entity] }),
+ );
+ module.addDependency(codeDocDependency);
+ }
+
+ // noinspection JSMethodCanBeStatic
+ private addConstantCodeDocDependency(
+ constantInformation: ConstantInformation,
+ module: Module,
+ ): void {
+ const name = constantInformation.name;
+ const uniqueId = getGlobalUniqueId(module.identifier(), name);
+ const codeDocDependency = new CodeDocDependency(
+ name,
+ uniqueId,
+ getNonClassArgCodeBlock(name, { constants: [constantInformation.entity] }),
+ );
+ module.addDependency(codeDocDependency);
+ }
+
// noinspection JSMethodCanBeStatic
private addGroupedExportsCodeDocDependency(
groupedExportInformation: GroupedExportInformation,
@@ -157,8 +274,8 @@ export class WebpackAngularTypesPlugin {
groupedExportInformation.name,
uniqueId,
getNonClassArgCodeBlock(groupedExportInformation.name, {
- functions: groupedExportInformation.functionsInformation.map((f) => f.entity),
constants: groupedExportInformation.constantsInformation.map((c) => c.entity),
+ functions: groupedExportInformation.functionsInformation.map((f) => f.entity),
}),
);
module.addDependency(codeDocDependency);
diff --git a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/templating/arg-code-block-templates.ts b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/templating/arg-code-block-templates.ts
index 57e229a..acd31aa 100644
--- a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/templating/arg-code-block-templates.ts
+++ b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/templating/arg-code-block-templates.ts
@@ -1,3 +1,4 @@
+import { EntitiesByCategory } from '../../types';
import { STORYBOOK_ANGULAR_ARG_TYPES } from '../../constants';
import { classWithIdString } from '../utils';
@@ -5,7 +6,11 @@ const windowVariableInitializer = `if (!window["${STORYBOOK_ANGULAR_ARG_TYPES}"]
window["${STORYBOOK_ANGULAR_ARG_TYPES}"] = {};
}`;
-export function getClassArgCodeBlock(className: string, id: number, types: object) {
+export function getClassArgCodeBlock(
+ className: string,
+ id: number,
+ types: Partial,
+) {
return `${windowVariableInitializer}
window["${STORYBOOK_ANGULAR_ARG_TYPES}"]["${classWithIdString(
className,
@@ -13,7 +18,7 @@ window["${STORYBOOK_ANGULAR_ARG_TYPES}"]["${classWithIdString(
)}"] = ${JSON.stringify(types)};`;
}
-export function getNonClassArgCodeBlock(name: string, types: object) {
+export function getNonClassArgCodeBlock(name: string, types: Partial) {
return `${windowVariableInitializer}
window["${STORYBOOK_ANGULAR_ARG_TYPES}"]["${name}"] = ${JSON.stringify(types)};`;
}
diff --git a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/ts-morph-helpers.ts b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/ts-morph-helpers.ts
index 3ca5ce3..1969351 100644
--- a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/ts-morph-helpers.ts
+++ b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/ts-morph-helpers.ts
@@ -134,6 +134,8 @@ export function parseModuleResolution(
return ModuleResolutionKind.NodeJs;
case 'node16':
return ModuleResolutionKind.Node16;
+ case 'node10':
+ return ModuleResolutionKind.Node10;
case 'nodenext':
return ModuleResolutionKind.NodeNext;
case 'bundler':
diff --git a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/class-type-extraction.ts b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/class-type-extraction.ts
index e9a3ed0..d88b30d 100644
--- a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/class-type-extraction.ts
+++ b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/class-type-extraction.ts
@@ -11,7 +11,7 @@ import { isNativeAngularMethod } from './angular-utils';
import { collectBaseClasses, hasJsDocsTag } from './ast-utils';
import { mapDeclarationToEntities } from './declaration-mappers';
import { addGenericTypeMappings } from './type-details';
-import { getterOrSetterInputExists, mergeEntities } from './utils';
+import { getCategoryFromEntityKind, getterOrSetterInputExists, mergeEntities } from './utils';
/**
* Creates mappings from generic class arguments of a subClass to the generic
@@ -134,9 +134,8 @@ export function generateClassTypeInformation(
return {
name,
modulePath: filePath,
- entitiesByCategory: groupBy(
- mergedClassEntities,
- (entity) => entity.kind,
+ entitiesByCategory: groupBy(mergedClassEntities, (entity) =>
+ getCategoryFromEntityKind(entity.kind),
) as EntitiesByCategory,
};
}
diff --git a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/declaration-mappers.ts b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/declaration-mappers.ts
index 0a27879..4880f47 100644
--- a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/declaration-mappers.ts
+++ b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/declaration-mappers.ts
@@ -220,7 +220,7 @@ export function mapMethodDeclaration({
export function mapFunctionDeclaration(functionDeclaration: FunctionDeclaration): Entity {
return {
- kind: 'method',
+ kind: 'function',
alias: undefined,
name: functionDeclaration.getName() || '',
defaultValue: getJsDocsDefaultValue(functionDeclaration),
@@ -235,7 +235,7 @@ export function mapFunctionDeclaration(functionDeclaration: FunctionDeclaration)
export function mapVariableDeclaration(variableStatement: VariableStatement): Entity {
return {
- kind: 'property',
+ kind: 'constant',
alias: undefined,
name: getVariableName(variableStatement),
defaultValue:
diff --git a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/interface-type-extraction.ts b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/interface-type-extraction.ts
index c1b54c0..fd4f95a 100644
--- a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/interface-type-extraction.ts
+++ b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/interface-type-extraction.ts
@@ -3,7 +3,7 @@ import { InterfaceDeclaration } from 'ts-morph';
import { EXCLUDE_DOCS_JS_DOCS_PARAM, groupBy } from '../utils';
import { collectBaseInterfaces, getJsDocsIncludeDocsAliases, hasJsDocsTag } from './ast-utils';
import { mapSignatureToEntity } from './signature-mappers';
-import { getterOrSetterInputExists, mergeEntities } from './utils';
+import { getCategoryFromEntityKind, getterOrSetterInputExists, mergeEntities } from './utils';
/**
* Collects all interface entities (property and method signatures) of a interfaceDeclaration
@@ -85,9 +85,8 @@ export function generateInterfaceTypeInformation(
name,
aliases,
modulePath: filePath,
- entitiesByCategory: groupBy(
- mergedInterfaceEntities,
- (entity) => entity.kind,
+ entitiesByCategory: groupBy(mergedInterfaceEntities, (entity) =>
+ getCategoryFromEntityKind(entity.kind),
) as EntitiesByCategory,
};
}
diff --git a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/utils.ts b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/utils.ts
index f14c6d1..3af8316 100644
--- a/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/utils.ts
+++ b/packages/storybook-webpack-angular-types-plugin/src/lib/webpack-angular-types-plugin/type-extraction/utils.ts
@@ -1,5 +1,5 @@
import { PropertyDeclaration, Type } from 'ts-morph';
-import { Entity } from '../../types';
+import { Category, Entity, EntityKind } from '../../types';
/**
* Checks whether a getter/setter input is already present in the given map
@@ -81,3 +81,22 @@ export function getTypeArgument(type: Type, index: number): Type | undefined {
return typeArguments[index];
}
+
+export function getCategoryFromEntityKind(entityKind: EntityKind): Category {
+ switch (entityKind) {
+ case 'input':
+ return 'inputs';
+ case 'output':
+ return 'outputs';
+ case 'property':
+ return 'properties';
+ case 'method':
+ return 'methods';
+ case 'constant':
+ return 'constants';
+ case 'function':
+ return 'functions';
+ default:
+ return entityKind;
+ }
+}