Skip to content

Commit 3679393

Browse files
committed
feat(indexd): add contract delete
1 parent aa56baa commit 3679393

File tree

8 files changed

+129
-1
lines changed

8 files changed

+129
-1
lines changed
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
---
2+
'@siafoundation/indexd-types': minor
3+
'@siafoundation/indexd-js': minor
4+
'@siafoundation/indexd-react': minor
5+
---
6+
7+
Added contract delete API.
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
'indexd': minor
3+
---
4+
5+
Added contract delete action to contract side panel and bulk actions.

apps/indexd/components/Data/Contracts/SidePanelContract.tsx

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ import { SidePanelHeadingCopyable } from '../SidePanelHeadingCopyable'
1717
import { SidePanelSkeleton } from '../SidePanelSkeleton'
1818
import { useHost } from '../Hosts/useHost'
1919
import { countryCodeEmoji } from '@siafoundation/units'
20+
import { BulkContractDelete } from './bulkActions/BulkContractDelete'
2021

2122
export function SidePanelContract() {
2223
const { panelId, setPanelId } = useContractsParams()
@@ -46,7 +47,7 @@ export function SidePanelContract() {
4647
loading={
4748
<SidePanelSkeleton
4849
withMap
49-
withActions={false}
50+
withActions
5051
onClose={() => setPanelId(undefined)}
5152
/>
5253
}
@@ -67,6 +68,7 @@ export function SidePanelContract() {
6768
label="contract"
6869
/>
6970
}
71+
actions={<BulkContractDelete contracts={[contract]} />}
7072
>
7173
<HostMap
7274
hosts={mapContract ? [mapContract] : []}

apps/indexd/components/Data/Contracts/SidePanelContractList.tsx

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ import { ContractDataTableState } from './types'
33
import { SidePanel } from '../SidePanel'
44
import { useMemo } from 'react'
55
import { MetricsContracts } from '../../Metrics/MetricsContracts'
6+
import { BulkContractDelete } from './bulkActions/BulkContractDelete'
67

78
export function SidePanelContractList({
89
table,
@@ -23,6 +24,11 @@ export function SidePanelContractList({
2324
: 'All contracts'}
2425
</Text>
2526
}
27+
actions={
28+
table.isSelection ? (
29+
<BulkContractDelete contracts={table.selectedRows} />
30+
) : null
31+
}
2632
customCloseAction={
2733
table.isSelection ? (
2834
<Button onClick={() => table.setRowSelection({})}>
Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
import { Button, handleBatchOperation } from '@siafoundation/design-system'
2+
import { useAdminContractDelete } from '@siafoundation/indexd-react'
3+
import { useCallback } from 'react'
4+
import { pluralize } from '@siafoundation/units'
5+
import { ContractData } from '../types'
6+
import { useMutate } from '@siafoundation/react-core'
7+
import {
8+
adminContractRoute,
9+
adminContractsRoute,
10+
} from '@siafoundation/indexd-types'
11+
import { Row } from '@tanstack/react-table'
12+
import { TrashCan16 } from '@siafoundation/react-icons'
13+
import { useDialog } from '../../../../contexts/dialog'
14+
15+
export function BulkContractDelete({
16+
contracts,
17+
}: {
18+
contracts: ContractData[] | Row<ContractData>[]
19+
}) {
20+
const contractDelete = useAdminContractDelete()
21+
const mutate = useMutate()
22+
const { openConfirmDialog } = useDialog()
23+
24+
const normalized = contracts.map((contract) =>
25+
'id' in contract && 'displayFields' in contract
26+
? contract
27+
: (contract.original as ContractData)
28+
)
29+
30+
const operation = useCallback(async () => {
31+
await handleBatchOperation(
32+
normalized.map((contract) =>
33+
contractDelete.delete({
34+
params: {
35+
contractid: contract.id,
36+
},
37+
})
38+
),
39+
{
40+
toastError: ({ successCount, errorCount, totalCount }) => ({
41+
title: `Deleted ${pluralize(successCount, 'contract')}`,
42+
body: `Error deleting ${errorCount}/${totalCount} total contracts.`,
43+
}),
44+
toastSuccess: ({ totalCount }) => ({
45+
title: `Deleted ${pluralize(totalCount, 'contract')}`,
46+
}),
47+
}
48+
)
49+
await mutate((key) => key.startsWith(adminContractsRoute))
50+
await mutate((key) =>
51+
key.startsWith(adminContractRoute.replace(':contractid', ''))
52+
)
53+
}, [normalized, contractDelete, mutate])
54+
55+
return (
56+
<Button
57+
onClick={() =>
58+
openConfirmDialog({
59+
title:
60+
normalized.length === 1
61+
? 'Delete this contract?'
62+
: `Delete ${pluralize(normalized.length, 'contract')}?`,
63+
action: 'Delete',
64+
variant: 'red',
65+
body:
66+
normalized.length === 1
67+
? 'Sectors pinned to this contract will be unpinned and the contract will be marked as bad.'
68+
: 'Sectors pinned to the selected contracts will be unpinned and the contracts will be marked as bad.',
69+
onConfirm: operation,
70+
})
71+
}
72+
variant="red"
73+
>
74+
<TrashCan16 />
75+
Delete{contracts.length > 1 ? ` (${contracts.length})` : ''}
76+
</Button>
77+
)
78+
}

libs/indexd-js/src/admin.ts

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,9 @@ import {
2424
AdminContractParams,
2525
AdminContractPayload,
2626
AdminContractResponse,
27+
AdminContractDeleteParams,
28+
AdminContractDeletePayload,
29+
AdminContractDeleteResponse,
2730
adminContractRoute,
2831
AdminContractsParams,
2932
AdminContractsPayload,
@@ -253,6 +256,11 @@ export function Admin({
253256
AdminContractPayload,
254257
AdminContractResponse
255258
>(axios, 'get', adminContractRoute),
259+
contractDelete: buildRequestHandler<
260+
AdminContractDeleteParams,
261+
AdminContractDeletePayload,
262+
AdminContractDeleteResponse
263+
>(axios, 'delete', adminContractRoute),
256264
contracts: buildRequestHandler<
257265
AdminContractsParams,
258266
AdminContractsPayload,

libs/indexd-react/src/admin.ts

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,9 @@ import {
3030
adminContractRoute,
3131
AdminContractParams,
3232
AdminContractResponse,
33+
AdminContractDeleteParams,
34+
AdminContractDeletePayload,
35+
AdminContractDeleteResponse,
3336
AdminContractsParams,
3437
AdminContractsResponse,
3538
adminContractsRoute,
@@ -313,6 +316,19 @@ export function useAdminContract(
313316
})
314317
}
315318

319+
export function useAdminContractDelete(
320+
args?: HookArgsCallback<
321+
AdminContractDeleteParams,
322+
AdminContractDeletePayload,
323+
AdminContractDeleteResponse
324+
>,
325+
) {
326+
return useDeleteFunc({
327+
...args,
328+
route: adminContractRoute,
329+
})
330+
}
331+
316332
export function useAdminContracts(
317333
args?: HookArgsSwr<AdminContractsParams, AdminContractsResponse>,
318334
) {

libs/indexd-types/src/admin/index.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -123,6 +123,12 @@ export type AdminContractParams = {
123123
export type AdminContractPayload = void
124124
export type AdminContractResponse = Contract
125125

126+
export type AdminContractDeleteParams = {
127+
contractid: FileContractID
128+
}
129+
export type AdminContractDeletePayload = void
130+
export type AdminContractDeleteResponse = void
131+
126132
export const adminContractsRoute = '/contracts'
127133
export type AdminContractsSortBy =
128134
| 'id'

0 commit comments

Comments
 (0)