[contracts] Do not crash when contract interaction fails

Log error instead.
This commit is contained in:
Mark Spanbroek 2022-04-20 12:39:40 +02:00 committed by markspanbroek
parent d2da225f21
commit fae05fce86
3 changed files with 37 additions and 22 deletions

View File

@ -2,6 +2,7 @@ import std/sets
import std/times import std/times
import pkg/upraises import pkg/upraises
import pkg/questionable import pkg/questionable
import pkg/chronicles
import ./por/timing/proofs import ./por/timing/proofs
export sets export sets
@ -33,15 +34,18 @@ proc removeEndedContracts(proving: Proving) {.async.} =
proving.contracts.excl(ended) proving.contracts.excl(ended)
proc run(proving: Proving) {.async.} = proc run(proving: Proving) {.async.} =
while not proving.stopped: try:
let currentPeriod = await proving.proofs.getCurrentPeriod() while not proving.stopped:
await proving.removeEndedContracts() let currentPeriod = await proving.proofs.getCurrentPeriod()
for id in proving.contracts: await proving.removeEndedContracts()
if (await proving.proofs.isProofRequired(id)) or for id in proving.contracts:
(await proving.proofs.willProofBeRequired(id)): if (await proving.proofs.isProofRequired(id)) or
if callback =? proving.onProofRequired: (await proving.proofs.willProofBeRequired(id)):
callback(id) if callback =? proving.onProofRequired:
await proving.proofs.waitUntilPeriod(currentPeriod + 1) callback(id)
await proving.proofs.waitUntilPeriod(currentPeriod + 1)
except CatchableError as e:
error "Proving failed", msg = e.msg
proc start*(proving: Proving) = proc start*(proving: Proving) =
asyncSpawn proving.run() asyncSpawn proving.run()

View File

@ -80,7 +80,6 @@ proc run(purchase: Purchase) {.async.} =
proc start(purchase: Purchase) = proc start(purchase: Purchase) =
purchase.future = purchase.run() purchase.future = purchase.run()
asyncSpawn purchase.future
proc wait*(purchase: Purchase) {.async.} = proc wait*(purchase: Purchase) {.async.} =
await purchase.future await purchase.future

View File

@ -4,6 +4,7 @@ import pkg/questionable
import pkg/upraises import pkg/upraises
import pkg/stint import pkg/stint
import pkg/nimcrypto import pkg/nimcrypto
import pkg/chronicles
import ./market import ./market
export stint export stint
@ -111,16 +112,17 @@ proc waitForExpiry(negotiation: Negotiation) {.async.} =
negotiation.finish(success = false) negotiation.finish(success = false)
proc start(negotiation: Negotiation) {.async.} = proc start(negotiation: Negotiation) {.async.} =
let sales = negotiation.sales try:
let availability = negotiation.availability let sales = negotiation.sales
sales.remove(availability) let availability = negotiation.availability
await negotiation.sendOffer() sales.remove(availability)
await negotiation.subscribeSelect() await negotiation.sendOffer()
negotiation.waiting = some negotiation.waitForExpiry() await negotiation.subscribeSelect()
negotiation.waiting = some negotiation.waitForExpiry()
except CatchableError as e:
error "Negotiation failed", msg = e.msg
proc handleRequest(sales: Sales, proc handleRequest(sales: Sales, requestId: array[32, byte], ask: StorageAsk) =
requestId: array[32, byte],
ask: StorageAsk) {.async.} =
without availability =? sales.findAvailability(ask): without availability =? sales.findAvailability(ask):
return return
@ -137,14 +139,24 @@ proc start*(sales: Sales) =
doAssert sales.subscription.isNone, "Sales already started" doAssert sales.subscription.isNone, "Sales already started"
proc onRequest(requestId: array[32, byte], ask: StorageAsk) {.gcsafe, upraises:[].} = proc onRequest(requestId: array[32, byte], ask: StorageAsk) {.gcsafe, upraises:[].} =
asyncSpawn sales.handleRequest(requestId, ask) sales.handleRequest(requestId, ask)
proc subscribe {.async.} = proc subscribe {.async.} =
sales.subscription = some await sales.market.subscribeRequests(onRequest) try:
sales.subscription = some await sales.market.subscribeRequests(onRequest)
except CatchableError as e:
error "Unable to start sales", msg = e.msg
asyncSpawn subscribe() asyncSpawn subscribe()
proc stop*(sales: Sales) = proc stop*(sales: Sales) =
if subscription =? sales.subscription: if subscription =? sales.subscription:
asyncSpawn subscription.unsubscribe()
sales.subscription = Subscription.none sales.subscription = Subscription.none
proc unsubscribe {.async.} =
try:
await subscription.unsubscribe()
except CatchableError as e:
warn "Unsubscribe failed", msg = e.msg
asyncSpawn unsubscribe()