diff --git a/.changeset/afraid-points-admire.md b/.changeset/afraid-points-admire.md
new file mode 100644
index 00000000000..1ff6aa401bd
--- /dev/null
+++ b/.changeset/afraid-points-admire.md
@@ -0,0 +1,5 @@
+---
+"thirdweb": patch
+---
+
+Expose max() & min() util methods for bigints
diff --git a/apps/dashboard/src/contract-ui/tabs/listings/components/listing-stats.tsx b/apps/dashboard/src/contract-ui/tabs/listings/components/listing-stats.tsx
index 4ef827abc09..3af62cad99c 100644
--- a/apps/dashboard/src/contract-ui/tabs/listings/components/listing-stats.tsx
+++ b/apps/dashboard/src/contract-ui/tabs/listings/components/listing-stats.tsx
@@ -1,30 +1,22 @@
import { Skeleton, Stack, Stat, StatLabel, StatNumber } from "@chakra-ui/react";
-import {
- useDirectListingsCount,
- useEnglishAuctionsCount,
-} from "@thirdweb-dev/react";
-import type { MarketplaceV3 } from "@thirdweb-dev/sdk";
-import { BigNumber } from "ethers";
import { useMemo } from "react";
+import type { ThirdwebContract } from "thirdweb";
+import { totalAuctions, totalListings } from "thirdweb/extensions/marketplace";
+import { useReadContract } from "thirdweb/react";
import { Card } from "tw-components";
-interface ListingStatsV3Props {
- contract?: MarketplaceV3;
- features: string[];
-}
-
-const TotalListingsStat: React.FC<{ contract?: MarketplaceV3 }> = ({
+const TotalListingsStat: React.FC<{ contract: ThirdwebContract }> = ({
contract,
}) => {
- const directListingsQuery = useDirectListingsCount(contract);
- const englishAuctionsQuery = useEnglishAuctionsCount(contract);
-
- const totalListings = useMemo(
- () =>
- BigNumber.from(directListingsQuery?.data || 0).add(
- BigNumber.from(englishAuctionsQuery?.data || 0),
- ),
- [directListingsQuery?.data, englishAuctionsQuery?.data],
+ const directListingsQuery = useReadContract(totalListings, {
+ contract,
+ });
+ const englishAuctionsQuery = useReadContract(totalAuctions, {
+ contract,
+ });
+ const combinedListingCount = useMemo(
+ () => (directListingsQuery.data || 0n) + (englishAuctionsQuery.data || 0n),
+ [directListingsQuery.data, englishAuctionsQuery.data],
);
return (
@@ -32,56 +24,63 @@ const TotalListingsStat: React.FC<{ contract?: MarketplaceV3 }> = ({
Total Listings
- {totalListings.toString()}
+ {combinedListingCount.toString()}
);
};
-const DirectListingsStat: React.FC<{ contract?: MarketplaceV3 }> = ({
+const DirectListingsStat: React.FC<{ contract: ThirdwebContract }> = ({
contract,
}) => {
- const directListingsQuery = useDirectListingsCount(contract);
+ const directListingsQuery = useReadContract(totalListings, {
+ contract,
+ });
return (
Direct Listings
-
- {(directListingsQuery.data || 0).toString()}
+
+ {(directListingsQuery.data || 0n).toString()}
);
};
-const EnglishAuctionsStat: React.FC<{ contract?: MarketplaceV3 }> = ({
+const EnglishAuctionsStat: React.FC<{ contract: ThirdwebContract }> = ({
contract,
}) => {
- const englishAuctionsQuery = useEnglishAuctionsCount(contract);
+ const englishAuctionsQuery = useReadContract(totalAuctions, {
+ contract,
+ });
return (
English Auctions
-
- {(englishAuctionsQuery.data || 0).toString()}
+
+ {(englishAuctionsQuery.data || 0n).toString()}
);
};
+interface ListingStatsV3Props {
+ contract: ThirdwebContract;
+ hasDirectListings: boolean;
+ hasEnglishAuctions: boolean;
+}
+
export const ListingStatsV3: React.FC = ({
contract,
- features,
+ hasDirectListings,
+ hasEnglishAuctions,
}) => {
- const hasDirectListings = features.includes("DirectListings");
- const hasEnglishAuctions = features.includes("EnglishAuctions");
-
return (
- {hasDirectListings && hasEnglishAuctions && (
+ {hasDirectListings && hasEnglishAuctions && contract && (
)}
{hasDirectListings && }
diff --git a/apps/dashboard/src/contract-ui/tabs/overview/components/MarketplaceDetails.tsx b/apps/dashboard/src/contract-ui/tabs/overview/components/MarketplaceDetails.tsx
index 9ab5773e1f9..c75772186f2 100644
--- a/apps/dashboard/src/contract-ui/tabs/overview/components/MarketplaceDetails.tsx
+++ b/apps/dashboard/src/contract-ui/tabs/overview/components/MarketplaceDetails.tsx
@@ -7,14 +7,10 @@ import {
SkeletonText,
useBreakpointValue,
} from "@chakra-ui/react";
-import { useContract } from "@thirdweb-dev/react";
-import type { MarketplaceV3 } from "@thirdweb-dev/sdk";
import { ListingStatsV3 } from "contract-ui/tabs/listings/components/listing-stats";
import { useTabHref } from "contract-ui/utils";
-import { BigNumber } from "ethers";
-import { useV5DashboardChain } from "lib/v5-adapter";
import { useMemo } from "react";
-import { getContract } from "thirdweb";
+import type { ThirdwebContract } from "thirdweb";
import {
type DirectListing,
type EnglishAuction,
@@ -24,17 +20,10 @@ import {
totalListings,
} from "thirdweb/extensions/marketplace";
import { useReadContract } from "thirdweb/react";
-import {
- Badge,
- Card,
- Heading,
- Text,
- TrackedLink,
- type TrackedLinkProps,
-} from "tw-components";
+import { max } from "thirdweb/utils";
+import { Badge, Card, Heading, Text, TrackedLink } from "tw-components";
import { AddressCopyButton } from "tw-components/AddressCopyButton";
import { NFTMediaWithEmptyState } from "tw-components/nft-media";
-import { thirdwebClient } from "../../../../lib/thirdweb-client";
type ListingData =
| (Pick<
@@ -53,33 +42,19 @@ type ListingData =
});
type MarketplaceDetailsProps = {
- contractAddress: string;
- contractType: "marketplace" | "marketplace-v3";
+ contract: ThirdwebContract;
features: string[];
- trackingCategory: TrackedLinkProps["category"];
+ trackingCategory: string;
};
-interface MarketplaceDetailsVersionProps {
- contract: T;
- trackingCategory: TrackedLinkProps["category"];
- features: MarketplaceDetailsProps["features"];
-}
-
export const MarketplaceDetails: React.FC = ({
- contractAddress,
- contractType,
+ contract,
trackingCategory,
features,
}) => {
- const { contract } = useContract(contractAddress, contractType);
-
- if (contractType === "marketplace" && contract) {
- // no longer supported
- return null;
- }
return (
@@ -87,26 +62,25 @@ export const MarketplaceDetails: React.FC = ({
};
type ListingCardsSectionProps = {
- contract: MarketplaceV3;
- trackingCategory: TrackedLinkProps["category"];
+ contract: ThirdwebContract;
+ trackingCategory: string;
};
const DirectListingCards: React.FC = ({
trackingCategory,
- contract: v4Contract,
+ contract,
}) => {
- const chain = useV5DashboardChain(v4Contract.chainId);
- const contract = getContract({
- client: thirdwebClient,
- address: v4Contract.getAddress(),
- chain: chain,
- });
const directListingsHref = useTabHref("direct-listings");
const countQuery = useReadContract(totalListings, { contract });
const listingsQuery = useReadContract(getAllListings, {
contract,
count: 3n,
- start: Math.max(BigNumber.from(countQuery?.data || 3)?.toNumber() - 3, 0),
+ start: Math.max(
+ Number(
+ max((countQuery?.data || 3n) - 3n, BigInt(Number.MAX_SAFE_INTEGER)),
+ ),
+ 0,
+ ),
});
const listings = useMemo(
() =>
@@ -121,7 +95,7 @@ const DirectListingCards: React.FC = ({
[listingsQuery?.data],
);
- if (!countQuery.isLoading && BigNumber.from(countQuery.data || 0).eq(0)) {
+ if (!countQuery.isLoading && (countQuery.data || 0n) === 0n) {
return null;
}
if (!listingsQuery.isLoading && listings.length === 0) {
@@ -156,21 +130,19 @@ const DirectListingCards: React.FC = ({
const EnglishAuctionCards: React.FC = ({
trackingCategory,
- contract: v4Contract,
+ contract,
}) => {
- const chain = useV5DashboardChain(v4Contract.chainId);
- const contract = getContract({
- client: thirdwebClient,
- address: v4Contract.getAddress(),
- chain: chain,
- });
-
const englishAuctionsHref = useTabHref("english-auctions");
const countQuery = useReadContract(totalAuctions, { contract });
const auctionsQuery = useReadContract(getAllAuctions, {
contract,
count: 3n,
- start: Math.max(BigNumber.from(countQuery?.data || 3)?.toNumber() - 3, 0),
+ start: Math.max(
+ Number(
+ max((countQuery?.data || 3n) - 3n, BigInt(Number.MAX_SAFE_INTEGER)),
+ ),
+ 0,
+ ),
});
const auctions = useMemo(
() =>
@@ -185,7 +157,7 @@ const EnglishAuctionCards: React.FC = ({
[auctionsQuery?.data],
);
- if (!countQuery.isLoading && BigNumber.from(countQuery.data || 0).eq(0)) {
+ if (!countQuery.isLoading && (countQuery.data || 0n) === 0n) {
return null;
}
if (!auctionsQuery.isLoading && auctions.length === 0) {
@@ -218,16 +190,28 @@ const EnglishAuctionCards: React.FC = ({
);
};
-const MarketplaceV3Details: React.FC<
- MarketplaceDetailsVersionProps
-> = ({ contract, trackingCategory, features }) => {
+interface MarketplaceDetailsVersionProps {
+ contract: ThirdwebContract;
+ trackingCategory: string;
+ features: MarketplaceDetailsProps["features"];
+}
+
+const MarketplaceV3Details: React.FC = ({
+ contract,
+ trackingCategory,
+ features,
+}) => {
const hasDirectListings = features.includes("DirectListings");
const hasEnglishAuctions = features.includes("EnglishAuctions");
return (
Listings
-
+
{hasDirectListings && contract && (
ListingData = (idx) => ({
interface ListingCardsProps {
listings: ListingData[];
isLoading: boolean;
- trackingCategory: TrackedLinkProps["category"];
+ trackingCategory: string;
isMarketplaceV1?: boolean;
}
const ListingCards: React.FC = ({
diff --git a/apps/dashboard/src/contract-ui/tabs/overview/page.tsx b/apps/dashboard/src/contract-ui/tabs/overview/page.tsx
index c4056cb2681..bbd68d307c5 100644
--- a/apps/dashboard/src/contract-ui/tabs/overview/page.tsx
+++ b/apps/dashboard/src/contract-ui/tabs/overview/page.tsx
@@ -72,11 +72,11 @@ export const ContractOverviewPage: React.FC = ({
(contractTypeData === "marketplace" ||
["DirectListings", "EnglishAuctions"].some((type) =>
detectedFeatureNames.includes(type),
- )) && (
+ )) &&
+ contractV5 && (
)}
diff --git a/apps/dashboard/src/contract-ui/tabs/shared-components/marketplace-table.tsx b/apps/dashboard/src/contract-ui/tabs/shared-components/marketplace-table.tsx
index 8a9844ecbcf..65b0640bcfb 100644
--- a/apps/dashboard/src/contract-ui/tabs/shared-components/marketplace-table.tsx
+++ b/apps/dashboard/src/contract-ui/tabs/shared-components/marketplace-table.tsx
@@ -18,7 +18,6 @@ import {
} from "@chakra-ui/react";
import { MediaCell } from "components/contract-pages/table/table-columns/cells/media-cell";
import { ListingDrawer } from "contract-ui/tabs/shared-components/listing-drawer";
-import { BigNumber } from "ethers";
import {
type Dispatch,
type SetStateAction,
@@ -40,6 +39,7 @@ import type {
DirectListing,
EnglishAuction,
} from "thirdweb/extensions/marketplace";
+import { max } from "thirdweb/utils";
import { Button, Text } from "tw-components";
import { AddressCopyButton } from "tw-components/AddressCopyButton";
import { LISTING_STATUS } from "./types";
@@ -162,8 +162,10 @@ export const MarketplaceTable: React.FC = ({
manualPagination: true,
pageCount: Math.max(
Math.ceil(
- BigNumber.from(totalCountQuery.data || 0).toNumber() /
- queryParams.count,
+ Number(
+ // To avoid overflow issue
+ max(totalCountQuery.data || 0n, BigInt(Number.MAX_SAFE_INTEGER)),
+ ) / queryParams.count,
),
1,
),
diff --git a/packages/thirdweb/src/exports/utils.ts b/packages/thirdweb/src/exports/utils.ts
index 99b9c255cd6..6bb73c3d713 100644
--- a/packages/thirdweb/src/exports/utils.ts
+++ b/packages/thirdweb/src/exports/utils.ts
@@ -176,3 +176,8 @@ export {
export type { NFTMetadata, NFTInput } from "../utils/nft/parseNft.js";
export { parseAbiParams } from "../utils/contract/parse-abi-params.js";
+
+// ------------------------------------------------
+// bigint
+// ------------------------------------------------
+export { max, min } from "../utils/bigint.js";
diff --git a/packages/thirdweb/src/utils/bigint.ts b/packages/thirdweb/src/utils/bigint.ts
index eca3444ce69..4977d84036b 100644
--- a/packages/thirdweb/src/utils/bigint.ts
+++ b/packages/thirdweb/src/utils/bigint.ts
@@ -5,6 +5,7 @@ import { uint8ArrayToHex } from "./encoding/hex.js";
* @param a - The first BigInt value.
* @param b - The second BigInt value.
* @returns The smaller of the two BigInt values.
+ * @utils
* @example
* ```ts
* min(1n, 2n)
@@ -19,6 +20,7 @@ export function min(a: bigint, b: bigint) {
* @param a - The first BigInt value.
* @param b - The second BigInt value.
* @returns The larger of the two BigInt values.
+ * @utils
* @example
* ```ts
* max(1n, 2n)