Skip to content

Commit 2c42e8c

Browse files
authored
fix(flow): Fix to Flow Maximum Callstack exceeded error on recursive generic structs (#428)
* implemented fix to flow recursive struct error * added test case for flow overflow issue with react class component
1 parent c73fbb9 commit 2c42e8c

File tree

6 files changed

+166
-0
lines changed

6 files changed

+166
-0
lines changed

src/__tests__/__snapshots__/main-test.js.snap

Lines changed: 112 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1465,3 +1465,115 @@ Object {
14651465
},
14661466
}
14671467
`;
1468+
1469+
exports[`main fixtures processes component "component_29.js" without errors 1`] = `
1470+
Object {
1471+
"description": "",
1472+
"displayName": "MyComponent",
1473+
"methods": Array [],
1474+
"props": Object {
1475+
"prop": Object {
1476+
"description": "",
1477+
"flowType": Object {
1478+
"name": "T",
1479+
},
1480+
"required": true,
1481+
},
1482+
},
1483+
}
1484+
`;
1485+
1486+
exports[`main fixtures processes component "component_30.js" without errors 1`] = `
1487+
Object {
1488+
"description": "",
1489+
"displayName": "MyComponent",
1490+
"methods": Array [],
1491+
"props": Object {
1492+
"prop": Object {
1493+
"description": "",
1494+
"flowType": Object {
1495+
"name": "string",
1496+
},
1497+
"required": true,
1498+
},
1499+
},
1500+
}
1501+
`;
1502+
1503+
exports[`main fixtures processes component "component_31.js" without errors 1`] = `
1504+
Object {
1505+
"description": "",
1506+
"displayName": "MyComponent",
1507+
"methods": Array [],
1508+
"props": Object {
1509+
"prop": Object {
1510+
"description": "",
1511+
"flowType": Object {
1512+
"name": "T",
1513+
},
1514+
"required": true,
1515+
},
1516+
},
1517+
}
1518+
`;
1519+
1520+
exports[`main fixtures processes component "component_32.js" without errors 1`] = `
1521+
Object {
1522+
"description": "",
1523+
"displayName": "Segments",
1524+
"methods": Array [
1525+
Object {
1526+
"docblock": null,
1527+
"modifiers": Array [],
1528+
"name": "foo",
1529+
"params": Array [
1530+
Object {
1531+
"name": "props",
1532+
"optional": undefined,
1533+
"type": Object {
1534+
"alias": "Props",
1535+
"name": "signature",
1536+
"raw": "{
1537+
segments: Array<T>,
1538+
}",
1539+
"signature": Object {
1540+
"properties": Array [
1541+
Object {
1542+
"key": "segments",
1543+
"value": Object {
1544+
"elements": Array [
1545+
Object {
1546+
"name": "T",
1547+
},
1548+
],
1549+
"name": "Array",
1550+
"raw": "Array<T>",
1551+
"required": true,
1552+
},
1553+
},
1554+
],
1555+
},
1556+
"type": "object",
1557+
},
1558+
},
1559+
],
1560+
"returns": null,
1561+
},
1562+
],
1563+
"props": Object {
1564+
"segments": Object {
1565+
"description": "",
1566+
"flowType": Object {
1567+
"elements": Array [
1568+
Object {
1569+
"name": "T",
1570+
},
1571+
],
1572+
"name": "Array",
1573+
"raw": "Array<T>",
1574+
},
1575+
"required": true,
1576+
},
1577+
},
1578+
}
1579+
`;
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
import React from "react";
2+
3+
type Identity<T> = T;
4+
5+
type Props<T> = {
6+
prop: Identity<T>,
7+
}
8+
9+
export default function MyComponent<T>(props: Props<T>) {
10+
return <div>Hello World</div>
11+
}
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
import React from "react";
2+
3+
type Identity<T> = T;
4+
5+
type Props = {
6+
prop: Identity<string>,
7+
}
8+
9+
export default function MyComponent(props: Props) {
10+
return <div>Hello World</div>
11+
}
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
import React from "react";
2+
3+
type Identity<T> = T;
4+
5+
type Props<T> = {
6+
prop: Identity<Identity<T>>,
7+
}
8+
9+
export default function MyComponent<T>(props: Props<T>) {
10+
return <div>Hello World</div>
11+
}
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
import * as React from "react";
2+
3+
type Props<T> = {
4+
segments: Array<T>,
5+
};
6+
7+
export default class Segments<T> extends React.Component<Props<T>> {
8+
render(): React.Node {
9+
return null;
10+
}
11+
12+
foo(props: Props<T>) {}
13+
}

src/utils/getFlowType.js

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -139,6 +139,14 @@ function handleGenericTypeAnnotation(
139139
);
140140
}
141141

142+
if (
143+
typeParams &&
144+
typeParams[type.name] &&
145+
typeParams[type.name].value.type === t.GenericTypeAnnotation.name
146+
) {
147+
return type;
148+
}
149+
142150
if (typeParams && typeParams[type.name]) {
143151
type = getFlowTypeWithResolvedTypes(resolvedPath, typeParams);
144152
}

0 commit comments

Comments
 (0)