Skip to content

Commit

Permalink
feat: paginate tile list
Browse files Browse the repository at this point in the history
  • Loading branch information
pregnantboy committed Oct 2, 2024
1 parent 5b54628 commit 4447dab
Show file tree
Hide file tree
Showing 6 changed files with 86 additions and 32 deletions.
13 changes: 10 additions & 3 deletions packages/backend/src/graphql/queries/tiles/get-tables.ts
Original file line number Diff line number Diff line change
@@ -1,15 +1,22 @@
import paginate from '@/helpers/pagination'

import type { QueryResolvers } from '../../__generated__/types.generated'

const getTables: QueryResolvers['getTables'] = async (
_parent,
_params,
{ limit, offset, name },
context,
) => {
const tables = await context.currentUser
const tables = context.currentUser
.$relatedQuery('tables')
.where((builder) => {
if (name) {
builder.where('table_metadata.name', 'ilike', `%${name}%`)
}
})
.orderBy('last_accessed_at', 'desc')

return tables
return paginate(tables, limit, offset)
}

export default getTables
39 changes: 26 additions & 13 deletions packages/backend/src/graphql/schema.graphql
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ type Query {
appKey: String
connectionId: String
name: String
): FlowConnection
): PaginatedFlows
getStepWithTestExecutions(stepId: String!): [Step] @deprecated(reason: "Use getTestExecution instead")
getTestExecutionSteps(flowId: String!, ignoreTestExecutionId: Boolean): [ExecutionStep]
getExecution(executionId: String!): Execution
Expand All @@ -23,20 +23,24 @@ type Query {
offset: Int!
status: String
searchInput: String
): ExecutionConnection
): PaginatedExecutions
getExecutionSteps(
executionId: String!
limit: Int!
offset: Int!
): ExecutionStepConnection
): PagingatedExecutionSteps
getDynamicData(
stepId: String!
key: String!
parameters: JSONObject
): [JSONObject]
# Tiles
getTable(tableId: String!): TableMetadata!
getTables: [TableMetadata!]!
getTables(
limit: Int!
offset: Int!
name: String
): PaginatedTables!
# Tiles rows
getAllRows(tableId: String!): Any!
getCurrentUser: User
Expand Down Expand Up @@ -320,9 +324,9 @@ type Field {
options: [ArgumentOption]
}

type FlowConnection {
edges: [FlowEdge]
pageInfo: PageInfo
type PaginatedFlows {
edges: [FlowEdge]!
pageInfo: PageInfo!
}

type FlowEdge {
Expand Down Expand Up @@ -668,14 +672,14 @@ type ExecutionStepEdge {
node: ExecutionStep
}

type ExecutionConnection {
edges: [ExecutionEdge]
pageInfo: PageInfo
type PaginatedExecutions {
edges: [ExecutionEdge]!
pageInfo: PageInfo!
}

type ExecutionStepConnection {
edges: [ExecutionStepEdge]
pageInfo: PageInfo
type PagingatedExecutionSteps {
edges: [ExecutionStepEdge]!
pageInfo: PageInfo!
}

# Tiles types
Expand Down Expand Up @@ -744,6 +748,15 @@ type TableMetadata {
role: String
}

type TableMetadataEdge {
node: TableMetadata!
}

type PaginatedTables {
edges: [TableMetadataEdge!]!
pageInfo: PageInfo!
}

# End Tiles types

# Start Tiles row types
Expand Down
1 change: 1 addition & 0 deletions packages/backend/src/helpers/pagination.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ const paginate = async <TModel extends Model>(
totalCount: count,
},
edges: records.map((record: TModel) => {
// TODO: remove this node key and return the record directly
return {
node: record,
}
Expand Down
20 changes: 14 additions & 6 deletions packages/frontend/src/graphql/queries/tiles/get-tables.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,20 @@
import { gql } from '@apollo/client'

export const GET_TABLES = gql`
query GetTables {
getTables {
id
name
lastAccessedAt
role
query GetTables($limit: Int!, $offset: Int!, $name: String) {
getTables(limit: $limit, offset: $offset, name: $name) {
pageInfo {
currentPage
totalCount
}
edges {
node {
id
name
lastAccessedAt
role
}
}
}
}
`
7 changes: 3 additions & 4 deletions packages/frontend/src/pages/Tiles/components/TileList.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
import { ITableMetadata } from '@plumber/types'

import { MouseEvent, useCallback, useRef } from 'react'
import { BiDotsHorizontalRounded, BiShow, BiTrash } from 'react-icons/bi'
import { MdOutlineRemoveRedEye } from 'react-icons/md'
Expand Down Expand Up @@ -33,11 +31,12 @@ import {
} from '@opengovsg/design-system-react'

import * as URLS from '@/config/urls'
import { TableMetadata } from '@/graphql/__generated__/graphql'
import { DELETE_TABLE } from '@/graphql/mutations/tiles/delete-table'
import { GET_TABLES } from '@/graphql/queries/tiles/get-tables'
import { toPrettyDateString } from '@/helpers/dateTime'

const TileListItem = ({ table }: { table: ITableMetadata }): JSX.Element => {
const TileListItem = ({ table }: { table: TableMetadata }): JSX.Element => {
const navigate = useNavigate()
const [deleteTable, { loading: isDeletingTable }] = useMutation(
DELETE_TABLE,
Expand Down Expand Up @@ -182,7 +181,7 @@ const TileListItem = ({ table }: { table: ITableMetadata }): JSX.Element => {
}

interface TileListProps {
tiles: ITableMetadata[]
tiles: TableMetadata[]
}

const TileList = ({ tiles }: TileListProps): JSX.Element => {
Expand Down
38 changes: 32 additions & 6 deletions packages/frontend/src/pages/Tiles/index.tsx
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
import { ITableMetadata } from '@plumber/types'

import { useSearchParams } from 'react-router-dom'
import { useQuery } from '@apollo/client'
import { Center, Flex } from '@chakra-ui/react'
import { Pagination } from '@opengovsg/design-system-react'

import Container from '@/components/Container'
import PageTitle from '@/components/PageTitle'
import PrimarySpinner from '@/components/PrimarySpinner'
import { PaginatedTables } from '@/graphql/__generated__/graphql'
import { GET_TABLES } from '@/graphql/queries/tiles/get-tables'

import CreateTileButton from './components/CreateTileButton'
Expand All @@ -14,10 +15,20 @@ import TileList from './components/TileList'

const TILES_TITLE = 'Tiles'

const TILES_PER_PAGE = 10

export default function Tiles(): JSX.Element {
const [searchParams, setSearchParams] = useSearchParams()
const page = parseInt(searchParams.get('page') || '', 10) || 1

const { data, loading: isTileListLoading } = useQuery<{
getTables: ITableMetadata[]
}>(GET_TABLES)
getTables: PaginatedTables
}>(GET_TABLES, {
variables: {
limit: TILES_PER_PAGE,
offset: (page - 1) * TILES_PER_PAGE,
},
})

if (!data?.getTables || isTileListLoading) {
return (
Expand All @@ -27,7 +38,10 @@ export default function Tiles(): JSX.Element {
)
}

const isEmpty = data.getTables.length === 0
const { pageInfo, edges } = data.getTables || {}
const tilesToDisplay = edges.map(({ node }) => node)
const isEmpty = tilesToDisplay?.length === 0

return (
<Container py={9}>
<Flex
Expand All @@ -44,8 +58,20 @@ export default function Tiles(): JSX.Element {
<PageTitle title={TILES_TITLE} />
{!isEmpty && <CreateTileButton />}
</Flex>
{isEmpty ? <EmptyTileList /> : <TileList tiles={data.getTables} />}
{isEmpty ? <EmptyTileList /> : <TileList tiles={tilesToDisplay} />}
</Flex>
{pageInfo && pageInfo.totalCount > TILES_PER_PAGE && (
<Flex justifyContent="center" mt={6}>
<Pagination
currentPage={pageInfo.currentPage}
onPageChange={(page) =>
setSearchParams(page === 1 ? {} : { page: page.toString() })
}
pageSize={TILES_PER_PAGE}
totalCount={pageInfo.totalCount}
/>
</Flex>
)}
</Container>
)
}

0 comments on commit 4447dab

Please sign in to comment.