diff --git a/.changeset/thick-rice-remain.md b/.changeset/thick-rice-remain.md new file mode 100644 index 00000000..6e6b95c8 --- /dev/null +++ b/.changeset/thick-rice-remain.md @@ -0,0 +1,5 @@ +--- +'@soramitsu-ui/ui': minor +--- + +**refactor**(`STableColumn`): use strict type for `sort-orders` prop -- it should be 1-3 length array without duplications diff --git a/packages/theme/package.json b/packages/theme/package.json index 130245b6..58824281 100644 --- a/packages/theme/package.json +++ b/packages/theme/package.json @@ -10,7 +10,7 @@ "src" ], "scripts": { - "test": "vitest" + "test": "vitest run" }, "devDependencies": { "sass": "^1.49.0" diff --git a/packages/ui/package.json b/packages/ui/package.json index e08e7ee1..1a23422c 100644 --- a/packages/ui/package.json +++ b/packages/ui/package.json @@ -30,7 +30,7 @@ "build:clean": "del dist ts-build", "build:vite": "vite build", "build:dts": "run-s build:dts:tsc build:dts:rollup", - "build:dts:tsc": "vue-tsc --outDir ts-build --declaration --emitDeclarationOnly", + "build:dts:tsc": "vue-tsc -p tsconfig.build.json", "build:dts:rollup": "rollup -c rollup.dts.config.cjs" }, "dependencies": { @@ -42,7 +42,6 @@ "focus-trap": "^7.3", "jsoneditor": "^9.5", "lodash-es": "^4.17", - "tiny-invariant": "^1.3", "type-fest": "^3.6", "vue": "^3.2" }, diff --git a/packages/ui/src/components/Table/STableColumn.ts b/packages/ui/src/components/Table/STableColumn.ts index 434d6cd8..2993c84e 100644 --- a/packages/ui/src/components/Table/STableColumn.ts +++ b/packages/ui/src/components/Table/STableColumn.ts @@ -1,17 +1,17 @@ import { defineComponent, type PropType } from 'vue' -import { type TableActionColumnApi, type TableColumnApi, useTableApi } from '@/components' import { uniqueElementId } from '@/util' import { usePropTypeFilter } from '@/composables/prop-type-filter' -import { TABLE_COLUMN_ALIGN_VALUES, TABLE_COLUMN_TYPE_VALUES } from '@/components/Table/consts' +import { TABLE_COLUMN_ALIGN_VALUES, TABLE_COLUMN_TYPE_VALUES } from './consts' import type { TableColumnCellValueFormatter, TableColumnRowSelectableFunc, TableColumnSortBy, - TableColumnSortOrder, + TableColumnSortOrders, TableColumnAlign, TableColumnType, } from './types' -import type { TableColumnWidthProps } from './api' +import { useTableApi } from './api' +import type { TableColumnWidthProps, TableActionColumnApi, TableColumnApi } from './api' export default /* @__PURE__ */ defineComponent({ name: 'STableColumn', @@ -81,8 +81,8 @@ export default /* @__PURE__ */ defineComponent({ * Accepts an array, as the user clicks on the header, the column is sorted in order of the elements in the array */ sortOrders: { - type: Array as PropType, - default: () => ['ascending', 'descending', null], + type: Array as unknown as PropType, + default: (): TableColumnSortOrders => ['ascending', 'descending', null], }, /** * Function that formats cell content diff --git a/packages/ui/src/components/Table/api.ts b/packages/ui/src/components/Table/api.ts index 37b74c57..9b9aecd4 100644 --- a/packages/ui/src/components/Table/api.ts +++ b/packages/ui/src/components/Table/api.ts @@ -4,9 +4,9 @@ import type { TableColumnCellValueFormatter, TableColumnRowSelectableFunc, TableColumnSortBy, - TableColumnSortOrder, TableColumnAlign, TableRow, + TableColumnSortOrders, } from './types' export interface TableColumnWidthProps { @@ -23,7 +23,7 @@ export interface TableColumnSortProps { sortable: boolean | 'custom' sortMethod: ((a: T, b: T) => number) | null sortBy: TableColumnSortBy - sortOrders: TableColumnSortOrder[] + sortOrders: TableColumnSortOrders } export interface TableCommonColumnApi extends TableColumnWidthProps, TableColumnAlignProps, TableColumnSortProps { diff --git a/packages/ui/src/components/Table/types.ts b/packages/ui/src/components/Table/types.ts index 28d2df17..9e3d3be8 100644 --- a/packages/ui/src/components/Table/types.ts +++ b/packages/ui/src/components/Table/types.ts @@ -24,7 +24,16 @@ export type TableColumnCellValueFormatter = ( export type TableColumnSortByPropKeyFunc = (row: TableRow, index: number) => string export type TableColumnRowSelectableFunc = (row: TableRow, index: number) => boolean export type TableColumnSortBy = string | TableColumnSortByPropKeyFunc | (TableColumnSortByPropKeyFunc | string)[] -export type TableColumnSortOrder = 'ascending' | 'descending' | null +export type TableColumnSortOrder = TableColumnSortOrders[0] +export type TableColumnSortOrders = + | OptionalNonEmptyTriple<['ascending', 'descending', null]> + | OptionalNonEmptyTriple<['ascending', null, 'descending']> + | OptionalNonEmptyTriple<['descending', 'ascending', null]> + | OptionalNonEmptyTriple<['descending', null, 'ascending']> + | OptionalNonEmptyTriple<[null, 'ascending', 'descending']> + | OptionalNonEmptyTriple<[null, 'descending', 'ascending']> + +type OptionalNonEmptyTriple = [T[0], T[1]?, T[2]?] export interface TableRowConfigCallbackParams { row: TableRow diff --git a/packages/ui/src/components/Table/use-column-sort.ts b/packages/ui/src/components/Table/use-column-sort.ts index b80a3b59..f7233e8b 100644 --- a/packages/ui/src/components/Table/use-column-sort.ts +++ b/packages/ui/src/components/Table/use-column-sort.ts @@ -2,7 +2,6 @@ import type { Ref } from 'vue' import type { TableColumnApi } from './api' import type { TableColumnSortOrder, TableRow } from './types' import { get } from 'lodash-es' -import invariant from 'tiny-invariant' export function useColumnSort(data: Ref) { const sortState: { column: TableColumnApi | null; order: TableColumnSortOrder } = shallowReactive({ @@ -16,11 +15,10 @@ export function useColumnSort(data: Ref) { sortState.order = null } - function getNextOrder(column: TableColumnApi, order: TableColumnSortOrder) { - const index = column.sortOrders.indexOf(order) - const item = column.sortOrders[(index + 1) % column.sortOrders.length] - invariant(item) - return item + function getNextOrder(column: TableColumnApi, order: TableColumnSortOrder): TableColumnSortOrder { + const array = column.sortOrders + // `!` is safe because of `%` and array's non-emptiness + return array[(array.indexOf(order) + 1) % array.length]! } function getKey(column: TableColumnApi, { value, index }: { value: TableRow; index: number }) { diff --git a/packages/ui/tsconfig.build.json b/packages/ui/tsconfig.build.json new file mode 100644 index 00000000..76827b39 --- /dev/null +++ b/packages/ui/tsconfig.build.json @@ -0,0 +1,9 @@ +{ + "extends": "./tsconfig.json", + "include": ["src", "auto-imports.d.ts"], + "compilerOptions": { + "outDir": "ts-build", + "declaration": true, + "emitDeclarationOnly": true + } +} \ No newline at end of file diff --git a/packages/ui/tsconfig.json b/packages/ui/tsconfig.json index ad5b1732..138acfb1 100644 --- a/packages/ui/tsconfig.json +++ b/packages/ui/tsconfig.json @@ -10,6 +10,12 @@ // not really works within Vue templates "exactOptionalPropertyTypes": false }, + "ts-node": { + "compilerOptions": { + // Cypress conflicts with `verbatimModuleSyntax` + "verbatimModuleSyntax": false + } + }, "include": ["."], "exclude": ["dist", "ts-build", "cypress", "test", "storybook-static", "stories"] } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index c227e6c5..a2f2c085 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -93,7 +93,6 @@ importers: sass: ^1.41.1 storybook: ^7.0.0-beta.62 tabbable: ^6.0.0 - tiny-invariant: ^1.3 ts-pattern: ^4.2.1 type-fest: ^3.6 typescript: 5.0.1-rc @@ -114,7 +113,6 @@ importers: focus-trap: 7.3.1 jsoneditor: 9.10.0 lodash-es: 4.17.21 - tiny-invariant: 1.3.1 type-fest: 3.6.1 vue: 3.2.47 devDependencies: @@ -2826,12 +2824,12 @@ packages: telejson: 7.0.4 dev: true - /@storybook/channel-postmessage/7.0.0-rc.1: - resolution: {integrity: sha512-lIj0oDecEOSy6ZSNXBgWs0hqnjKudrDxuRyR0gAC5w5lZ8sMaj6er9caqaii61S4HRAcT5312RpA0V1J746hZw==} + /@storybook/channel-postmessage/7.0.0-rc.3: + resolution: {integrity: sha512-1uptuCjA4vAvvoxNoIJPTIpSARzJnLU7eahRhTPwELBnCH0ObqvgInge0cvbYsaTRDNV90oBbEKlxLf1Zb1BhQ==} dependencies: - '@storybook/channels': 7.0.0-rc.1 - '@storybook/client-logger': 7.0.0-rc.1 - '@storybook/core-events': 7.0.0-rc.1 + '@storybook/channels': 7.0.0-rc.3 + '@storybook/client-logger': 7.0.0-rc.3 + '@storybook/core-events': 7.0.0-rc.3 '@storybook/global': 5.0.0 qs: 6.11.1 telejson: 7.0.4 @@ -2850,8 +2848,8 @@ packages: resolution: {integrity: sha512-WG0bH5EYIi2Eh7iRNq9ScvQlzuBZqtlg0CV8FdLdEeDp6LuYRgIabdjON0PDGagwpir0ozDAqF5sRMwYkhuVPg==} dev: true - /@storybook/channels/7.0.0-rc.1: - resolution: {integrity: sha512-hBER6gliJxsrYEbWlXNljf0/1ybIlYCtaK0Vcgqdw/zmTLG6hEbBpVnxJh56T3mD0Beng8ro9D4EkcLZGQ1LlA==} + /@storybook/channels/7.0.0-rc.3: + resolution: {integrity: sha512-jaODIck+um16Fn2k1vwHK9RNk2J8hLVyzLSkoGM40TsMF5nichwI3rA6225pLk015itJbhCAi/RhaMFBI+ZtsA==} dev: true /@storybook/cli/7.0.0-beta.62: @@ -2909,8 +2907,8 @@ packages: '@storybook/global': 5.0.0 dev: true - /@storybook/client-logger/7.0.0-rc.1: - resolution: {integrity: sha512-ltdDjd5wwq1xyFmA7Q7PT0Rx4Jrd0u8m0hnjnlou7qjKd7J+tqi8019oC4t5CSWRhl8lDg0QbI11LUM2SmkRMA==} + /@storybook/client-logger/7.0.0-rc.3: + resolution: {integrity: sha512-cC7lq+S4n5fFooDCyefgTAOfipadiZskNuzsQF7drE9nQLZ8GflLdmTKK//5NQUHKPzF7r+4Q5DAK4I3nqIkxA==} dependencies: '@storybook/global': 5.0.0 dev: true @@ -2991,8 +2989,8 @@ packages: resolution: {integrity: sha512-/301tBWbUnhv4tTg5feTR3r1iZ+ep+drEX3ii61SfQNWLugeo9sLIldtxRuEElT6X3Xypw4nCnd+fc3IKDs/Xw==} dev: true - /@storybook/core-events/7.0.0-rc.1: - resolution: {integrity: sha512-kp5p7U8H4X+XnJwzm3S9UM1vOREZ/bziQ34882FevPq7HaAQ5JI7p9gQO50JdTbDoe8gtn8cgfzxSkqO6FlY1w==} + /@storybook/core-events/7.0.0-rc.3: + resolution: {integrity: sha512-EBihNmxxiIJbPt6OhCTXFPl2T/9OXNVKtsy8hchBNEzp+UJGyeHx+t9K6tRvbcmt5TG/y7C7ZsYx9U28JTwNkg==} dev: true /@storybook/core-server/7.0.0-beta.62: @@ -3111,14 +3109,14 @@ packages: '@storybook/preview-api': 7.0.0-beta.62 dev: true - /@storybook/instrumenter/7.0.0-rc.1: - resolution: {integrity: sha512-spihMm1Xb+lw1Vac5Uo+06m2jdDEhGGkM/nesXO3ZkYyNatC0IGXgU9NyELI6YCkhEprwK3MIXoo8in97Kjk+w==} + /@storybook/instrumenter/7.0.0-rc.3: + resolution: {integrity: sha512-LgFLh7v4wHgalThho8BjHd0xq2Tz8EACIbKOJO/qkSvpupfE6FDROrCYGJpQHsTKWAVdZZwVIMd6A+OnPHOLyg==} dependencies: - '@storybook/channels': 7.0.0-rc.1 - '@storybook/client-logger': 7.0.0-rc.1 - '@storybook/core-events': 7.0.0-rc.1 + '@storybook/channels': 7.0.0-rc.3 + '@storybook/client-logger': 7.0.0-rc.3 + '@storybook/core-events': 7.0.0-rc.3 '@storybook/global': 5.0.0 - '@storybook/preview-api': 7.0.0-rc.1 + '@storybook/preview-api': 7.0.0-rc.3 dev: true /@storybook/manager-api/7.0.0-beta.62_biqbaboplfbrettd7655fr4n2y: @@ -3188,16 +3186,16 @@ packages: util-deprecate: 1.0.2 dev: true - /@storybook/preview-api/7.0.0-rc.1: - resolution: {integrity: sha512-KrXMxCffKsXLsWb8ptXmLcbetZOPLbPpnKU43S1iHnvc5Jp89lrJBpztHZsUnuwGMJ1K5ajdZd+l/kGs75ru6Q==} + /@storybook/preview-api/7.0.0-rc.3: + resolution: {integrity: sha512-iIifbFRmrFIlLzApTZyCWmI3JNt2IxfM8Dm4rNlMJBifjtgHfpxA+DsQI8mW8UGM64a8N1wF7azkN6cnRz6v2w==} dependencies: - '@storybook/channel-postmessage': 7.0.0-rc.1 - '@storybook/channels': 7.0.0-rc.1 - '@storybook/client-logger': 7.0.0-rc.1 - '@storybook/core-events': 7.0.0-rc.1 + '@storybook/channel-postmessage': 7.0.0-rc.3 + '@storybook/channels': 7.0.0-rc.3 + '@storybook/client-logger': 7.0.0-rc.3 + '@storybook/core-events': 7.0.0-rc.3 '@storybook/csf': 0.0.2-next.10 '@storybook/global': 5.0.0 - '@storybook/types': 7.0.0-rc.1 + '@storybook/types': 7.0.0-rc.3 '@types/qs': 6.9.7 dequal: 2.0.3 lodash: 4.17.21 @@ -3256,8 +3254,8 @@ packages: /@storybook/testing-library/0.0.14-next.1: resolution: {integrity: sha512-1CAl40IKIhcPaCC4pYCG0b9IiYNymktfV/jTrX7ctquRY3akaN7f4A1SippVHosksft0M+rQTFE0ccfWW581fw==} dependencies: - '@storybook/client-logger': 7.0.0-rc.1 - '@storybook/instrumenter': 7.0.0-rc.1 + '@storybook/client-logger': 7.0.0-rc.3 + '@storybook/instrumenter': 7.0.0-rc.3 '@testing-library/dom': 8.20.0 '@testing-library/user-event': 13.5.0_yxlyej73nftwmh2fiao7paxmlm ts-dedent: 2.2.0 @@ -3286,10 +3284,10 @@ packages: file-system-cache: 2.0.2 dev: true - /@storybook/types/7.0.0-rc.1: - resolution: {integrity: sha512-wWFGKzXXD04j52iHTE7mxCz0zkJH0J/wh7pSsYAxUgyQaYHIIqLZUb9PLWVWf1v6RiSSa5k0HXhFWnfBOJeVIQ==} + /@storybook/types/7.0.0-rc.3: + resolution: {integrity: sha512-2xxgs4zL1QZUdut+Zt5sQdgNCUP0n/y5CRbvEpDwkcuE4KWbfJYixJNumioZ6UwK17ZE9gf4ZxVgttvexmW8eg==} dependencies: - '@storybook/channels': 7.0.0-rc.1 + '@storybook/channels': 7.0.0-rc.3 '@types/babel__core': 7.20.0 '@types/express': 4.17.17 file-system-cache: 2.0.2 @@ -10030,10 +10028,6 @@ packages: xtend: 4.0.2 dev: true - /tiny-invariant/1.3.1: - resolution: {integrity: sha512-AD5ih2NlSssTCwsMznbvwMZpJ1cbhkGd2uueNxzv2jDlEeZdU04JQfRnggJQ8DrcVBGjAsCKwFBbDlVNtEMlzw==} - dev: false - /tinybench/2.4.0: resolution: {integrity: sha512-iyziEiyFxX4kyxSp+MtY1oCH/lvjH3PxFN8PGCDeqcZWAJ/i+9y+nL85w99PxVzrIvew/GSkSbDYtiGVa85Afg==} dev: true