Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

chore(marketplace): add a cache for storage requests #1090

Open
wants to merge 4 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion codex/codex.nim
Original file line number Diff line number Diff line change
Expand Up @@ -107,7 +107,9 @@ proc bootstrapInteractions(s: CodexServer): Future[void] {.async.} =
quit QuitFailure

let marketplace = Marketplace.new(marketplaceAddress, signer)
let market = OnChainMarket.new(marketplace, config.rewardRecipient)
let market = OnChainMarket.new(
marketplace, config.rewardRecipient, config.marketplaceRequestCacheSize
)
let clock = OnChainClock.new(provider)

var client: ?ClientInteractions
Expand Down
13 changes: 12 additions & 1 deletion codex/conf.nim
Original file line number Diff line number Diff line change
Expand Up @@ -44,14 +44,15 @@ import ./utils
import ./nat
import ./utils/natutils

from ./contracts/config import DefaultRequestCacheSize
from ./validationconfig import MaxSlots, ValidationGroups

export units, net, codextypes, logutils, completeCmdArg, parseCmdArg, NatConfig
export ValidationGroups, MaxSlots

export
DefaultQuotaBytes, DefaultBlockTtl, DefaultBlockMaintenanceInterval,
DefaultNumberOfBlocksToMaintainPerInterval
DefaultNumberOfBlocksToMaintainPerInterval, DefaultRequestCacheSize

proc defaultDataDir*(): string =
let dataDir =
Expand Down Expand Up @@ -347,6 +348,16 @@ type
name: "reward-recipient"
.}: Option[EthAddress]

marketplaceRequestCacheSize* {.
desc:
"Maximum number of StorageRequests kept in memory." &
"Reduces fetching of StorageRequest data from the contract.",
defaultValue: DefaultRequestCacheSize,
defaultValueDesc: $DefaultRequestCacheSize,
name: "request-cache-size",
hidden
.}: uint16

case persistenceCmd* {.defaultValue: noCmd, command.}: PersistenceCmd
of PersistenceCmd.prover:
circuitDir* {.
Expand Down
2 changes: 2 additions & 0 deletions codex/contracts/config.nim
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@ import pkg/questionable/results

export contractabi

const DefaultRequestCacheSize* = 128.uint16

type
MarketplaceConfig* = object
collateral*: CollateralConfig
Expand Down
25 changes: 22 additions & 3 deletions codex/contracts/market.nim
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
import pkg/ethers
import pkg/upraises
import pkg/questionable
import pkg/lrucache
import ../utils/exceptions
import ../logutils
import ../market
Expand All @@ -20,19 +21,30 @@
signer: Signer
rewardRecipient: ?Address
configuration: ?MarketplaceConfig
requestCache: LruCache[string, StorageRequest]

MarketSubscription = market.Subscription
EventSubscription = ethers.Subscription
OnChainMarketSubscription = ref object of MarketSubscription
eventSubscription: EventSubscription

func new*(
_: type OnChainMarket, contract: Marketplace, rewardRecipient = Address.none
_: type OnChainMarket,
contract: Marketplace,
rewardRecipient = Address.none,
requestCacheSize: uint16 = DefaultRequestCacheSize,
): OnChainMarket =
without signer =? contract.signer:
raiseAssert("Marketplace contract should have a signer")

OnChainMarket(contract: contract, signer: signer, rewardRecipient: rewardRecipient)
var requestCache = newLruCache[string, StorageRequest](int(requestCacheSize))

OnChainMarket(
contract: contract,
signer: signer,
rewardRecipient: rewardRecipient,
requestCache: requestCache,
)

proc raiseMarketError(message: string) {.raises: [MarketError].} =
raise newException(MarketError, message)
Expand Down Expand Up @@ -112,9 +124,16 @@
method getRequest*(
market: OnChainMarket, id: RequestId
): Future[?StorageRequest] {.async.} =
let key = $id

if market.requestCache.contains(key):
return some market.requestCache[key]

Check warning on line 131 in codex/contracts/market.nim

View check run for this annotation

Codecov / codecov/patch

codex/contracts/market.nim#L127-L131

Added lines #L127 - L131 were not covered by tests
convertEthersError:
try:
return some await market.contract.getRequest(id)
let request = await market.contract.getRequest(id)
market.requestCache[key] = request
return some request

Check warning on line 136 in codex/contracts/market.nim

View check run for this annotation

Codecov / codecov/patch

codex/contracts/market.nim#L134-L136

Added lines #L134 - L136 were not covered by tests
except Marketplace_UnknownRequest:
return none StorageRequest

Expand Down
11 changes: 11 additions & 0 deletions tests/contracts/testMarket.nim
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import std/importutils
import pkg/chronos
import pkg/ethers/erc20
import codex/contracts
import pkg/lrucache
import ../ethertest
import ./examples
import ./time
Expand Down Expand Up @@ -591,3 +592,13 @@ ethersuite "On-Chain Market":
let expectedPayout = request.expectedPayout(filledAt, requestEnd.u256)
check endBalanceHost == (startBalanceHost + request.ask.collateralPerSlot)
check endBalanceReward == (startBalanceReward + expectedPayout)

test "the request is added in cache after the fist access":
await market.requestStorage(request)

check market.requestCache.contains($request.id) == false
discard await market.getRequest(request.id)

check market.requestCache.contains($request.id) == true
let cacheValue = market.requestCache[$request.id]
check cacheValue == request
Loading