Skip to content

Commit

Permalink
🤺 Persist bid place in BidsProvider (#22)
Browse files Browse the repository at this point in the history
  • Loading branch information
b-tarczynski authored Apr 19, 2024
1 parent ec1142d commit 543c5ba
Show file tree
Hide file tree
Showing 9 changed files with 56 additions and 74 deletions.
4 changes: 2 additions & 2 deletions packages/frontend/src/blockchain/hooks/useUserBid.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import { useAccount } from 'wagmi'
import { useBids } from '@/providers/BidsProvider'
import { useMemo } from 'react'
import { BidWithPlace } from '@/types/bid'
import { Bid } from '@/types/bid'

export const useUserBid = (): BidWithPlace | undefined => {
export const useUserBid = (): Bid | undefined => {
const { address } = useAccount()
const { bidList } = useBids()

Expand Down
4 changes: 2 additions & 2 deletions packages/frontend/src/components/bids/BidsListEntry.tsx
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
import { AddressColumn, BidColumn, PlaceColumn } from '@/components/bids/BidsColumns'
import styled, { css } from 'styled-components'
import { BidWithPlace } from '@/types/bid'
import { Bid } from '@/types/bid'
import { Colors } from '@/styles/colors'
import { formatEther, Hex } from 'viem'
import { useExplorerAddressLink } from '@/blockchain/hooks/useExplorerAddressLink'

interface Props {
bid: BidWithPlace
bid: Bid
isUser?: boolean
view?: 'short' | 'full'
}
Expand Down
6 changes: 2 additions & 4 deletions packages/frontend/src/components/bids/allBids/AllBidsList.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -36,10 +36,8 @@ export const AllBidsList = ({ search, auctionWinnersCount, raffleWinnersCount }:
) : (
<>
<BidsListHeaders />
{bids.auction.length !== 0 && <BidsSubList bids={bids.auction} placeOffset={0} title="AUCTION" />}
{bids.raffle.length !== 0 && (
<BidsSubList bids={bids.raffle} placeOffset={bids.auction.length} title="RAFFLE" />
)}
{bids.auction.length !== 0 && <BidsSubList bids={bids.auction} title="AUCTION" />}
{bids.raffle.length !== 0 && <BidsSubList bids={bids.raffle} title="RAFFLE" />}
</>
)}
</>
Expand Down
12 changes: 3 additions & 9 deletions packages/frontend/src/components/bids/allBids/BidsSubList.tsx
Original file line number Diff line number Diff line change
@@ -1,17 +1,16 @@
import styled from 'styled-components'
import { Bid, bidToBidWithPlace } from '@/types/bid'
import { Bid } from '@/types/bid'
import { Colors } from '@/styles/colors'
import { BidsListContainer } from '@/components/bids/BidsListContainer'
import { BidsListEntry } from '@/components/bids/BidsListEntry'
import { useAccount } from 'wagmi'

interface Props {
bids: Bid[]
placeOffset: number
title: string
}

export const BidsSubList = ({ bids, placeOffset, title }: Props) => {
export const BidsSubList = ({ bids, title }: Props) => {
const { address } = useAccount()

return (
Expand All @@ -21,12 +20,7 @@ export const BidsSubList = ({ bids, placeOffset, title }: Props) => {
</TitleBanner>
<BidsListContainer>
{bids.map((bid, index) => (
<BidsListEntry
key={bid.bidderId}
bid={bidToBidWithPlace(bid, placeOffset + index)}
isUser={address === bid.address}
view="full"
/>
<BidsListEntry key={bid.bidderId} bid={bid} isUser={address === bid.address} view="full" />
))}
</BidsListContainer>
</>
Expand Down
27 changes: 8 additions & 19 deletions packages/frontend/src/components/bids/allBids/SettledBidsList.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { useMemo } from 'react'
import { Bid, bidToBidWithPlace } from '@/types/bid'
import { Bid } from '@/types/bid'
import { useBids } from '@/providers/BidsProvider'
import { useAuctionWinners } from '@/blockchain/hooks/useAuctionWinners'
import { GoldenTicketWinner } from '@/components/bids/allBids/GoldenTicketWinner'
Expand Down Expand Up @@ -39,19 +39,9 @@ export const SettledBidsList = ({ search }: SettledBidsListProps) => {
<>
{filteredBids.goldenTicket && <GoldenTicketWinner bidderAddress={filteredBids.goldenTicket.address} />}
<BidsListHeaders />
{filteredBids.auction.length !== 0 && (
<BidsSubList bids={filteredBids.auction} placeOffset={0} title="AUCTION" />
)}
{filteredBids.raffle.length !== 0 && (
<BidsSubList bids={filteredBids.raffle} placeOffset={filteredBids.auction.length} title="RAFFLE" />
)}
{filteredBids.others.length !== 0 && (
<BidsSubList
bids={filteredBids.others}
placeOffset={filteredBids.raffle.length + filteredBids.auction.length}
title="OTHERS"
/>
)}
{filteredBids.auction.length !== 0 && <BidsSubList bids={filteredBids.auction} title="AUCTION" />}
{filteredBids.raffle.length !== 0 && <BidsSubList bids={filteredBids.raffle} title="RAFFLE" />}
{filteredBids.others.length !== 0 && <BidsSubList bids={filteredBids.others} title="OTHERS" />}
</>
)}
</>
Expand All @@ -75,20 +65,19 @@ function divideBids(

bids.forEach((bid, index) => {
const bidderID = bid.bidderId
const bidWithPlace = bidToBidWithPlace(bid, index)
if (auctionWinners.find((winnerId) => bid.bidderId === winnerId)) {
settledBids.auction.push(bidWithPlace)
settledBids.auction.push(bid)
return
}
if (bidderID === raffleWinners[0]) {
settledBids.goldenTicket = bidWithPlace
settledBids.goldenTicket = bid
return
}
if (raffleWinners.find((winnerId) => bid.bidderId === winnerId)) {
settledBids.raffle.push(bidWithPlace)
settledBids.raffle.push(bid)
return
}
settledBids.others.push(bidWithPlace)
settledBids.others.push(bid)
})
return settledBids
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { useMemo } from 'react'
import styled from 'styled-components'
import { Bid, bidToBidWithPlace, BidWithPlace } from '@/types/bid'
import { Bid } from '@/types/bid'
import { useUserBid } from '@/blockchain/hooks/useUserBid'
import { Colors } from '@/styles/colors'
import { useReadAuctionParams } from '@/blockchain/hooks/useReadAuctionParams'
Expand Down Expand Up @@ -51,7 +51,7 @@ export const BidsShortList = () => {
}

function isAuctionParticipant(
userBid: BidWithPlace | undefined,
userBid: Bid | undefined,
auctionWinnersCount: number | undefined,
raffleWinnersCount: number | undefined,
bidsLength: number,
Expand All @@ -63,30 +63,26 @@ function isAuctionParticipant(
return userBid.place <= firstRaffleBidIndex
}

function selectBids(
auctionWinnersCount: number | undefined,
bidList: Bid[],
userBid: BidWithPlace | undefined,
): BidWithPlace[] {
function selectBids(auctionWinnersCount: number | undefined, bidList: Bid[], userBid: Bid | undefined): Bid[] {
if (auctionWinnersCount === undefined) {
return []
}

if (bidList.length <= bidsMaxCount) {
return bidList.map(bidToBidWithPlace)
return bidList
}

const topAuctionBids = bidList.slice(0, topAuctionBidsCount).map(bidToBidWithPlace)
const topAuctionBids = bidList.slice(0, topAuctionBidsCount)

const lastAuctionBidIndex = bidList.length > auctionWinnersCount ? auctionWinnersCount - 1 : bidList.length - 1
const lastAuctionBid = bidToBidWithPlace(bidList[lastAuctionBidIndex], lastAuctionBidIndex)
const lastAuctionBid = bidList[lastAuctionBidIndex]

return userBid && shouldUserBidBeDisplayed(userBid, lastAuctionBid, auctionWinnersCount)
? topAuctionBids.concat([userBid, lastAuctionBid])
: topAuctionBids.concat([lastAuctionBid])
}

const shouldUserBidBeDisplayed = (userBid: BidWithPlace, lastAuctionBid: Bid, auctionWinnersCount: number) => {
const shouldUserBidBeDisplayed = (userBid: Bid, lastAuctionBid: Bid, auctionWinnersCount: number) => {
return !(userBid.address === lastAuctionBid.address) && within(bidsMaxCount, auctionWinnersCount - 1, userBid.place)
}

Expand Down
4 changes: 1 addition & 3 deletions packages/frontend/src/providers/BidsProvider/provider.tsx
Original file line number Diff line number Diff line change
@@ -1,11 +1,9 @@
import { createContext, ReactNode, useContext, useReducer } from 'react'
import { Hex } from 'viem'
import { defaultBidsState, reduceBids } from '@/providers/BidsProvider/reduceBids'
import { useWatchEvents } from '@/providers/BidsProvider/useWatchEvents'
import { Bid } from '@/types/bid'

const BidsContext = createContext({
bids: new Map<Hex, Bid>(),
bidList: new Array<Bid>(),
isLoading: true,
})
Expand All @@ -16,5 +14,5 @@ export const BidsProvider = ({ children }: { children: ReactNode }) => {
const [bidsState, updateBids] = useReducer(reduceBids, defaultBidsState)
const { isLoading } = useWatchEvents(updateBids)

return <BidsContext.Provider value={{ ...bidsState, isLoading }}>{children}</BidsContext.Provider>
return <BidsContext.Provider value={{ bidList: bidsState.bidList, isLoading }}>{children}</BidsContext.Provider>
}
50 changes: 31 additions & 19 deletions packages/frontend/src/providers/BidsProvider/reduceBids.ts
Original file line number Diff line number Diff line change
@@ -1,24 +1,23 @@
import { Bid } from '@/types/bid'
import { Hex } from 'viem'

interface BidEvent {
args: {
bidder?: Hex
bidderID?: bigint
bidAmount?: bigint
}
}
export type RawBid = Omit<Bid, 'place'>

interface BidsState {
bids: Map<Hex, Bid>
bids: Map<Hex, RawBid>
bidList: Bid[]
}

export const defaultBidsState: BidsState = {
bids: new Map<Hex, Bid>(),
bids: new Map<Hex, RawBid>(),
bidList: [],
}

interface InitialBidsAction {
type: 'InitialBids'
bids: readonly BidWithAddressPayload[]
}

interface BidWithAddressPayload {
bidder: Hex
bid: {
Expand All @@ -27,16 +26,19 @@ interface BidWithAddressPayload {
}
}

interface InitialBidsAction {
type: 'InitialBids'
bids: readonly BidWithAddressPayload[]
}

interface NewBidsAction {
type: 'NewBids'
events: BidEvent[]
}

interface BidEvent {
args: {
bidder?: Hex
bidderID?: bigint
bidAmount?: bigint
}
}

export type ReduceBidsAction = InitialBidsAction | NewBidsAction

export const reduceBids = (previousState: BidsState, action: ReduceBidsAction) => {
Expand All @@ -49,7 +51,7 @@ export const reduceBids = (previousState: BidsState, action: ReduceBidsAction) =
}

const addInitialBids = (bidsPayload: readonly BidWithAddressPayload[]): BidsState => {
const bids = new Map<Hex, Bid>()
const bids = new Map<Hex, RawBid>()
bidsPayload.forEach((bidPayload) =>
bids.set(bidPayload.bidder, {
address: bidPayload.bidder,
Expand All @@ -60,7 +62,7 @@ const addInitialBids = (bidsPayload: readonly BidWithAddressPayload[]): BidsStat

return {
bids,
bidList: Array.from(bids.values()).sort(biggerFirst),
bidList: bidsMapToList(bids),
}
}

Expand All @@ -71,11 +73,11 @@ const addNewBids = (previousState: BidsState, events: BidEvent[]): BidsState =>

return {
bids,
bidList: Array.from(bids.values()).sort(biggerFirst),
bidList: bidsMapToList(bids),
}
}

const handleBid = (bids: Map<Hex, Bid>, eventArgs: BidEvent['args']) => {
const handleBid = (bids: Map<Hex, RawBid>, eventArgs: BidEvent['args']) => {
if (!eventArgs.bidder || !eventArgs.bidAmount || !eventArgs.bidderID) {
return
}
Expand All @@ -92,7 +94,17 @@ const handleBid = (bids: Map<Hex, Bid>, eventArgs: BidEvent['args']) => {
})
}

const biggerFirst = (a: Bid, b: Bid) => {
const bidsMapToList = (bids: Map<Hex, RawBid>) =>
Array.from(bids.values())
.sort(biggerFirst)
.map(
(bid: RawBid, arrayIndex: number): Bid => ({
...bid,
place: arrayIndex + 1,
}),
)

const biggerFirst = (a: RawBid, b: RawBid) => {
if (a.amount === b.amount) {
return 0
}
Expand Down
5 changes: 0 additions & 5 deletions packages/frontend/src/types/bid.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,5 @@ export interface Bid {
address: Hex
amount: bigint
bidderId: bigint
}

export interface BidWithPlace extends Bid {
place: number
}

export const bidToBidWithPlace = (bid: Bid, arrayIndex: number): BidWithPlace => ({ ...bid, place: arrayIndex + 1 })

0 comments on commit 543c5ba

Please sign in to comment.