Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "react-docgen-typescript",
"version": "0.0.9",
"version": "0.0.10",
"description": "",
"main": "lib/index.js",
"scripts": {
Expand All @@ -21,7 +21,7 @@
"devDependencies": {
"@types/chai": "^3.4.35",
"@types/mocha": "^2.2.39",
"@types/node": "^7.0.5",
"@types/node": "^7.0.16",
"@types/react": "^15.0.14",
"@types/react-dom": "^0.14.23",
"babel-core": "^6.8.0",
Expand Down
16 changes: 10 additions & 6 deletions src/__tests__/data/ColumnHigherOrderComponent.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import * as React from 'react';
import { externalHoc } from "./ColumnHigherOrderComponentHoc";
/**
* Column properties.
*/
Expand Down Expand Up @@ -62,13 +63,16 @@ function hoc<T>(C: T): T {
return ((props) => <div>{C}</div>) as any as T;
}

/** ColumnHighOrderComponent1 specific comment */
export const ColumnHighOrderComponent1 = hoc(Column);
/** ColumnHigherOrderComponent1 specific comment */
export const ColumnHigherOrderComponent1 = hoc(Column);

export const ColumnHighOrderComponent2 = hoc(Column);
export const ColumnHigherOrderComponent2 = hoc(Column);

/** RowHighOrderComponent1 specific comment */
export const RowHighOrderComponent1 = hoc(Row);
/** RowHigherOrderComponent1 specific comment */
export const RowHigherOrderComponent1 = hoc(Row);

export const RowHighOrderComponent2 = hoc(Row);
export const RowHigherOrderComponent2 = hoc(Row);

export const ColumnExternalHigherOrderComponent = externalHoc(Column);
export const RowExternalHigherOrderComponent = externalHoc(Row);

5 changes: 5 additions & 0 deletions src/__tests__/data/ColumnHigherOrderComponentHoc.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
import * as React from 'react';

export function externalHoc<T>(C: T): T {
return ((props) => <div>{C}</div>) as any as T;
}
16 changes: 14 additions & 2 deletions src/__tests__/data/transformAST.tsx
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
import { externalHoc } from './transformAST_hoc';

const unexportedVar = 10;
export const exportedVar = 10;

Expand Down Expand Up @@ -51,5 +53,15 @@ export function hoc<T>(component: T): T {
return component;
}

/** exportedHoc comment */
export const exportedHoc = hoc(ExportedClass);
/** exportedHoc1 comment */
export const exportedHoc1 = hoc(ExportedClass);

/** exportedHoc2 comment */
export const exportedHoc2 = hoc(exportedFunction);


/** exportedExternalHoc1 comment */
export const exportedExternalHoc1 = externalHoc(ExportedClass);

/** exportedExternalHoc2 comment */
export const exportedExternalHoc2 = externalHoc(exportedFunction);
3 changes: 3 additions & 0 deletions src/__tests__/data/transformAST_hoc.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export function externalHoc<T>(component: T): T {
return component;
}
75 changes: 54 additions & 21 deletions src/__tests__/getFileDocumentation.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -173,39 +173,72 @@ describe('getFileDocumentation', () => {
const fileName = path.join(__dirname, '../../src/__tests__/data/ColumnHigherOrderComponent.tsx'); // it's running in ./temp
const result = getFileDocumentation(fileName);
assert.ok(result.components);
assert.equal(4, result.components.length);
assert.equal(6, result.components.length);

const r1 = result.components[0];
assert.equal('ColumnHighOrderComponent1', r1.name);
assert.equal('ColumnHighOrderComponent1 specific comment', r1.comment);
assert.equal('ColumnHigherOrderComponent1', r1.name);
assert.equal('ColumnHigherOrderComponent1 specific comment', r1.comment);
assert.equal('Column', r1.extends);
assert.isNotNull(r1.propInterface);

const i = r1.propInterface;
assert.equal('IColumnProps', i.name);
assert.equal('Column properties.', i.comment);
assert.equal(4, i.members.length);
assert.equal('prop1', i.members[0].name);
assert.equal('prop1 description', i.members[0].comment);
assert.equal(false, i.members[0].isRequired);
const p1 = r1.propInterface;
assert.equal('IColumnProps', p1.name);
assert.equal('Column properties.', p1.comment);
assert.equal(4, p1.members.length);
assert.equal('prop1', p1.members[0].name);
assert.equal('prop1 description', p1.members[0].comment);
assert.equal(false, p1.members[0].isRequired);

assert.equal('prop2', i.members[1].name);
assert.equal('prop2 description', i.members[1].comment);
assert.equal(true, i.members[1].isRequired);
assert.equal('prop2', p1.members[1].name);
assert.equal('prop2 description', p1.members[1].comment);
assert.equal(true, p1.members[1].isRequired);

assert.equal('prop3', i.members[2].name);
assert.equal('prop3 description', i.members[2].comment);
assert.equal(true, i.members[2].isRequired);
assert.equal('prop3', p1.members[2].name);
assert.equal('prop3 description', p1.members[2].comment);
assert.equal(true, p1.members[2].isRequired);

assert.equal('prop4', i.members[3].name);
assert.equal('prop4 description', i.members[3].comment);
assert.equal(true, i.members[3].isRequired);
assert.equal('prop4', p1.members[3].name);
assert.equal('prop4 description', p1.members[3].comment);
assert.equal(true, p1.members[3].isRequired);

const r2 = result.components[1];
assert.equal('ColumnHighOrderComponent2', r2.name);
assert.equal('ColumnHigherOrderComponent2', r2.name);
assert.equal('Form column.', r2.comment);
assert.equal('Column', r2.extends);
assert.isNotNull(r2.propInterface);

const p2 = r2.propInterface;
assert.equal('IColumnProps', p2.name);

const r3 = result.components[2];
assert.equal('ColumnExternalHigherOrderComponent', r3.name);
assert.equal('Form column.', r3.comment);
assert.equal('Column', r3.extends);
assert.isNotNull(r3.propInterface);
const p3 = r3.propInterface;
assert.equal('IColumnProps', p3.name);

const r4 = result.components[3];
assert.equal('RowHigherOrderComponent1', r4.name);
assert.equal('RowHigherOrderComponent1 specific comment', r4.comment);
assert.equal('Row', r4.extends);
assert.isNotNull(r4.propInterface);
const p4 = r4.propInterface;
assert.equal('IRowProps', p4.name);

const r5 = result.components[4];
assert.equal('RowHigherOrderComponent2', r5.name);
assert.equal('Form row.', r5.comment);
assert.equal('Row', r5.extends);
assert.isNotNull(r5.propInterface);
const p5 = r5.propInterface;
assert.equal('IRowProps', p5.name);

const r6 = result.components[5];
assert.equal('RowExternalHigherOrderComponent', r6.name);
assert.equal('Form row.', r6.comment);
assert.equal('Row', r6.extends);
assert.isNotNull(r6.propInterface);
const p6 = r6.propInterface;
assert.equal('IRowProps', p6.name);
});
});
35 changes: 31 additions & 4 deletions src/__tests__/transformAST.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ describe('transformAST', () => {

it('should provide data about variables', () => {
const result = target.variables;
assert.equal(result.length, 5);
assert.equal(result.length, 8);

const r1 = result[0];
assert.equal(r1.name, 'unexportedVar');
Expand Down Expand Up @@ -48,14 +48,41 @@ describe('transformAST', () => {
assert.equal(r4.arrowFunctionType, 'string');
assert.deepEqual(r4.arrowFunctionParams, ['number', 'string']);

// hoc
// hoc class
const r5 = result[4];
assert.equal(r5.name, 'exportedHoc');
assert.equal(r5.name, 'exportedHoc1');
assert.equal(r5.exported, true);
assert.equal(r5.type, 'ExportedClass');
assert.equal(r5.kind, 'callExpression');
assert.equal(r5.comment, 'exportedHoc comment');
assert.equal(r5.comment, 'exportedHoc1 comment');
assert.deepEqual(r5.callExpressionArguments, ['ExportedClass']);

// hoc function
const r6 = result[5];
assert.equal(r6.name, 'exportedHoc2');
assert.equal(r6.exported, true);
assert.equal(r6.type, 'exportedFunction');
assert.equal(r6.kind, 'callExpression');
assert.equal(r6.comment, 'exportedHoc2 comment');
assert.deepEqual(r6.callExpressionArguments, ['exportedFunction']);

// external hoc class
const r7 = result[6];
assert.equal(r7.name, 'exportedExternalHoc1');
assert.equal(r7.exported, true);
assert.equal(r7.type, 'ExportedClass');
assert.equal(r7.kind, 'callExpression');
assert.equal(r7.comment, 'exportedExternalHoc1 comment');
assert.deepEqual(r7.callExpressionArguments, ['ExportedClass']);

// external hoc function
const r8 = result[7];
assert.equal(r8.name, 'exportedExternalHoc2');
assert.equal(r8.exported, true);
assert.equal(r8.type, 'exportedFunction');
assert.equal(r8.kind, 'callExpression');
assert.equal(r8.comment, 'exportedExternalHoc2 comment');
assert.deepEqual(r8.callExpressionArguments, ['exportedFunction']);
});

it('should provide data about interfaces', () => {
Expand Down
20 changes: 11 additions & 9 deletions src/getFileDocumentation.ts
Original file line number Diff line number Diff line change
Expand Up @@ -37,26 +37,28 @@ function isVarComponent(
function isHocClassComponent(entry: VariableEntry, classes: ClassEntry[]): boolean {
return entry.exported
&& entry.kind === 'callExpression'
&& entry.type !== null
// quick fix for external hoc - && entry.type !== null
&& entry.callExpressionArguments.length === 1
&& classes
.filter(i => isClassComponent(i, false))
.some(i => i.name === entry.type);
.some(i => i.name === entry.callExpressionArguments[0]);
}

function isVarClassComponent(
function isHocVarComponent(
entry: VariableEntry,
variables: VariableEntry[],
interfaces: InterfaceEntry[]): boolean {

return entry.exported
&& entry.kind === 'callExpression'
&& entry.type === '__function'
// quick fix for external hoc - && entry.type === '__function'
&& entry.callExpressionArguments.length === 1
&& variables
.filter(i => isVarComponent(i, interfaces, false))
.some(i => i.name === entry.callExpressionArguments[0]);
}


function getInterfaceDoc(entry: InterfaceEntry): InterfaceDoc {
return {
name: entry.name,
Expand Down Expand Up @@ -90,7 +92,7 @@ function getPropInterface(interfaces: InterfaceEntry[], propInterfaceName: strin
}
/** Generate documention for all classes in a set of .ts files */
export function getFileDocumentation(fileName: string, options: ts.CompilerOptions = defaultOptions): FileDoc {
const components: ComponentDoc[] = [];
const components: ComponentDoc[] = [];
let program = ts.createProgram([fileName], options);
let checker = program.getTypeChecker();
const model = transformAST(program.getSourceFile(fileName), checker);
Expand Down Expand Up @@ -119,24 +121,24 @@ export function getFileDocumentation(fileName: string, options: ts.CompilerOptio
.filter(i => isHocClassComponent(i, classes))
.map(i => ({
variable: i,
origin: classes.filter(c => c.name === i.type)[0]
origin: classes.filter(c => c.name === i.callExpressionArguments[0])[0]
}))
.map(i => ({
name: i.variable.name,
extends: i.variable.type,
extends: i.variable.callExpressionArguments[0],
comment: i.variable.comment || i.origin.comment,
propInterface: getClassPropInterface(interfaces, i.origin),
}));

const hocVarComponents = variables
.filter(i => isVarClassComponent(i, variables, interfaces))
.filter(i => isHocVarComponent(i, variables, interfaces))
.map(i => ({
variable: i,
origin: variables.filter(c => c.name === i.callExpressionArguments[0])[0]
}))
.map(i => ({
name: i.variable.name,
extends: i.variable.type,
extends: i.variable.callExpressionArguments[0],
comment: i.variable.comment || i.origin.comment,
propInterface: getVarPropInterface(interfaces, i.origin),
}));
Expand Down
4 changes: 2 additions & 2 deletions src/transformAST.ts
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,7 @@ function findAllNodes(rootNode: ts.Node, result: ts.Node[]) {
* Transform source file AST (abstract syntax tree) to our
* model (classes, interfaces, variables, methods).
*/
export function transformAST(sourceFile: ts.SourceFile, checker: ts.TypeChecker) {
export function transformAST(sourceFile: ts.SourceFile, checker: ts.TypeChecker) {
const nodes = [];
findAllNodes(sourceFile, nodes);

Expand Down Expand Up @@ -116,7 +116,7 @@ export function transformAST(sourceFile: ts.SourceFile, checker: ts.TypeChecker)
callExpressionArguments = callExpresson.arguments.map(i => i.getText());
}
}

return {
name: identifier.text,
exported: isNodeExported(i),
Expand Down
14 changes: 3 additions & 11 deletions yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
version "2.2.41"
resolved "https://registry.yarnpkg.com/@types/mocha/-/mocha-2.2.41.tgz#e27cf0817153eb9f2713b2d3f6c68f1e1c3ca608"

"@types/node@^7.0.5":
"@types/node@^7.0.16":
version "7.0.16"
resolved "https://registry.yarnpkg.com/@types/node/-/node-7.0.16.tgz#e3440e3ce4d4931616ac418cc4dc16cd94b80092"

Expand Down Expand Up @@ -1592,14 +1592,10 @@ escape-html@~1.0.3:
version "1.0.3"
resolved "https://registry.yarnpkg.com/escape-html/-/escape-html-1.0.3.tgz#0258eae4d3d0c0974de1c169188ef0051d1d1988"

escape-string-regexp@1.0.2:
escape-string-regexp@1.0.2, escape-string-regexp@^1.0.2:
version "1.0.2"
resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.2.tgz#4dbc2fe674e71949caf3fb2695ce7f2dc1d9a8d1"

escape-string-regexp@^1.0.2:
version "1.0.5"
resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4"

esprima-fb@~15001.1001.0-dev-harmony-fb:
version "15001.1001.0-dev-harmony-fb"
resolved "https://registry.yarnpkg.com/esprima-fb/-/esprima-fb-15001.1001.0-dev-harmony-fb.tgz#43beb57ec26e8cf237d3dd8b33e42533577f2659"
Expand Down Expand Up @@ -3298,11 +3294,7 @@ randomatic@^1.1.3:
is-number "^2.0.2"
kind-of "^3.0.2"

range-parser@^1.0.3:
version "1.2.0"
resolved "https://registry.yarnpkg.com/range-parser/-/range-parser-1.2.0.tgz#f49be6b487894ddc40dcc94a322f611092e00d5e"

range-parser@~1.0.3:
range-parser@^1.0.3, range-parser@~1.0.3:
version "1.0.3"
resolved "https://registry.yarnpkg.com/range-parser/-/range-parser-1.0.3.tgz#6872823535c692e2c2a0103826afd82c2e0ff175"

Expand Down