This commit is contained in:
Samandar Turgunboyev
2025-11-02 21:49:06 +05:00
parent 68f371db08
commit 9803edc478
7 changed files with 97 additions and 58 deletions

View File

@@ -192,24 +192,22 @@ export interface History {
total_pages: number;
page_size: number;
current_page: number;
results: [
{
results: {
id: number;
travel_agency: {
custom_id: string;
name: string;
email: string;
phone: string;
};
amount: number;
note: string;
accountant: {
id: number;
travel_agency: {
custom_id: string;
name: string;
email: string;
phone: string;
};
amount: number;
note: string;
accountant: {
id: number;
first_name: string;
last_name: string;
role: string;
};
},
];
first_name: string;
last_name: string;
role: string;
};
}[];
};
}

View File

@@ -392,8 +392,11 @@ export default function FinanceDetailUser() {
<div className="flex gap-2">
{companion.participant_pasport_image.map(
(img) => (
<div
<a
key={index}
href={img.image}
target="_blank"
rel="noopener noreferrer"
className="w-20 h-20 rounded-lg bg-slate-700/50 flex items-center justify-center overflow-hidden border border-slate-600/50"
>
<img
@@ -401,7 +404,7 @@ export default function FinanceDetailUser() {
src={img.image}
className="w-full h-full"
/>
</div>
</a>
),
)}
</div>

View File

@@ -21,9 +21,16 @@ export function PaymentHistory() {
const { t } = useTranslation();
const [page, setPage] = useState(1);
const { data, isLoading, isError } = useQuery({
const {
data: history,
isLoading,
isError,
} = useQuery({
queryKey: ["payment-history", page],
queryFn: () => getPaymentHistory({ page, page_size: 10 }),
select(data) {
return data.data;
},
});
if (isLoading)
@@ -33,15 +40,13 @@ export function PaymentHistory() {
</div>
);
if (isError || !data)
if (isError || !history)
return (
<Card className="p-6 text-center">
<p className="text-red-500">Xatolik yuz berdi. Qayta urinib koring.</p>
</Card>
);
const history = data.data;
return (
<Card className="bg-gray-900 text-white">
<CardHeader>
@@ -60,7 +65,7 @@ export function PaymentHistory() {
</TableRow>
</TableHeader>
<TableBody>
{history.data.results.map((item) => (
{history?.data.results.map((item) => (
<TableRow key={item.id}>
<TableCell>{item.travel_agency.custom_id}</TableCell>
<TableCell>{item.travel_agency.name}</TableCell>
@@ -68,7 +73,9 @@ export function PaymentHistory() {
<TableCell>{formatPrice(item.amount, true)}</TableCell>
<TableCell>{item.note || "-"}</TableCell>
<TableCell>
{item.accountant.first_name} {item.accountant.last_name}
{item.accountant?.first_name || item.accountant?.last_name
? `${item.accountant?.first_name ?? ""} ${item.accountant?.last_name ?? ""}`
: "-"}
</TableCell>
</TableRow>
))}
@@ -78,14 +85,14 @@ export function PaymentHistory() {
{/* Pagination */}
<div className="flex justify-between items-center mt-6">
<p className="text-sm text-gray-400">
{t("Sahifa")} {history.data.current_page} /{" "}
{history.data.total_pages}
{t("Sahifa")} {history?.data.current_page} /{" "}
{history?.data.total_pages}
</p>
<div className="flex gap-2">
<Button
variant="outline"
size="sm"
disabled={!history.data.links.previous}
disabled={!history?.data.links.previous}
onClick={() => setPage((p) => Math.max(p - 1, 1))}
>
<ChevronLeft className="size-6" />
@@ -93,10 +100,10 @@ export function PaymentHistory() {
<Button
variant="outline"
size="sm"
disabled={!history.data.links.next}
disabled={!history?.data.links.next}
onClick={() =>
setPage((p) =>
Math.min(p + 1, history.data.total_pages || p + 1),
Math.min(p + 1, history?.data.total_pages || p + 1),
)
}
>

View File

@@ -245,28 +245,49 @@ const SupportAgency = () => {
{selected.travel_agency_documents &&
selected.travel_agency_documents.length > 0 ? (
<div className="grid grid-cols-2 sm:grid-cols-3 gap-3">
{selected.travel_agency_documents.map((doc, i) => (
<a
key={i}
href={doc.file}
target="_blank"
rel="noopener noreferrer"
className="group relative aspect-square border-2 border-gray-200 rounded-lg overflow-hidden hover:border-blue-500 transition"
>
<img
src={doc.file}
alt={`Hujjat ${i + 1}`}
className="w-full h-full object-cover"
/>
<div className="absolute inset-0 bg-black/0 group-hover:bg-black/10 transition flex items-end">
<div className="w-full bg-gradient-to-t from-black/70 to-transparent p-2">
<span className="text-white text-xs font-medium">
{t("Hujjat")} {i + 1}
</span>
{selected.travel_agency_documents.map((doc, i) => {
const isImage = /\.(jpg|jpeg|png|gif|webp)$/i.test(
doc.file,
);
const fileName = doc.file.split("/").pop();
return (
<a
key={i}
href={doc.file}
target="_blank"
rel="noopener noreferrer"
className="group relative aspect-square border-2 border-gray-200 rounded-lg overflow-hidden hover:border-blue-500 transition"
>
{isImage ? (
<img
src={doc.file}
alt={`Hujjat ${i + 1}`}
className="w-full h-full object-cover"
/>
) : (
<div className="w-full h-full flex flex-col items-center justify-center bg-gray-800 text-gray-300">
{/* <img
src="/icons/document-placeholder.png"
alt="Document icon"
className="w-10 h-10 mb-2 opacity-70"
/> */}
<span className="text-xl text-center truncate px-2">
{fileName}
</span>
</div>
)}
<div className="absolute inset-0 bg-black/0 group-hover:bg-black/10 transition flex items-end">
<div className="w-full bg-gradient-to-t from-black/70 to-transparent p-2">
<span className="text-white text-xs font-medium">
{t("Hujjat")} {i + 1}
</span>
</div>
</div>
</div>
</a>
))}
</a>
);
})}
</div>
) : (
<div className="text-gray-500">{t("Hujjat topilmadi")}</div>

View File

@@ -442,7 +442,9 @@ export interface GetDetailTours {
];
tariff: [
{
tariff: number;
tariff: {
name: string;
};
price: number;
},
];

View File

@@ -278,9 +278,14 @@ export default function TourDetailPage() {
<CheckCircle2 className="w-5 h-5 text-blue-400 mt-1" />
<div>
<p className="text-sm text-gray-400">{t("Tarif")}</p>
<p className="font-semibold text-white capitalize">
{tour.tariff[0]?.tariff}
</p>
{tour.tariff.map((e) => (
<p
key={e.tariff.name}
className="font-semibold text-white capitalize"
>
{e.tariff.name}
</p>
))}
</div>
</div>
</div>

View File

@@ -471,8 +471,11 @@ const UserDetail = () => {
<div className="flex gap-2">
{companion.participant_pasport_image.map(
(img) => (
<div
<a
key={img.id}
href={img.image}
target="_blank"
rel="noopener noreferrer"
className="w-20 h-20 rounded-lg bg-slate-700/50 flex items-center justify-center overflow-hidden border border-slate-600/50"
>
<img
@@ -480,7 +483,7 @@ const UserDetail = () => {
src={img.image}
className="w-full h-full"
/>
</div>
</a>
),
)}
</div>