[sales] Add callback for clearing storage when no longer needed
This commit is contained in:
parent
adcb91a5d5
commit
592a3dce4d
|
@ -312,10 +312,15 @@ proc start*(node: CodexNodeRef) {.async.} =
|
|||
await node.discovery.start()
|
||||
|
||||
if contracts =? node.contracts:
|
||||
contracts.sales.store = proc(cid: string) {.async.} =
|
||||
contracts.sales.store = proc(cid: string, _: Availability) {.async.} =
|
||||
# store data in local storage
|
||||
(await node.store(Cid.init(cid).tryGet())).tryGet()
|
||||
contracts.sales.onClear = proc(availability: Availability, request: StorageRequest) =
|
||||
# TODO: remove data from local storage
|
||||
discard
|
||||
contracts.sales.prove = proc(cid: string): Future[seq[byte]] {.async.} =
|
||||
return @[42'u8] # TODO: generate actual proof
|
||||
# TODO: generate proof
|
||||
return @[42'u8]
|
||||
await contracts.start()
|
||||
|
||||
node.networkId = node.switch.peerInfo.peerId
|
||||
|
|
|
@ -17,6 +17,7 @@ type
|
|||
available*: seq[Availability]
|
||||
store: ?Store
|
||||
prove: ?Prove
|
||||
onClear: ?OnClear
|
||||
onSale: ?OnSale
|
||||
Availability* = object
|
||||
id*: array[32, byte]
|
||||
|
@ -33,8 +34,9 @@ type
|
|||
running: ?Future[void]
|
||||
waiting: ?Future[void]
|
||||
finished: bool
|
||||
Store = proc(cid: string): Future[void] {.gcsafe, upraises: [].}
|
||||
Store = proc(cid: string, availability: Availability): Future[void] {.gcsafe, upraises: [].}
|
||||
Prove = proc(cid: string): Future[seq[byte]] {.gcsafe, upraises: [].}
|
||||
OnClear = proc(availability: Availability, request: StorageRequest) {.gcsafe, upraises: [].}
|
||||
OnSale = proc(availability: Availability, request: StorageRequest) {.gcsafe, upraises: [].}
|
||||
|
||||
func new*(_: type Sales, market: Market, clock: Clock): Sales =
|
||||
|
@ -57,6 +59,9 @@ proc `store=`*(sales: Sales, store: Store) =
|
|||
proc `prove=`*(sales: Sales, prove: Prove) =
|
||||
sales.prove = some prove
|
||||
|
||||
proc `onClear=`*(sales: Sales, onClear: OnClear) =
|
||||
sales.onClear = some onClear
|
||||
|
||||
proc `onSale=`*(sales: Sales, callback: OnSale) =
|
||||
sales.onSale = some callback
|
||||
|
||||
|
@ -88,10 +93,12 @@ proc finish(agent: SalesAgent, success: bool) =
|
|||
if waiting =? agent.waiting:
|
||||
waiting.cancel()
|
||||
|
||||
if success and request =? agent.request:
|
||||
if onSale =? agent.sales.onSale:
|
||||
if success:
|
||||
if onSale =? agent.sales.onSale and request =? agent.request:
|
||||
onSale(agent.availability, request)
|
||||
else:
|
||||
if onClear =? agent.sales.onClear and request =? agent.request:
|
||||
onClear(agent.availability, request)
|
||||
agent.sales.add(agent.availability)
|
||||
|
||||
proc onFulfill(agent: SalesAgent, requestId: array[32, byte]) {.async.} =
|
||||
|
@ -139,7 +146,7 @@ proc start(agent: SalesAgent) {.async.} =
|
|||
|
||||
agent.waiting = some agent.waitForExpiry()
|
||||
|
||||
await store(request.content.cid)
|
||||
await store(request.content.cid, availability)
|
||||
let proof = await prove(request.content.cid)
|
||||
await market.fulfillRequest(request.id, proof)
|
||||
except CancelledError:
|
||||
|
|
|
@ -32,8 +32,10 @@ suite "Sales":
|
|||
market = MockMarket.new()
|
||||
clock = MockClock.new()
|
||||
sales = Sales.new(market, clock)
|
||||
sales.store = proc(_: string) {.async.} = discard
|
||||
sales.prove = proc(_: string): Future[seq[byte]] {.async.} = return proof
|
||||
sales.store = proc(cid: string, availability: Availability) {.async.} =
|
||||
discard
|
||||
sales.prove = proc(cid: string): Future[seq[byte]] {.async.} =
|
||||
return proof
|
||||
await sales.start()
|
||||
request.expiry = (clock.now() + 42).u256
|
||||
|
||||
|
@ -76,14 +78,18 @@ suite "Sales":
|
|||
|
||||
test "retrieves and stores data locally":
|
||||
var storingCid: string
|
||||
sales.store = proc(cid: string) {.async.} = storingCid = cid
|
||||
var storingAvailability: Availability
|
||||
sales.store = proc(cid: string, availability: Availability) {.async.} =
|
||||
storingCid = cid
|
||||
storingAvailability = availability
|
||||
sales.add(availability)
|
||||
discard await market.requestStorage(request)
|
||||
check storingCid == request.content.cid
|
||||
|
||||
test "makes storage available again when data retrieval fails":
|
||||
let error = newException(IOError, "data retrieval failed")
|
||||
sales.store = proc(cid: string) {.async.} = raise error
|
||||
sales.store = proc(cid: string, availability: Availability) {.async.} =
|
||||
raise error
|
||||
sales.add(availability)
|
||||
discard await market.requestStorage(request)
|
||||
check sales.available == @[availability]
|
||||
|
@ -114,16 +120,31 @@ suite "Sales":
|
|||
check soldAvailability == availability
|
||||
check soldRequest == request
|
||||
|
||||
test "calls onClear when storage becomes available again":
|
||||
sales.prove = proc(cid: string): Future[seq[byte]] {.async.} =
|
||||
raise newException(IOError, "proof failed")
|
||||
var clearedAvailability: Availability
|
||||
var clearedRequest: StorageRequest
|
||||
sales.onClear = proc(availability: Availability, request: StorageRequest) =
|
||||
clearedAvailability = availability
|
||||
clearedRequest = request
|
||||
sales.add(availability)
|
||||
discard await market.requestStorage(request)
|
||||
check clearedAvailability == availability
|
||||
check clearedRequest == request
|
||||
|
||||
test "makes storage available again when other host fulfills request":
|
||||
let otherHost = Address.example
|
||||
sales.store = proc(_: string) {.async.} = await sleepAsync(1.hours)
|
||||
sales.store = proc(cid: string, availability: Availability) {.async.} =
|
||||
await sleepAsync(1.hours)
|
||||
sales.add(availability)
|
||||
discard await market.requestStorage(request)
|
||||
market.fulfillRequest(request.id, proof, otherHost)
|
||||
check sales.available == @[availability]
|
||||
|
||||
test "makes storage available again when request expires":
|
||||
sales.store = proc(_: string) {.async.} = await sleepAsync(1.hours)
|
||||
sales.store = proc(cid: string, availability: Availability) {.async.} =
|
||||
await sleepAsync(1.hours)
|
||||
sales.add(availability)
|
||||
discard await market.requestStorage(request)
|
||||
clock.set(request.expiry.truncate(int64))
|
||||
|
|
Loading…
Reference in New Issue