Skip to content
This repository was archived by the owner on Sep 21, 2019. It is now read-only.

Use question mark token for optional props #8

Merged
merged 2 commits into from
Jul 16, 2017
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
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ class MyComponent extends React.Component {
```tsx
type MyComponentProps = {
prop1: string;
prop2: number | undefined;
prop2?: number;
}

type MyComponentState = {
Expand Down
32 changes: 18 additions & 14 deletions src/transforms/react-js-make-props-and-state-transform.ts
Original file line number Diff line number Diff line change
Expand Up @@ -222,16 +222,23 @@ export function reactJSMakePropsAndStateInterfaceTransformFactoryFactory(typeChe
console.warn('Bad value for propType', name, 'at', propertyAssignment.getStart());
return result;
}
const typeValue = getTypeFromReactPropTypeExpression(propertyAssignment.initializer);

// Ignore children, React types have it
if (propertyAssignment.name.getText() === 'children') {
return result;
}

// Ignore children, React types have it
if (propertyAssignment.name.getText() === 'children') {
return result;
}

const typeValue = getTypeFromReactPropTypeExpression(propertyAssignment.initializer);
const isOptional = isPropTypeOptional(propertyAssignment.initializer);
const propertySignature = ts.createPropertySignature(
[],
name,
undefined,
isOptional ? ts.createToken(ts.SyntaxKind.QuestionToken): undefined,
typeValue,
undefined,
);
Expand Down Expand Up @@ -291,19 +298,16 @@ export function reactJSMakePropsAndStateInterfaceTransformFactoryFactory(typeChe
} else {
result = ts.createKeywordTypeNode(ts.SyntaxKind.AnyKeyword);
}
return result;
}

if (!/\.isRequired/.test(text)) {
return makeTypeNodeOptional(result);
} else {
return result;
}

function makeTypeNodeOptional(node: ts.TypeNode) {
return ts.createUnionOrIntersectionTypeNode(ts.SyntaxKind.UnionType, [
node,
ts.createKeywordTypeNode(ts.SyntaxKind.UndefinedKeyword)
]);
}
/**
* Decide if node is optional
* @param node React propTypes member node
*/
function isPropTypeOptional(node: ts.PropertyAccessExpression) {
const text = node.getText().replace(/React\.PropTypes\./, '');
return !/\.isRequired/.test(text)
}
};
};
Expand Down
Original file line number Diff line number Diff line change
@@ -1,15 +1,15 @@
import * as React from 'react';

export default class MyComponent extends React.Component<{
any: any | undefined;
array: any[] | undefined;
bool: boolean | undefined;
func: ((...args: any[]) => any) | undefined;
number: number | undefined;
object: object | undefined;
string: string | undefined;
node: (number | string | JSX.Element) | undefined;
element: JSX.Element | undefined;
any?: any;
array?: any[];
bool?: boolean;
func?: (...args: any[]) => any;
number?: number;
object?: object;
string?: string;
node?: number | string | JSX.Element;
element?: JSX.Element;
anyRequired: any;
arrayRequired: any[];
boolRequired: boolean;
Expand Down