aboutsummaryrefslogtreecommitdiff
path: root/jb-ui/src/components/Wallet.tsx
diff options
context:
space:
mode:
Diffstat (limited to 'jb-ui/src/components/Wallet.tsx')
-rw-r--r--jb-ui/src/components/Wallet.tsx866
1 files changed, 450 insertions, 416 deletions
diff --git a/jb-ui/src/components/Wallet.tsx b/jb-ui/src/components/Wallet.tsx
index e4fc694..819eff7 100644
--- a/jb-ui/src/components/Wallet.tsx
+++ b/jb-ui/src/components/Wallet.tsx
@@ -1,464 +1,498 @@
import {
- UserLedgerTransactionsResponse,
- UserLedgerTransactionsResponseTransactionsInner,
- WalletApi
+ UserLedgerTransactionsResponse,
+ UserLedgerTransactionsResponseTransactionsInner,
+ WalletApi,
} from "@/api_fsb";
+import { useGetMeQuery } from "@/models/authAPI";
import { useAppDispatch, useAppSelector } from "@/hooks";
-import { bpid, formatCentsToUSD, } from "@/lib/utils";
+import { bpid, formatCentsToUSD } from "@/lib/utils";
import {
- setTxPagination, setTxTotalItems, setTxTotalPages,
- setUserLedgerSummary,
- setUserLedgerTxs
+ setTxPagination,
+ setTxTotalItems,
+ setTxTotalPages,
+ setUserLedgerSummary,
+ setUserLedgerTxs,
} from "@/models/appSlice";
import {
- RowData, createColumnHelper, flexRender, getCoreRowModel,
- useReactTable
+ RowData,
+ createColumnHelper,
+ flexRender,
+ getCoreRowModel,
+ useReactTable,
} from "@tanstack/react-table";
import moment from "moment";
import { useEffect, useState } from "react";
-declare module '@tanstack/react-table' {
- interface ColumnMeta<TData extends RowData, TValue> {
- align?: 'left' | 'center' | 'right';
- }
+declare module "@tanstack/react-table" {
+ interface ColumnMeta<TData extends RowData, TValue> {
+ align?: "left" | "center" | "right";
+ }
}
// Function to calculate background color based on balance
const getBackgroundColor = (balance: number | undefined): string => {
- if (balance === undefined || balance === null) return 'bg-blue-600';
-
- if (balance > 0) {
- return 'bg-blue-600';
- } else if (balance <= -100) {
- return 'bg-red-600';
- } else {
- // Interpolate between blue and red for values between 0 and -100
- // progress goes from 0 (at balance = 0) to 1 (at balance = -100)
- const progress = Math.abs(balance) / 100;
-
- // Blue RGB: (37, 99, 235) - Tailwind blue-600
- // Red RGB: (220, 38, 38) - Tailwind red-600
- const r = Math.round(37 + (220 - 37) * progress);
- const g = Math.round(99 + (38 - 99) * progress);
- const b = Math.round(235 + (38 - 235) * progress);
-
- return `rgb(${r}, ${g}, ${b})`;
- }
+ if (balance === undefined || balance === null) return "bg-blue-600";
+
+ if (balance > 0) {
+ return "bg-blue-600";
+ } else if (balance <= -100) {
+ return "bg-red-600";
+ } else {
+ // Interpolate between blue and red for values between 0 and -100
+ // progress goes from 0 (at balance = 0) to 1 (at balance = -100)
+ const progress = Math.abs(balance) / 100;
+
+ // Blue RGB: (37, 99, 235) - Tailwind blue-600
+ // Red RGB: (220, 38, 38) - Tailwind red-600
+ const r = Math.round(37 + (220 - 37) * progress);
+ const g = Math.round(99 + (38 - 99) * progress);
+ const b = Math.round(235 + (38 - 235) * progress);
+
+ return `rgb(${r}, ${g}, ${b})`;
+ }
};
-
const WalletHeader = () => {
- const amount = useAppSelector(state => state.app.userWalletBalance)?.amount ?? 0
-
- const bgStyle = typeof getBackgroundColor(amount) === 'string' &&
- getBackgroundColor(amount).startsWith('bg-')
- ? {}
- : { backgroundColor: getBackgroundColor(amount) };
-
- const bgClass = typeof getBackgroundColor(amount) === 'string' &&
- getBackgroundColor(amount).startsWith('bg-')
- ? getBackgroundColor(amount)
- : '';
-
- return (
- <div className={`w-full py-1 px-1 text-white rounded ${bgClass}`}
- style={bgStyle}
- >
- <h2 className="text-xs font-semibold flex justify-between items-center">
- <span className="text-left">User Wallet:</span>
-
- {amount >= 0 ? (
- <span className='text-emerald-50'>
- {`${formatCentsToUSD(Math.abs(amount))}`}
- </span>
- ) : (
- <span className='text-rose-50'>
- {`(${formatCentsToUSD(Math.abs(amount))})`}
- </span>
- )}
-
- </h2>
- </div>
- )
+ const amount =
+ useAppSelector((state) => state.app.userDisplayedWalletBalance?.amount) ??
+ 0;
+
+ const amount_string =
+ useAppSelector(
+ (state) => state.app.userDisplayedWalletBalance?.amount_string,
+ ) ?? "$0.00";
+
+ const bgStyle =
+ typeof getBackgroundColor(amount) === "string" &&
+ getBackgroundColor(amount).startsWith("bg-")
+ ? {}
+ : { backgroundColor: getBackgroundColor(amount) };
+
+ const bgClass =
+ typeof getBackgroundColor(amount) === "string" &&
+ getBackgroundColor(amount).startsWith("bg-")
+ ? getBackgroundColor(amount)
+ : "";
+
+ return (
+ <div
+ className={`w-full py-1 px-1 text-white rounded ${bgClass}`}
+ style={bgStyle}
+ >
+ <h2 className="text-xs font-semibold flex justify-between items-center">
+ <span className="text-left">User Wallet:</span>
+
+ {amount >= 0 ? (
+ <span className="text-emerald-50">{`${amount_string}`}</span>
+ ) : (
+ <span className="text-rose-50">{`(${amount_string})`}</span>
+ )}
+ </h2>
+ </div>
+ );
};
const WalletSummary = () => {
- const summary = useAppSelector(state => state.app.userLedgerSummary)
-
- const survey_completes = summary?.bp_payment?.entry_count ?? 0
- const survey_completes_f = (survey_completes ?? 0).toLocaleString('en-US')
-
- const survey_adjustments = summary?.bp_adjustment?.entry_count ?? 0
- const survey_adjustments_f = (survey_adjustments ?? 0).toLocaleString('en-US')
-
- const min_payout: number = summary?.bp_payment?.min_amount ?? 0
- const max_payout: number = summary?.bp_payment?.max_amount ?? 0
- const adj_total: number = summary?.bp_adjustment?.total_amount ?? 0
- const user_payments_total: number = (summary?.user_payout_request?.total_amount ?? 0) * -1
-
- return (
- <div className="grid grid-cols-[auto_1fr] text-xs">
- <div className="label text-left">Completes:</div>
- <div className="value text-right">{survey_completes_f} surveys</div>
-
- <div className="label text-left">Avg Payouts:</div>
- <div className="value text-right">{formatCentsToUSD(min_payout)} – {formatCentsToUSD(max_payout)}</div>
-
- <div className="label text-left">Survey Adjustments:</div>
- <div className="value text-right">{survey_adjustments_f}</div>
-
- <div className="label text-left">Adjustment Amount:</div>
- <div className="value text-right">
- {adj_total >= 0 ? (
- <span className='text-emerald-300'>
- {`${formatCentsToUSD(adj_total)}`}
- </span>
- ) : (
- <span className='text-rose-300'>
- {`(${formatCentsToUSD(Math.abs(adj_total))})`}
- </span>
- )}
- </div>
-
- <div className="label text-left">User Payments:</div>
- <div className="value text-right">
- {user_payments_total >= 0 ? (
- <span className='text-emerald-300'>
- {`${formatCentsToUSD(user_payments_total)}`}
- </span>
- ) : (
- <span className='text-rose-300'>
- {`(${formatCentsToUSD(Math.abs(user_payments_total))})`}
- </span>
- )}
-
- </div>
- </div >
- )
+ const summary = useAppSelector((state) => state.app.userLedgerSummary);
+
+ const userWallet = useAppSelector((state) => state.app.userWallet);
+
+ userWallet;
+
+ const survey_completes = summary?.bp_payment?.entry_count ?? 0;
+ const survey_completes_f = (survey_completes ?? 0).toLocaleString("en-US");
+
+ const survey_adjustments = summary?.bp_adjustment?.entry_count ?? 0;
+ const survey_adjustments_f = (survey_adjustments ?? 0).toLocaleString(
+ "en-US",
+ );
+
+ const min_payout: number = summary?.bp_payment?.min_amount ?? 0;
+ const max_payout: number = summary?.bp_payment?.max_amount ?? 0;
+ const adj_total: number = summary?.bp_adjustment?.total_amount ?? 0;
+ const user_payments_total: number =
+ (summary?.user_payout_request?.total_amount ?? 0) * -1;
+
+ return (
+ <div className="grid grid-cols-[auto_1fr] text-xs">
+ <div className="label text-left">Completes:</div>
+ <div className="value text-right">{survey_completes_f} surveys</div>
+
+ <div className="label text-left">Avg Payouts:</div>
+ <div className="value text-right">
+ {formatCentsToUSD(min_payout)} – {formatCentsToUSD(max_payout)}
+ </div>
+
+ <div className="label text-left">Survey Adjustments:</div>
+ <div className="value text-right">{survey_adjustments_f}</div>
+
+ <div className="label text-left">Adjustment Amount:</div>
+ <div className="value text-right">
+ {adj_total >= 0 ? (
+ <span className="text-emerald-300">
+ {`${formatCentsToUSD(adj_total)}`}
+ </span>
+ ) : (
+ <span className="text-rose-300">
+ {`(${formatCentsToUSD(Math.abs(adj_total))})`}
+ </span>
+ )}
+ </div>
+
+ <div className="label text-left">User Payments:</div>
+ <div className="value text-right">
+ {user_payments_total >= 0 ? (
+ <span className="text-emerald-300">
+ {`${formatCentsToUSD(user_payments_total)}`}
+ </span>
+ ) : (
+ <span className="text-rose-300">
+ {`(${formatCentsToUSD(Math.abs(user_payments_total))})`}
+ </span>
+ )}
+ </div>
+ </div>
+ );
};
const WalletTransactionsHeader = () => {
- const tx_cnt = useAppSelector(state => state.app.txTotalItems)
- const txt_cnt_f = (tx_cnt ?? 0).toLocaleString('en-US')
-
- const [showTx, setShowTx] = useState(false);
-
- return (
- <div className="w-full bg-blue-600 text-white rounded text-left">
- <div className="hover:cursor-pointer hover:bg-blue-700 transition-colors duration-200"
- onClick={() => setShowTx(!showTx)}>
-
- <h2 className="text-xs font-semibold rounded flex justify-between
+ const tx_cnt = useAppSelector((state) => state.app.txTotalItems);
+ const txt_cnt_f = (tx_cnt ?? 0).toLocaleString("en-US");
+
+ const [showTx, setShowTx] = useState(false);
+
+ return (
+ <div className="w-full bg-blue-600 text-white rounded text-left">
+ <div
+ className="hover:cursor-pointer hover:bg-blue-700 transition-colors duration-200"
+ onClick={() => setShowTx(!showTx)}
+ >
+ <h2
+ className="text-xs font-semibold rounded flex justify-between
py-1 px-1"
- onClick={() => setShowTx(!showTx)}
- >
- <span>Total Transactions:</span> <span>{txt_cnt_f}</span>
- </h2>
-
- <h4 className="text-[10px] text-center italic text-blue-300 py-1"
- onClick={() => setShowTx(!showTx)}
- >
- (Click to {showTx ? 'hide' : 'show'})
- </h4>
-
- </div>
-
- {showTx && (
- <>
- <WalletTransactions />
- </>
- )}
+ onClick={() => setShowTx(!showTx)}
+ >
+ <span>Total Transactions:</span> <span>{txt_cnt_f}</span>
+ </h2>
- </div>
- )
+ <h4
+ className="text-[10px] text-center italic text-blue-300 py-1"
+ onClick={() => setShowTx(!showTx)}
+ >
+ (Click to {showTx ? "hide" : "show"})
+ </h4>
+ </div>
+
+ {showTx && (
+ <>
+ <WalletTransactions />
+ </>
+ )}
+ </div>
+ );
};
-
const WalletTransactions = () => {
- const dispatch = useAppDispatch()
- const bpuid = useAppSelector(state => state.app.bpuid)
- const userLedgerTxs = useAppSelector(state => state.app.userLedgerTxs);
-
- const txPagination = useAppSelector(state => state.app.txPagination);
- const txTotalPages = useAppSelector(state => state.app.txTotalPages);
-
- useEffect(() => {
- if (!bpuid) return;
-
- new WalletApi().getUserTransactionHistoryProductIdTransactionHistoryGet(
- bpid, // productId
- bpuid, // bpuid
- undefined, // createdAfter
- undefined, // createdBefore
- "-created", // orderBy
- txPagination.pageIndex + 1, // page
- txPagination.pageSize // pageSize
- ).then(res => {
- const response = res.data as UserLedgerTransactionsResponse;
- console.log("Wallet: fetched user ledger", response);
- dispatch(setUserLedgerSummary(response.summary));
-
- dispatch(setUserLedgerTxs(response.transactions ?? []))
- dispatch(setTxTotalItems(response.total!))
- dispatch(setTxTotalPages(response.pages!))
- });
-
- }, [bpuid, txPagination.pageIndex, txPagination.pageSize]);
-
- const columnHelper = createColumnHelper<UserLedgerTransactionsResponseTransactionsInner>()
- const columns = [
- columnHelper.accessor('created', {
- header: () => 'Date',
- cell: (info) => moment(info.getValue()).format('M/D/YY H:mm'),
- size: 110,
- meta: {
- align: 'left'
- }
- }),
- columnHelper.accessor('description', {
- header: () => 'Type',
- cell: props => {
- const desc = props.getValue();
- switch (desc) {
- case 'Task Complete':
- return 'Survey 🎉';
- case 'Task Adjustment':
- return 'Reject ⚠️';
- case 'Compensation Bonus':
- return 'Bonus 🎁';
- case 'HIT Bonus':
- return 'Bonus';
- case 'HIT Reward':
- return 'Assignment';
- default:
- return desc;
- }
- },
- size: 80,
- meta: {
- align: 'left'
- }
- }),
- columnHelper.accessor('amount', {
- header: () => 'Amount',
- cell: (props) => {
- const val = props.renderValue() as number;
- const isPositive = val >= 0;
- const emoji = isPositive ? "⬆\uFE0E" : "⬇\uFE0E";
- const colorClass = isPositive ? 'font-variant-emoji-text text-emerald-300' : 'font-variant-emoji-text text-rose-300';
+ const dispatch = useAppDispatch();
+ const { data: user } = useGetMeQuery();
+ const userLedgerTxs = useAppSelector((state) => state.app.userLedgerTxs);
+
+ const txPagination = useAppSelector((state) => state.app.txPagination);
+ const txTotalPages = useAppSelector((state) => state.app.txTotalPages);
+
+ useEffect(() => {
+ if (!user?.product_user_id) return;
+
+ new WalletApi()
+ .getUserTransactionHistoryProductIdTransactionHistoryGet(
+ bpid, // productId
+ user.product_user_id,
+ undefined, // createdAfter
+ undefined, // createdBefore
+ "-created", // orderBy
+ txPagination.pageIndex + 1, // page
+ txPagination.pageSize, // pageSize
+ )
+ .then((res) => {
+ const response = res.data as UserLedgerTransactionsResponse;
+ console.log("Wallet: fetched user ledger", response);
+ dispatch(setUserLedgerSummary(response.summary));
+
+ dispatch(setUserLedgerTxs(response.transactions ?? []));
+ dispatch(setTxTotalItems(response.total!));
+ dispatch(setTxTotalPages(response.pages!));
+ });
+ }, [user?.product_user_id, txPagination.pageIndex, txPagination.pageSize]);
+
+ const columnHelper =
+ createColumnHelper<UserLedgerTransactionsResponseTransactionsInner>();
+ const columns = [
+ columnHelper.accessor("created", {
+ header: () => "Date",
+ cell: (info) => moment(info.getValue()).format("M/D/YY H:mm"),
+ size: 110,
+ meta: {
+ align: "left",
+ },
+ }),
+ columnHelper.accessor("description", {
+ header: () => "Type",
+ cell: (props) => {
+ const desc = props.getValue();
+ switch (desc) {
+ case "Task Complete":
+ return "Survey 🎉";
+ case "Task Adjustment":
+ return "Reject ⚠️";
+ case "Compensation Bonus":
+ return "Bonus 🎁";
+ case "HIT Bonus":
+ return "Bonus";
+ case "HIT Reward":
+ return "Assignment";
+ default:
+ return desc;
+ }
+ },
+ size: 80,
+ meta: {
+ align: "left",
+ },
+ }),
+ columnHelper.accessor("amount", {
+ header: () => "Amount",
+ cell: (props) => {
+ const val = props.renderValue() as number;
+ const isPositive = val >= 0;
+ const emoji = isPositive ? "⬆\uFE0E" : "⬇\uFE0E";
+ const colorClass = isPositive
+ ? "font-variant-emoji-text text-emerald-300"
+ : "font-variant-emoji-text text-rose-300";
+
+ return (
+ <span className={colorClass}>
+ {`${emoji} ${formatCentsToUSD(Math.abs(val))}`}
+ </span>
+ );
+ },
+ size: 70,
+ meta: {
+ align: "center",
+ },
+ }),
+ columnHelper.accessor("balance_after", {
+ header: () => "Balance",
+ cell: (props) => {
+ const val = props.renderValue() as number;
+ const isPositive = val >= 0;
+ const colorClass = isPositive ? "text-emerald-300" : "text-rose-300";
+
+ return (
+ <>
+ {isPositive ? (
+ <span className={colorClass}>
+ {`${formatCentsToUSD(Math.abs(val))}`}
+ </span>
+ ) : (
+ <span className={colorClass}>
+ {`(${formatCentsToUSD(Math.abs(val))})`}
+ </span>
+ )}
+ </>
+ );
+ },
+ size: 70,
+ meta: {
+ align: "center",
+ },
+ }),
+ ];
+
+ const table = useReactTable({
+ data: userLedgerTxs,
+ columns: columns,
+ getCoreRowModel: getCoreRowModel(),
+ manualPagination: true,
+ pageCount: txTotalPages,
+ onPaginationChange: (updater) => {
+ dispatch(
+ setTxPagination(
+ typeof updater === "function" ? updater(txPagination) : updater,
+ ),
+ );
+ },
+ state: {
+ pagination: txPagination,
+ },
+ });
+
+ return (
+ <div className="w-full border-t-1 border-blue-800 p-2">
+ <table className="text-xs table-fixed border-collapse">
+ <thead className="font-bold">
+ {table.getHeaderGroups().map((headerGroup) => (
+ <tr key={headerGroup.id}>
+ {headerGroup.headers.map((header) => {
+ const align = header.column.columnDef.meta?.align || "left";
+ const alignClass =
+ align === "center"
+ ? "text-center"
+ : align === "right"
+ ? "text-right"
+ : "text-left";
return (
- <span className={colorClass}>
- {`${emoji} ${formatCentsToUSD(Math.abs(val))}`}
- </span>
- )
- },
- size: 70,
- meta: {
- align: 'center'
- }
- }),
- columnHelper.accessor('balance_after', {
- header: () => 'Balance',
- cell: (props) => {
- const val = props.renderValue() as number;
- const isPositive = val >= 0;
- const colorClass = isPositive ? 'text-emerald-300' : 'text-rose-300';
+ <th
+ key={header.id}
+ className={`p-0 m-0 ${alignClass}`}
+ style={{
+ width: `${header.column.getSize()}px`,
+ }}
+ >
+ {flexRender(
+ header.column.columnDef.header,
+ header.getContext(),
+ )}
+ </th>
+ );
+ })}
+ </tr>
+ ))}
+ </thead>
+ <tbody>
+ {table.getRowModel().rows.map((row) => (
+ <tr key={row.id}>
+ {row.getVisibleCells().map((cell) => {
+ const align = cell.column.columnDef.meta?.align || "left";
+ const alignClass =
+ align === "center"
+ ? "text-center"
+ : align === "right"
+ ? "text-right"
+ : "text-left";
return (
- <>
- {isPositive ? (
- <span className={colorClass}>
- {`${formatCentsToUSD(Math.abs(val))}`}
- </span>
- ) : (
- <span className={colorClass}>
- {`(${formatCentsToUSD(Math.abs(val))})`}
- </span>
- )}
- </>
- )
- },
- size: 70,
- meta: {
- align: 'center'
- }
- }),
- ]
-
- const table = useReactTable({
- 'data': userLedgerTxs,
- 'columns': columns,
- getCoreRowModel: getCoreRowModel(),
- manualPagination: true,
- pageCount: txTotalPages,
- onPaginationChange: (updater) => {
- dispatch(setTxPagination(
- typeof updater === 'function' ? updater(txPagination) : updater
- ));
- },
- state: {
- pagination: txPagination,
- },
- });
-
- return (
- <div className="w-full border-t-1 border-blue-800 p-2">
- <table className="text-xs table-fixed border-collapse">
- <thead className="font-bold">
- {table.getHeaderGroups().map((headerGroup) => (
-
- <tr key={headerGroup.id}>
- {headerGroup.headers.map((header) => {
- const align = header.column.columnDef.meta?.align || 'left';
- const alignClass = align === 'center' ? 'text-center' : align === 'right' ? 'text-right' : 'text-left';
-
- return (
- <th
- key={header.id}
- className={`p-0 m-0 ${alignClass}`}
- style={{
- width: `${header.column.getSize()}px`,
- }}
- >
- {flexRender(
- header.column.columnDef.header,
- header.getContext(),
- )}
- </th>
- )
- })}
- </tr>
- ))}
- </thead>
- <tbody>
- {table.getRowModel().rows.map((row) => (
- <tr key={row.id}>
- {row.getVisibleCells().map((cell) => {
- const align = cell.column.columnDef.meta?.align || 'left';
- const alignClass = align === 'center' ? 'text-center' :
- align === 'right' ? 'text-right' : 'text-left';
-
- return (
- <td key={cell.id}
- className={`p-0 ${alignClass}`}
- style={{
- width: `${cell.column.getSize()}px`,
- }}
- >
- {flexRender(cell.column.columnDef.cell, cell.getContext())}
- </td>
- )
- })}
- </tr>
- ))}
- </tbody>
-
- <tfoot>
- <tr>
- <td colSpan={columns.length} className="p-2">
- <div className="flex items-center justify-between text-xs">
-
- {/* Page info */}
- <div className="text-blue-50">
- Page {table.getState().pagination.pageIndex + 1} of{' '}
- {table.getPageCount()}
- </div>
-
- {/* Navigation buttons */}
- <div className="flex gap-8 text-xs">
- <button
- onClick={() => table.previousPage()}
- disabled={!table.getCanPreviousPage()}
- className="px-3 py-1 border border-blue-200 rounded
+ <td
+ key={cell.id}
+ className={`p-0 ${alignClass}`}
+ style={{
+ width: `${cell.column.getSize()}px`,
+ }}
+ >
+ {flexRender(cell.column.columnDef.cell, cell.getContext())}
+ </td>
+ );
+ })}
+ </tr>
+ ))}
+ </tbody>
+
+ <tfoot>
+ <tr>
+ <td colSpan={columns.length} className="p-2">
+ <div className="flex items-center justify-between text-xs">
+ {/* Page info */}
+ <div className="text-blue-50">
+ Page {table.getState().pagination.pageIndex + 1} of{" "}
+ {table.getPageCount()}
+ </div>
+
+ {/* Navigation buttons */}
+ <div className="flex gap-8 text-xs">
+ <button
+ onClick={() => table.previousPage()}
+ disabled={!table.getCanPreviousPage()}
+ className="px-3 py-1 border border-blue-200 rounded
font-variant-emoji-text
hover:cursor-pointer hover:bg-blue-700
disabled:opacity-50 disabled:cursor-not-allowed"
- >
- {'⬅\uFE0E'}
- </button>
- <button
- onClick={() => table.nextPage()}
- disabled={!table.getCanNextPage()}
- className="px-3 py-1 border border-blue-200 rounded
+ >
+ {"⬅\uFE0E"}
+ </button>
+ <button
+ onClick={() => table.nextPage()}
+ disabled={!table.getCanNextPage()}
+ className="px-3 py-1 border border-blue-200 rounded
font-variant-emoji-text
hover:cursor-pointer hover:bg-blue-700
disabled:opacity-50 disabled:cursor-not-allowed"
- >
- {'⮕\uFE0E'}
- </button>
- </div>
-
- {/* Page size selector */}
- <select
- value={table.getState().pagination.pageSize}
- onChange={e => table.setPageSize(Number(e.target.value))}
- className="px-2 py-1 border border-blue-200 rounded
+ >
+ {"⮕\uFE0E"}
+ </button>
+ </div>
+
+ {/* Page size selector */}
+ <select
+ value={table.getState().pagination.pageSize}
+ onChange={(e) => table.setPageSize(Number(e.target.value))}
+ className="px-2 py-1 border border-blue-200 rounded
hover:cursor-pointer hover:bg-blue-700"
- >
- {[10, 20, 30, 40].map(pageSize => (
- <option key={pageSize} value={pageSize}>
- Show {pageSize}
- </option>
- ))}
- </select>
- </div>
- </td>
- </tr>
- </tfoot>
-
- </table>
- </div>
- )
+ >
+ {[10, 20, 30, 40].map((pageSize) => (
+ <option key={pageSize} value={pageSize}>
+ Show {pageSize}
+ </option>
+ ))}
+ </select>
+ </div>
+ </td>
+ </tr>
+ </tfoot>
+ </table>
+ </div>
+ );
};
-
const Wallet = () => {
- const dispatch = useAppDispatch()
- const bpuid = useAppSelector(state => state.app.bpuid)
- const pagination = useAppSelector(state => state.app.txPagination);
-
- useEffect(() => {
- if (!bpuid) return;
-
- new WalletApi().getUserTransactionHistoryProductIdTransactionHistoryGet(
- bpid, // productId
- bpuid, // bpuid
- undefined, // createdAfter
- undefined, // createdBefore
- "-created", // orderBy
- pagination.pageIndex + 1, // page
- pagination.pageSize // pageSize
- ).then(res => {
- const response = res.data as UserLedgerTransactionsResponse;
- dispatch(setUserLedgerSummary(response.summary));
- dispatch(setUserLedgerTxs(response.transactions ?? []))
-
- dispatch(setTxPagination({
- pageIndex: (response.page ?? 1) - 1,
- pageSize: response.size ?? 10,
- }))
- dispatch(setTxTotalItems(response.total ?? 0))
- dispatch(setTxTotalPages(response.pages ?? 9))
- });
-
- }, [bpuid])
-
- if (!bpuid) return null;
-
- return (
- <div className="fixed top-2 left-2 p-2 rounded
+ const dispatch = useAppDispatch();
+ const pagination = useAppSelector((state) => state.app.txPagination);
+ const { data: user } = useGetMeQuery();
+
+ useEffect(() => {
+ if (!user?.product_user_id) return;
+
+ new WalletApi()
+ .getUserTransactionHistoryProductIdTransactionHistoryGet(
+ bpid, // productId
+ user.product_user_id,
+ undefined, // createdAfter
+ undefined, // createdBefore
+ "-created", // orderBy
+ pagination.pageIndex + 1, // page
+ pagination.pageSize, // pageSize
+ )
+ .then((res) => {
+ const response = res.data as UserLedgerTransactionsResponse;
+ dispatch(setUserLedgerSummary(response.summary));
+ dispatch(setUserLedgerTxs(response.transactions ?? []));
+
+ dispatch(
+ setTxPagination({
+ pageIndex: (response.page ?? 1) - 1,
+ pageSize: response.size ?? 10,
+ }),
+ );
+ dispatch(setTxTotalItems(response.total ?? 0));
+ dispatch(setTxTotalPages(response.pages ?? 9));
+ });
+ }, [user?.product_user_id]);
+
+ if (!user?.product_user_id) return null;
+
+ return (
+ <div
+ className="fixed top-2 left-2 p-2 rounded
bg-blue-500 text-white shadow-lg z-50
font-mono
max-h-[calc(100vh-2.5rem)] overflow-y-auto
max-w-[96vw]
- ">
- <WalletHeader />
- <WalletSummary />
- <WalletTransactionsHeader />
- </div>
- )
+ "
+ >
+ <WalletHeader />
+ <WalletSummary />
+ <WalletTransactionsHeader />
+ </div>
+ );
};
-
-export default Wallet; \ No newline at end of file
+export default Wallet;