Skip to content

refactor(DataTable): update optional type signatures #2987

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 6 commits into from
Mar 6, 2023
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
60 changes: 0 additions & 60 deletions docs/content/drafts/DataTable.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -6,66 +6,6 @@ status: Draft

import data from '../../../src/DataTable/DataTable.docs.json'

## Examples

```jsx
<DataTable
title="Repositories"
data={[
{
id: 1,
name: 'codeql-dca-worker',
type: 'internal',
securityFeatures: {
dependabot: ['alerts', 'security updates'],
},
},
{
id: 2,
name: 'aegir',
type: 'public',
securityFeatures: {
dependabot: ['alerts'],
},
},
{
id: 3,
name: 'strapi',
type: 'public',
securityFeatures: {
dependabot: [],
},
},
]}
columns={[
{
header: 'Repository',
field: 'name',
rowHeader: true,
},
{
header: 'Type',
field: 'type',
renderCell: row => {
return <Label>{uppercase(row.type)}</Label>
},
},
{
header: 'Dependabot',
renderCell: row => {
return row.securityFeatures.dependabot.length > 0 ? (
<LabelGroup>
{row.securityFeatures.dependabot.map(feature => {
return <Label key={feature}>{uppercase(feature)}</Label>
})}
</LabelGroup>
) : null
},
},
]}
/>
```

## Props

<ComponentProps data={data} />
Expand Down
22 changes: 21 additions & 1 deletion generated/components.json
Original file line number Diff line number Diff line change
Expand Up @@ -1906,6 +1906,26 @@
{
"id": "components-datatable--default",
"code": "() => (\n <Table.Container>\n <Table.Title as=\"h2\" id=\"repositories\">\n Repositories\n </Table.Title>\n <Table.Subtitle as=\"p\" id=\"repositories-subtitle\">\n A subtitle could appear here to give extra context to the data.\n </Table.Subtitle>\n <DataTable\n aria-labelledby=\"repositories\"\n aria-describedby=\"repositories-subtitle\"\n data={data}\n columns={[\n {\n header: 'Repository',\n field: 'name',\n rowHeader: true,\n },\n {\n header: 'Type',\n field: 'type',\n renderCell: (row) => {\n return <Label>{uppercase(row.type)}</Label>\n },\n },\n {\n header: 'Updated',\n field: 'updatedAt',\n renderCell: (row) => {\n return <RelativeTime date={new Date(row.updatedAt)} />\n },\n },\n {\n header: 'Dependabot',\n field: 'securityFeatures.dependabot',\n renderCell: (row) => {\n return row.securityFeatures.dependabot.length > 0 ? (\n <LabelGroup>\n {row.securityFeatures.dependabot.map((feature) => {\n return <Label key={feature}>{uppercase(feature)}</Label>\n })}\n </LabelGroup>\n ) : null\n },\n },\n {\n header: 'Code scanning',\n field: 'securityFeatures.codeScanning',\n renderCell: (row) => {\n return row.securityFeatures.codeScanning.length > 0 ? (\n <LabelGroup>\n {row.securityFeatures.codeScanning.map((feature) => {\n return <Label key={feature}>{uppercase(feature)}</Label>\n })}\n </LabelGroup>\n ) : null\n },\n },\n ]}\n />\n </Table.Container>\n)"
},
{
"id": "drafts-components-datatable--with-title",
"code": "() => (\n <Table.Container>\n <Table.Title as=\"h2\" id=\"repositories\">\n Repositories\n </Table.Title>\n <DataTable\n aria-labelledby=\"repositories\"\n aria-describedby=\"repositories-subtitle\"\n data={data}\n columns={[\n {\n header: 'Repository',\n field: 'name',\n rowHeader: true,\n },\n {\n header: 'Type',\n field: 'type',\n renderCell: (row) => {\n return <Label>{uppercase(row.type)}</Label>\n },\n },\n {\n header: 'Updated',\n field: 'updatedAt',\n renderCell: (row) => {\n return <RelativeTime date={new Date(row.updatedAt)} />\n },\n },\n {\n header: 'Dependabot',\n field: 'securityFeatures.dependabot',\n renderCell: (row) => {\n return row.securityFeatures.dependabot.length > 0 ? (\n <LabelGroup>\n {row.securityFeatures.dependabot.map((feature) => {\n return <Label key={feature}>{uppercase(feature)}</Label>\n })}\n </LabelGroup>\n ) : null\n },\n },\n {\n header: 'Code scanning',\n field: 'securityFeatures.codeScanning',\n renderCell: (row) => {\n return row.securityFeatures.codeScanning.length > 0 ? (\n <LabelGroup>\n {row.securityFeatures.codeScanning.map((feature) => {\n return <Label key={feature}>{uppercase(feature)}</Label>\n })}\n </LabelGroup>\n ) : null\n },\n },\n ]}\n />\n </Table.Container>\n)"
},
{
"id": "drafts-components-datatable--with-title-and-subtitle",
"code": "() => (\n <Table.Container>\n <Table.Title as=\"h2\" id=\"repositories\">\n Repositories\n </Table.Title>\n <Table.Subtitle as=\"p\" id=\"repositories-subtitle\">\n A subtitle could appear here to give extra context to the data.\n </Table.Subtitle>\n <DataTable\n aria-labelledby=\"repositories\"\n aria-describedby=\"repositories-subtitle\"\n data={data}\n columns={[\n {\n header: 'Repository',\n field: 'name',\n rowHeader: true,\n },\n {\n header: 'Type',\n field: 'type',\n renderCell: (row) => {\n return <Label>{uppercase(row.type)}</Label>\n },\n },\n {\n header: 'Updated',\n field: 'updatedAt',\n renderCell: (row) => {\n return <RelativeTime date={new Date(row.updatedAt)} />\n },\n },\n {\n header: 'Dependabot',\n field: 'securityFeatures.dependabot',\n renderCell: (row) => {\n return row.securityFeatures.dependabot.length > 0 ? (\n <LabelGroup>\n {row.securityFeatures.dependabot.map((feature) => {\n return <Label key={feature}>{uppercase(feature)}</Label>\n })}\n </LabelGroup>\n ) : null\n },\n },\n {\n header: 'Code scanning',\n field: 'securityFeatures.codeScanning',\n renderCell: (row) => {\n return row.securityFeatures.codeScanning.length > 0 ? (\n <LabelGroup>\n {row.securityFeatures.codeScanning.map((feature) => {\n return <Label key={feature}>{uppercase(feature)}</Label>\n })}\n </LabelGroup>\n ) : null\n },\n },\n ]}\n />\n </Table.Container>\n)"
},
{
"id": "drafts-components-datatable--with-sorting",
"code": "() => {\n const rows = Array.from(data).sort((a, b) => {\n return b.updatedAt - a.updatedAt\n })\n return (\n <Table.Container>\n <Table.Title as=\"h2\" id=\"repositories\">\n Repositories\n </Table.Title>\n <Table.Subtitle as=\"p\" id=\"repositories-subtitle\">\n A subtitle could appear here to give extra context to the data.\n </Table.Subtitle>\n <DataTable\n aria-labelledby=\"repositories\"\n aria-describedby=\"repositories-subtitle\"\n data={rows}\n columns={[\n {\n header: 'Repository',\n field: 'name',\n rowHeader: true,\n sortBy: true,\n },\n {\n header: 'Type',\n field: 'type',\n renderCell: (row) => {\n return <Label>{uppercase(row.type)}</Label>\n },\n },\n {\n header: 'Updated',\n field: 'updatedAt',\n sortBy: true,\n renderCell: (row) => {\n return <RelativeTime date={new Date(row.updatedAt)} />\n },\n },\n {\n header: 'Dependabot',\n field: 'securityFeatures.dependabot',\n renderCell: (row) => {\n return row.securityFeatures.dependabot.length > 0 ? (\n <LabelGroup>\n {row.securityFeatures.dependabot.map((feature) => {\n return <Label key={feature}>{uppercase(feature)}</Label>\n })}\n </LabelGroup>\n ) : null\n },\n },\n {\n header: 'Code scanning',\n field: 'securityFeatures.codeScanning',\n renderCell: (row) => {\n return row.securityFeatures.codeScanning.length > 0 ? (\n <LabelGroup>\n {row.securityFeatures.codeScanning.map((feature) => {\n return <Label key={feature}>{uppercase(feature)}</Label>\n })}\n </LabelGroup>\n ) : null\n },\n },\n ]}\n initialSortColumn=\"updatedAt\"\n initialSortDirection=\"DESC\"\n />\n </Table.Container>\n )\n}"
},
{
"id": "drafts-components-datatable--with-actions",
"code": "() => (\n <Table.Container>\n <Table.Title as=\"h2\" id=\"repositories\">\n Repositories\n </Table.Title>\n <Table.Actions>\n <IconButton\n aria-label=\"Download\"\n icon={DownloadIcon}\n variant=\"invisible\"\n />\n <IconButton aria-label=\"Add row\" icon={PlusIcon} variant=\"invisible\" />\n </Table.Actions>\n <Table.Divider />\n <Table.Subtitle as=\"p\" id=\"repositories-subtitle\">\n A subtitle could appear here to give extra context to the data.\n </Table.Subtitle>\n <DataTable\n aria-labelledby=\"repositories\"\n aria-describedby=\"repositories-subtitle\"\n data={data}\n columns={[\n {\n header: 'Repository',\n field: 'name',\n rowHeader: true,\n },\n {\n header: 'Type',\n field: 'type',\n renderCell: (row) => {\n return <Label>{uppercase(row.type)}</Label>\n },\n },\n {\n header: 'Updated',\n field: 'updatedAt',\n renderCell: (row) => {\n return <RelativeTime date={new Date(row.updatedAt)} />\n },\n },\n {\n header: 'Dependabot',\n field: 'securityFeatures.dependabot',\n renderCell: (row) => {\n return row.securityFeatures.dependabot.length > 0 ? (\n <LabelGroup>\n {row.securityFeatures.dependabot.map((feature) => {\n return <Label key={feature}>{uppercase(feature)}</Label>\n })}\n </LabelGroup>\n ) : null\n },\n },\n {\n header: 'Code scanning',\n field: 'securityFeatures.codeScanning',\n renderCell: (row) => {\n return row.securityFeatures.codeScanning.length > 0 ? (\n <LabelGroup>\n {row.securityFeatures.codeScanning.map((feature) => {\n return <Label key={feature}>{uppercase(feature)}</Label>\n })}\n </LabelGroup>\n ) : null\n },\n },\n ]}\n />\n </Table.Container>\n)"
},
{
"id": "drafts-components-datatable--with-action",
"code": "() => (\n <Table.Container>\n <Table.Title as=\"h2\" id=\"repositories\">\n Repositories\n </Table.Title>\n <Table.Actions>\n <Button>Action</Button>\n </Table.Actions>\n <Table.Divider />\n <Table.Subtitle as=\"p\" id=\"repositories-subtitle\">\n A subtitle could appear here to give extra context to the data.\n </Table.Subtitle>\n <DataTable\n aria-labelledby=\"repositories\"\n aria-describedby=\"repositories-subtitle\"\n data={data}\n columns={[\n {\n header: 'Repository',\n field: 'name',\n rowHeader: true,\n },\n {\n header: 'Type',\n field: 'type',\n renderCell: (row) => {\n return <Label>{uppercase(row.type)}</Label>\n },\n },\n {\n header: 'Updated',\n field: 'updatedAt',\n renderCell: (row) => {\n return <RelativeTime date={new Date(row.updatedAt)} />\n },\n },\n {\n header: 'Dependabot',\n field: 'securityFeatures.dependabot',\n renderCell: (row) => {\n return row.securityFeatures.dependabot.length > 0 ? (\n <LabelGroup>\n {row.securityFeatures.dependabot.map((feature) => {\n return <Label key={feature}>{uppercase(feature)}</Label>\n })}\n </LabelGroup>\n ) : null\n },\n },\n {\n header: 'Code scanning',\n field: 'securityFeatures.codeScanning',\n renderCell: (row) => {\n return row.securityFeatures.codeScanning.length > 0 ? (\n <LabelGroup>\n {row.securityFeatures.codeScanning.map((feature) => {\n return <Label key={feature}>{uppercase(feature)}</Label>\n })}\n </LabelGroup>\n ) : null\n },\n },\n ]}\n />\n </Table.Container>\n)"
}
],
"props": [
Expand Down Expand Up @@ -2005,7 +2025,7 @@
},
{
"name": "scope",
"type": "string",
"type": "'row'",
"description": "Provide the scope for a table cell, useful for defining a row header using `scope=\"row\"`"
}
]
Expand Down
20 changes: 18 additions & 2 deletions src/DataTable/DataTable.docs.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,23 @@
"name": "DataTable",
"status": "draft",
"a11yReviewed": false,
"stories": [],
"stories": [
{
"id": "drafts-components-datatable--with-title"
},
{
"id": "drafts-components-datatable--with-title-and-subtitle"
},
{
"id": "drafts-components-datatable--with-sorting"
},
{
"id": "drafts-components-datatable--with-actions"
},
{
"id": "drafts-components-datatable--with-action"
}
],
"props": [
{
"name": "aria-describedby",
Expand Down Expand Up @@ -101,7 +117,7 @@
},
{
"name": "scope",
"type": "string",
"type": "'row'",
"description": "Provide the scope for a table cell, useful for defining a row header using `scope=\"row\"`"
}
]
Expand Down
10 changes: 5 additions & 5 deletions src/DataTable/DataTable.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -14,18 +14,18 @@ export type DataTableProps<Data extends UniqueRow> = {
/**
* Provide an id to an element which uniquely describes this table
*/
'aria-describedby'?: string | undefined
'aria-describedby'?: string

/**
* Provide an id to an element which uniquely labels this table
*/
'aria-labelledby'?: string | undefined
'aria-labelledby'?: string

/**
* Specify the amount of space that should be available around the contents of
* a cell
*/
cellPadding?: 'condensed' | 'normal' | 'spacious' | undefined
cellPadding?: 'condensed' | 'normal' | 'spacious'

/**
* Provide a collection of the rows which will be rendered inside of the table
Expand All @@ -43,13 +43,13 @@ export type DataTableProps<Data extends UniqueRow> = {
* using this `prop`, the input data must be sorted by this column in
* ascending order
*/
initialSortColumn?: ObjectPaths<Data> | string | undefined
initialSortColumn?: ObjectPaths<Data> | string

/**
* Provide the sort direction that the table should be sorted by on the
* currently sorted column
*/
initialSortDirection?: Exclude<SortDirection, 'NONE'> | undefined
initialSortDirection?: Exclude<SortDirection, 'NONE'>
}

function DataTable<Data extends UniqueRow>({
Expand Down
8 changes: 4 additions & 4 deletions src/DataTable/Table.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -144,18 +144,18 @@ export type TableProps = React.ComponentPropsWithoutRef<'table'> & {
/**
* Provide an id to an element which uniquely describes this table
*/
'aria-describedby'?: string | undefined
'aria-describedby'?: string

/**
* Provide an id to an element which uniquely labels this table
*/
'aria-labelledby'?: string | undefined
'aria-labelledby'?: string

/**
* Specify the amount of space that should be available around the contents of
* a cell
*/
cellPadding?: 'condensed' | 'normal' | 'spacious' | undefined
cellPadding?: 'condensed' | 'normal' | 'spacious'
}

const Table = React.forwardRef<HTMLTableElement, TableProps>(function Table({cellPadding = 'normal', ...rest}, ref) {
Expand Down Expand Up @@ -252,7 +252,7 @@ export type TableCellProps = React.ComponentPropsWithoutRef<'td'> & {
* Provide the scope for a table cell, useful for defining a row header using
* `scope="row"`
*/
scope?: 'row' | undefined
scope?: 'row'
}

function TableCell({children, scope, ...rest}: TableCellProps) {
Expand Down
6 changes: 3 additions & 3 deletions src/DataTable/column.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import {UniqueRow} from './row'
import {SortStrategies} from './sorting'

export interface Column<Data extends UniqueRow> {
id?: string | undefined
id?: string

/**
* Provide the name of the column. This will be rendered as a table header
Expand All @@ -25,13 +25,13 @@ export interface Column<Data extends UniqueRow> {
* Provide a custom component or render prop to render the data for this
* column in a row
*/
renderCell?: ((data: Data) => React.ReactNode) | undefined
renderCell?: (data: Data) => React.ReactNode

/**
* Specify if the value of this column for a row should be treated as a row
* header
*/
rowHeader?: boolean | undefined
rowHeader?: boolean

/**
* Specify if the table should sort by this column and, if applicable, a
Expand Down
4 changes: 2 additions & 2 deletions src/DataTable/useTable.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,8 @@ import {ObjectPathValue} from './utils'
interface TableConfig<Data extends UniqueRow> {
columns: Array<Column<Data>>
data: Array<Data>
initialSortColumn?: string | undefined
initialSortDirection?: Exclude<SortDirection, 'NONE'> | undefined
initialSortColumn?: string
initialSortDirection?: Exclude<SortDirection, 'NONE'>
}

interface Table<Data extends UniqueRow> {
Expand Down
1 change: 1 addition & 0 deletions src/__tests__/storybook.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ const allowlist = [
'Checkbox',
'CheckboxGroup',
'CounterLabel',
'DataTable',
'Details',
'Flash',
'Heading',
Expand Down