Refactor file handling to improve URL safety and enhance file viewing capabilities across components

This commit is contained in:
Marshal
2026-06-28 08:19:21 +00:00
parent b424de8436
commit da533a488d
11 changed files with 100 additions and 28 deletions

View File

@@ -23,6 +23,7 @@ import { useMemo, useRef, useState } from "react";
import { useNavigate } from "react-router-dom";
import { api } from "@/services/api";
import { fileViewUrl } from "@/constants/apiConfig";
import type { SubmitBookingResponse } from "@/services/bookings.service";
import type { Freight } from "@edr/types";
@@ -288,14 +289,16 @@ export function DraftBookingView({
action={
isUploaded && !allowReplace ? (
<IconSquare
href={file?.signedUrl ?? file?.url}
href={file ? fileViewUrl(file.id, true) : undefined}
icon={<Download size={16} />}
/>
) : (
<>
{isUploaded && (
<IconSquare
href={file?.signedUrl ?? file?.url}
href={
file ? fileViewUrl(file.id, true) : undefined
}
icon={<Download size={16} />}
/>
)}

View File

@@ -6,6 +6,7 @@ import { useNavigate } from "react-router-dom";
import { isViewable } from "@edr/ui-common";
import { api } from "@/services/api";
import { fileViewUrl } from "@/constants/apiConfig";
import { useFileViewer } from "@/hooks/useFileViewer";
import { paymentsService, type PaymentMethod } from "@/services/payments.service";
import type { Freight } from "@edr/types";
@@ -165,7 +166,7 @@ export function ReadonlyBookingView({ booking }: { booking: Freight.IBooking })
<Group gap={6} wrap="nowrap">
{isViewable({
name: file.name,
url: file.signedUrl ?? file.url,
url: fileViewUrl(file.id),
mimeType: file.mimeType,
}) && (
<IconSquare
@@ -173,14 +174,14 @@ export function ReadonlyBookingView({ booking }: { booking: Freight.IBooking })
onClick={() =>
view({
name: file.name,
url: file.signedUrl ?? file.url,
url: fileViewUrl(file.id),
mimeType: file.mimeType,
})
}
/>
)}
<IconSquare
href={file.signedUrl ?? file.url}
href={fileViewUrl(file.id, true)}
icon={<Download size={16} />}
/>
</Group>

View File

@@ -1,4 +1,5 @@
import { api } from "@/services/api";
import { fileViewUrl } from "@/constants/apiConfig";
import type { CreateBookingPayload } from "@/services/bookings.service";
import type { Freight } from "@edr/types";
import { zodResolver } from "@hookform/resolvers/zod";
@@ -948,7 +949,11 @@ export default function EditBookingPage() {
<Group gap={6} wrap="nowrap">
{isUploaded && !selected && (
<IconSquare
href={uploadedFile?.signedUrl ?? uploadedFile?.url}
href={
uploadedFile
? fileViewUrl(uploadedFile.id, true)
: undefined
}
icon={<Download size={16} />}
/>
)}

View File

@@ -23,6 +23,7 @@ import type { Freight } from "@edr/types";
import { isViewable } from "@edr/ui-common";
import { IconSquare } from "../BookingDetailPage/components/Documents";
import { fileViewUrl } from "@/constants/apiConfig";
import { useFileViewer } from "@/hooks/useFileViewer";
import { OperationDatePicker } from "./OperationDatePicker";
import type { ClearanceFlowController } from "./useClearanceFlow";
@@ -169,16 +170,25 @@ export function ClearanceFlow({ booking, flow, footer }: ClearanceFlowProps) {
<Group gap={10} wrap="nowrap">
<StatusPill doc={doc} />
{doc.file &&
isViewable({ name: doc.file.name, url: doc.file.url }) && (
isViewable({
name: doc.file.name,
url: fileViewUrl(doc.file.id),
}) && (
<IconSquare
icon={<Eye size={15} />}
onClick={() =>
view({ name: doc.file!.name, url: doc.file!.url })
view({
name: doc.file!.name,
url: fileViewUrl(doc.file!.id),
})
}
/>
)}
{doc.file && (
<IconSquare href={doc.file.url} icon={<Download size={15} />} />
<IconSquare
href={fileViewUrl(doc.file.id, true)}
icon={<Download size={15} />}
/>
)}
{canUpload && doc.reviewStatus !== "APPROVED" && (
<FileButton
@@ -233,7 +243,10 @@ export function ClearanceFlow({ booking, flow, footer }: ClearanceFlowProps) {
{doc.label}
</Text>
{doc.file ? (
<IconSquare href={doc.file.url} icon={<Download size={15} />} />
<IconSquare
href={fileViewUrl(doc.file.id, true)}
icon={<Download size={15} />}
/>
) : (
<Text fz="12px" c="#9AA8B5">
Pending

View File

@@ -3,6 +3,7 @@ import { SmartFileInput } from "@edr/ui-common";
import { CheckCircle2, Download, FileText } from "lucide-react";
import { IconSquare } from "../BookingDetailPage/components/Documents";
import { fileViewUrl } from "@/constants/apiConfig";
import { labelForDocCode } from "./resubmitDocs";
import type { ResubmitFlowController } from "./useResubmitFlow";
@@ -69,7 +70,7 @@ export function ResubmitDocuments({ flow }: { flow: ResubmitFlowController }) {
</Text>
</Group>
<IconSquare
href={file.signedUrl ?? file.url}
href={fileViewUrl(file.id, true)}
icon={<Download size={15} />}
/>
</Group>