mirror of
https://github.com/get-drexa/drive.git
synced 2025-12-03 15:01:39 +00:00
feat: upload file dialog err handling & new flow
- add basic err handling to upload file dialog. - rework the upload flow. now, on all successful uploads, the dialog won't auto disappear. if some fails, the dialog will allow for retry.
This commit is contained in:
@@ -1,19 +1,39 @@
|
||||
import { atom } from "jotai"
|
||||
import { atomFamily } from "jotai/utils"
|
||||
|
||||
type FileUpload = {
|
||||
id: string
|
||||
export enum FileUploadStatusKind {
|
||||
InProgress = "InProgress",
|
||||
Error = "Error",
|
||||
Success = "Success",
|
||||
}
|
||||
|
||||
export type FileUploadInProgress = {
|
||||
kind: FileUploadStatusKind.InProgress
|
||||
progress: number
|
||||
}
|
||||
|
||||
export const fileUploadsAtom = atom<Record<string, FileUpload>>({})
|
||||
export type FileUploadError = {
|
||||
kind: FileUploadStatusKind.Error
|
||||
error: unknown
|
||||
}
|
||||
|
||||
export const fileUploadAtomFamily = atomFamily((id: string) =>
|
||||
export type FileUploadSuccess = {
|
||||
kind: FileUploadStatusKind.Success
|
||||
}
|
||||
|
||||
export type FileUploadStatus =
|
||||
| FileUploadInProgress
|
||||
| FileUploadError
|
||||
| FileUploadSuccess
|
||||
|
||||
export const fileUploadsAtom = atom<Record<string, FileUploadStatus>>({})
|
||||
|
||||
export const fileUploadStatusAtomFamily = atomFamily((id: string) =>
|
||||
atom(
|
||||
(get) => get(fileUploadsAtom)[id],
|
||||
(get, set, progress: number) => {
|
||||
(get, set, status: FileUploadStatus) => {
|
||||
const fileUploads = { ...get(fileUploadsAtom) }
|
||||
fileUploads[id] = { id, progress }
|
||||
fileUploads[id] = status
|
||||
set(fileUploadsAtom, fileUploads)
|
||||
},
|
||||
),
|
||||
@@ -22,12 +42,56 @@ export const fileUploadAtomFamily = atomFamily((id: string) =>
|
||||
export const clearFileUploadAtom = atom(null, (get, set, id: string) => {
|
||||
const fileUploads = { ...get(fileUploadsAtom) }
|
||||
delete fileUploads[id]
|
||||
fileUploadAtomFamily.remove(id)
|
||||
fileUploadStatusAtomFamily.remove(id)
|
||||
set(fileUploadsAtom, fileUploads)
|
||||
})
|
||||
|
||||
export const clearFileUploadStatusesAtom = atom(
|
||||
null,
|
||||
(get, set, ids: string[]) => {
|
||||
const fileUploads = { ...get(fileUploadsAtom) }
|
||||
for (const id of ids) {
|
||||
if (fileUploads[id]) {
|
||||
delete fileUploads[id]
|
||||
}
|
||||
fileUploadStatusAtomFamily.remove(id)
|
||||
}
|
||||
set(fileUploadsAtom, fileUploads)
|
||||
},
|
||||
)
|
||||
|
||||
export const fileUploadCountAtom = atom(
|
||||
(get) => Object.keys(get(fileUploadsAtom)).length,
|
||||
)
|
||||
|
||||
export const hasFileUploadsAtom = atom((get) => get(fileUploadCountAtom) > 0)
|
||||
export const inProgressFileUploadCountAtom = atom((get) => {
|
||||
const statuses = get(fileUploadsAtom)
|
||||
let count = 0
|
||||
for (const status in statuses) {
|
||||
if (statuses[status]?.kind === FileUploadStatusKind.InProgress) {
|
||||
count += 1
|
||||
}
|
||||
}
|
||||
return count
|
||||
})
|
||||
|
||||
export const successfulFileUploadCountAtom = atom((get) => {
|
||||
const statuses = get(fileUploadsAtom)
|
||||
let count = 0
|
||||
for (const status in statuses) {
|
||||
if (statuses[status]?.kind === FileUploadStatusKind.Success) {
|
||||
count += 1
|
||||
}
|
||||
}
|
||||
return count
|
||||
})
|
||||
|
||||
export const hasFileUploadsErrorAtom = atom((get) => {
|
||||
const statuses = get(fileUploadsAtom)
|
||||
for (const status in statuses) {
|
||||
if (statuses[status]?.kind === FileUploadStatusKind.Error) {
|
||||
return true
|
||||
}
|
||||
}
|
||||
return false
|
||||
})
|
||||
|
||||
Reference in New Issue
Block a user