Skip to content

Instantly share code, notes, and snippets.

@rjstires
Last active November 7, 2018 21:56
Show Gist options
  • Save rjstires/94ccd4716e44784a6a6a9ba0920ae620 to your computer and use it in GitHub Desktop.
Save rjstires/94ccd4716e44784a6a6a9ba0920ae620 to your computer and use it in GitHub Desktop.
Is this too much?
import React from 'react';
interface Props {
loading: any;
data?: any;
error?: any;
isEmpty: (data: any) => boolean;
renderEmpty: () => JSX.Element;
renderError?: (error: Error) => JSX.Element;
renderLoading: () => JSX.Element;
children: (data: any) => null | JSX.Element;
}
type CombinedProps = Props;
const MaybeRenderContent: React.StatelessComponent<CombinedProps> = (props) => {
const {
data,
error,
loading,
isEmpty,
renderEmpty,
renderError,
renderLoading,
children,
} = props;
if (error && renderError) {
return renderError(error);
}
if (loading) {
return renderLoading();
}
if (isEmpty(data)) {
return renderEmpty();
}
return children(data);
};
export default MaybeRenderContent;
/**
*
* EXAMPLE USAGE EXAMPLE USAGE EXAMPLE USAGE EXAMPLE USAGE
*
*/
interface MyComponentProps {
data?: number[];
error?: Error;
loading: boolean;
}
const MyComponent: React.StatelessComponent<MyComponentProps> = (props) => {
const { data, error, loading } = props;
return (
<table>
<thead>
<tr>
<td>id</td>
<td>name</td>
<td>options</td>
</tr>
</thead>
<tbody>
<tr>
<MaybeRenderContent
data={data}
error={error}
loading={loading}
isEmpty={contentIsEmpty}
renderEmpty={EmptyComponent}
renderError={ErrorComponent}
renderLoading={LoadingComponent}
>
{ContentComponent}
</MaybeRenderContent>
</tr>
</tbody>
<tfoot>
<tr>
<td colSpan={3} />
</tr>
</tfoot>
</table>
);
}
const contentIsEmpty = (d: number[]) => !d || d.length === 0;
const SingleRow: React.StatelessComponent = (props) =>
<tr>
<td colSpan={3}>{props.children}</td>
</tr>;
const ErrorComponent = (error: Error) =>
<SingleRow>Something bad happened.</SingleRow>
const EmptyComponent = () =>
<SingleRow>Aint nothin here...</SingleRow>
const LoadingComponent = () =>
<SingleRow>Hang on skippy, it's loading...</SingleRow>
const ContentComponent = (numbers: number[]) =>
<React.Fragment>
{numbers.map(n =>
<tr key={n}>
<td>{n}</td>
<td>some label</td>
<td>some options</td>
</tr>)
}
</React.Fragment>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment