Skip to content

Commit

Permalink
0.5.3
Browse files Browse the repository at this point in the history
  • Loading branch information
KABBOUCHI committed Oct 25, 2023
1 parent 31bcd61 commit d1a2553
Show file tree
Hide file tree
Showing 3 changed files with 128 additions and 2 deletions.
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@instadapp/utils",
"version": "0.5.2",
"version": "0.5.3",
"description": "",
"repository": "instadapp/utils",
"license": "MIT",
Expand Down
87 changes: 87 additions & 0 deletions src/providers/json-rpc-provider.ts
Original file line number Diff line number Diff line change
Expand Up @@ -819,3 +819,90 @@ export class JsonRpcBatchProvider extends JsonRpcProvider {
return promise
}
}

export class StaticJsonRpcBatchProvider extends StaticJsonRpcProvider {
_pendingBatchAggregator: NodeJS.Timer
_pendingBatch: Array<{
request: { method: string, params: Array<any>, id: number, jsonrpc: '2.0' },
resolve: (result: any) => void,
reject: (error: Error) => void
}>

send (method: string, params: Array<any>): Promise<any> {
const request = {
method,
params,
id: (this._nextId++),
jsonrpc: '2.0'
}

if (this._pendingBatch == null) {
this._pendingBatch = []
}

const inflightRequest: any = { request, resolve: null, reject: null }

const promise = new Promise((resolve, reject) => {
inflightRequest.resolve = resolve
inflightRequest.reject = reject
})

this._pendingBatch.push(inflightRequest)

if (!this._pendingBatchAggregator) {
// Schedule batch for next event loop + short duration
this._pendingBatchAggregator = setTimeout(() => {
// Get teh current batch and clear it, so new requests
// go into the next batch
const batch = this._pendingBatch
this._pendingBatch = null
this._pendingBatchAggregator = null

// Get the request as an array of requests
const request = batch.map(inflight => inflight.request)

this.emit('debug', {
action: 'requestBatch',
request: deepCopy(request),
provider: this
})

return fetchJson(this.connection, JSON.stringify(request)).then((result) => {
this.emit('debug', {
action: 'response',
request,
response: result,
provider: this
})

// For each result, feed it to the correct Promise, depending
// on whether it was a success or error
batch.forEach((inflightRequest, index) => {
const payload = result[index]
if (payload.error) {
const error = new Error(payload.error.message);
(<any>error).code = payload.error.code;
(<any>error).data = payload.error.data
inflightRequest.reject(error)
} else {
inflightRequest.resolve(payload.result)
}
})
}, (error) => {
this.emit('debug', {
action: 'response',
error,
request,
provider: this
})

batch.forEach((inflightRequest) => {
inflightRequest.reject(error)
})
})
}, 10)
}

return promise
}
}
41 changes: 40 additions & 1 deletion src/providers/retry-provider.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { retry } from '../promises'
import { JsonRpcProvider, StaticJsonRpcProvider, JsonRpcBatchProvider } from './json-rpc-provider'
import { JsonRpcProvider, StaticJsonRpcProvider, JsonRpcBatchProvider, StaticJsonRpcBatchProvider } from './json-rpc-provider'

export class JsonRpcRetryProvider extends JsonRpcProvider {
urls: string[]
Expand Down Expand Up @@ -117,3 +117,42 @@ export class StaticJsonRpcRetryProvider extends StaticJsonRpcProvider {
})
}
}

export class StaticJsonRpcRetryBatchProvider extends StaticJsonRpcBatchProvider {
urls: string[]
urlIndex: number = 0
timeouts: number[] = [5_000, 10_000, 15_000]
delay: number = 300

constructor (urls: string | string[], options?: { timeouts?: number[], delay?: number }) {
urls = Array.isArray(urls) ? urls : [urls]

super(urls[0])

this.urls = urls
this.urlIndex = 0

if (options && options.timeouts) {
this.timeouts = options.timeouts
}

if (options && options.delay) {
this.delay = options.delay
}

Object.setPrototypeOf(this, StaticJsonRpcRetryProvider.prototype)
}

public send (method: string, params: Array<any>): Promise<any> {
const operation = () => super.send(method, params)

return retry(operation, {
timeouts: this.timeouts,
delay: this.delay,
onRetry: () => {
this.urlIndex = (this.urlIndex + 1) % this.urls.length
this.connection.url = this.urls[this.urlIndex]
}
})
}
}

0 comments on commit d1a2553

Please sign in to comment.