Skip to content
This repository has been archived by the owner on Feb 12, 2024. It is now read-only.

Commit

Permalink
fix: remove client-side timeout from http rpc calls (#3178)
Browse files Browse the repository at this point in the history
Do not set up a client-side timeout, instead rely on the server-side version.

The global timeout is still respected, users can use an AbortSignal to do
timeouts on a per-call basis if desired.

Also brings refs API in line with go-IPFS - timeouts are recorded in the `.err`
prop of the output instead of the whole API call throwing a `TimeoutError`

fixes: #3161
  • Loading branch information
achingbrain committed Sep 1, 2021
1 parent eba5fe6 commit f11220e
Show file tree
Hide file tree
Showing 99 changed files with 45 additions and 112 deletions.
3 changes: 1 addition & 2 deletions packages/interface-ipfs-core/src/refs.js
Original file line number Diff line number Diff line change
Expand Up @@ -323,8 +323,7 @@ function getRefsTests () {
'should print nothing for non-existent hashes': {
path: () => 'QmYmW4HiZhotsoSqnv2o1oSssvkRM8b9RweBoH7ao5nki2',
params: { timeout: 2000 },
expected: [],
expectTimeout: true
expected: ['']
}
}
}
Expand Down
2 changes: 2 additions & 0 deletions packages/ipfs-core/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,7 @@
"@ipld/dag-pb": "^2.1.3",
"@multiformats/murmur3": "^1.0.1",
"abort-controller": "^3.0.0",
"any-signal": "^2.1.2",
"array-shuffle": "^2.0.0",
"blockstore-datastore-adapter": "^1.0.0",
"datastore-core": "^5.0.1",
Expand Down Expand Up @@ -126,6 +127,7 @@
"parse-duration": "^1.0.0",
"peer-id": "^0.15.1",
"streaming-iterables": "^6.0.0",
"timeout-abort-controller": "^1.1.1",
"uint8arrays": "^3.0.0"
},
"devDependencies": {
Expand Down
40 changes: 30 additions & 10 deletions packages/ipfs-core/src/components/refs/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,11 @@
const dagPb = require('@ipld/dag-pb')
const { Errors } = require('interface-datastore')
const ERR_NOT_FOUND = Errors.notFoundError().code
const withTimeoutOption = require('ipfs-core-utils/src/with-timeout-option')
const toCIDAndPath = require('ipfs-core-utils/src/to-cid-and-path')
const { CID } = require('multiformats/cid')
// @ts-expect-error no types
const TimeoutController = require('timeout-abort-controller')
const { anySignal } = require('any-signal')

const Format = {
default: '<dst>',
Expand All @@ -21,6 +23,8 @@ const Format = {
* @property {Node} parent
* @property {Node} node
* @property {boolean} isDuplicate
*
* @typedef {import('ipfs-core-types/src/utils').AbortOptions} AbortOptions
*/

/**
Expand Down Expand Up @@ -49,17 +53,30 @@ module.exports = function ({ repo, codecs, resolve, preload }) {
options.maxDepth = options.recursive ? Infinity : 1
}

if (options.timeout) {
const controller = new TimeoutController(options.timeout)

options.signal = anySignal([options.signal, controller.signal])
}

/** @type {(string|CID)[]} */
const rawPaths = Array.isArray(ipfsPath) ? ipfsPath : [ipfsPath]

const paths = rawPaths.map(p => getFullPath(preload, p, options))

for (const path of paths) {
yield * refsStream(resolve, repo, codecs, path, options)
try {
yield * refsStream(resolve, repo, codecs, path, options)
} catch (err) {
yield {
ref: '',
err: err.message
}
}
}
}

return withTimeoutOption(refs)
return refs
}

module.exports.Format = Format
Expand Down Expand Up @@ -93,7 +110,7 @@ function getFullPath (preload, ipfsPath, options) {
*/
async function * refsStream (resolve, repo, codecs, path, options) {
// Resolve to the target CID of the path
const resPath = await resolve(path)
const resPath = await resolve(path, options)
const {
cid
} = toCIDAndPath(resPath)
Expand All @@ -102,7 +119,7 @@ async function * refsStream (resolve, repo, codecs, path, options) {
const unique = options.unique || false

// Traverse the DAG, converting it into a stream
for await (const obj of objectStream(repo, codecs, cid, maxDepth, unique)) {
for await (const obj of objectStream(repo, codecs, cid, maxDepth, unique, options)) {
// Root object will not have a parent
if (!obj.parent) {
continue
Expand Down Expand Up @@ -144,8 +161,9 @@ function formatLink (srcCid, dstCid, linkName = '', format = Format.default) {
* @param {CID} rootCid
* @param {number} maxDepth
* @param {boolean} uniqueOnly
* @param {AbortOptions} options
*/
async function * objectStream (repo, codecs, rootCid, maxDepth, uniqueOnly) { // eslint-disable-line require-await
async function * objectStream (repo, codecs, rootCid, maxDepth, uniqueOnly, options) { // eslint-disable-line require-await
const seen = new Set()

/**
Expand All @@ -164,7 +182,7 @@ async function * objectStream (repo, codecs, rootCid, maxDepth, uniqueOnly) { //
// Get this object's links
try {
// Look at each link, parent and the new depth
for await (const link of getLinks(repo, codecs, parent.cid)) {
for await (const link of getLinks(repo, codecs, parent.cid, options)) {
yield {
parent: parent,
node: link,
Expand Down Expand Up @@ -195,14 +213,16 @@ async function * objectStream (repo, codecs, rootCid, maxDepth, uniqueOnly) { //
* @param {import('ipfs-repo').IPFSRepo} repo
* @param {import('ipfs-core-utils/src/multicodecs')} codecs
* @param {CID} cid
* @param {Array<string|number>} base
* @param {AbortOptions} options
* @returns {AsyncGenerator<{ name: string, cid: CID }, void, undefined>}
*/
async function * getLinks (repo, codecs, cid, base = []) {
const block = await repo.blocks.get(cid)
async function * getLinks (repo, codecs, cid, options) {
const block = await repo.blocks.get(cid, options)
const codec = await codecs.getCodec(cid.code)
const value = codec.decode(block)
const isDagPb = cid.code === dagPb.code
/** @type {Array<string|number>} */
const base = []

for (const [name, cid] of links(value, base)) {
// special case for dag-pb - use the name of the link
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/add-all.js
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,6 @@ module.exports = configure((api) => {
...options,
progress: Boolean(progressFn)
}),
timeout: options.timeout,
onUploadProgress,
signal,
headers,
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/bitswap/stat.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@ module.exports = configure(api => {
async function stat (options = {}) {
const res = await api.post('bitswap/stat', {
searchParams: toUrlSearchParams(options),
timeout: options.timeout,
signal: options.signal,
headers: options.headers
})
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/bitswap/unwant.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ module.exports = configure(api => {
*/
async function unwant (cid, options = {}) {
const res = await api.post('bitswap/unwant', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: cid.toString(),
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/bitswap/wantlist-for-peer.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ module.exports = configure(api => {
*/
async function wantlistForPeer (peerId, options = {}) {
const res = await (await api.post('bitswap/wantlist', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
...options,
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/bitswap/wantlist.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ module.exports = configure(api => {
*/
async function wantlist (options = {}) {
const res = await (await api.post('bitswap/wantlist', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams(options),
headers: options.headers
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/block/get.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ module.exports = configure(api => {
*/
async function get (cid, options = {}) {
const res = await api.post('block/get', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: cid.toString(),
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/block/put.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,6 @@ module.exports = configure(api => {
let res
try {
const response = await api.post('block/put', {
timeout: options.timeout,
signal: signal,
searchParams: toUrlSearchParams(options),
...(
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/block/rm.js
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,6 @@ module.exports = configure(api => {
}

const res = await api.post('block/rm', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: cid.map(cid => cid.toString()),
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/block/stat.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ module.exports = configure(api => {
*/
async function stat (cid, options = {}) {
const res = await api.post('block/stat', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: cid.toString(),
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/bootstrap/add.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ module.exports = configure(api => {
*/
async function add (addr, options = {}) {
const res = await api.post('bootstrap/add', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: addr,
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/bootstrap/clear.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ module.exports = configure(api => {
*/
async function clear (options = {}) {
const res = await api.post('bootstrap/rm', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
...options,
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/bootstrap/list.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ module.exports = configure(api => {
*/
async function list (options = {}) {
const res = await api.post('bootstrap/list', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams(options),
headers: options.headers
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/bootstrap/reset.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ module.exports = configure(api => {
*/
async function reset (options = {}) {
const res = await api.post('bootstrap/add', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
...options,
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/bootstrap/rm.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ module.exports = configure(api => {
*/
async function rm (addr, options = {}) {
const res = await api.post('bootstrap/rm', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: addr,
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/cat.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ module.exports = configure(api => {
*/
async function * cat (path, options = {}) {
const res = await api.post('cat', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: path.toString(),
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/commands.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ module.exports = configure(api => {
*/
const commands = async (options = {}) => {
const res = await api.post('commands', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams(options),
headers: options.headers
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/config/get.js
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@ module.exports = configure(api => {
}

const res = await api.post('config', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: key,
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/config/getAll.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ module.exports = configure(api => {
*/
const getAll = async (options = {}) => {
const res = await api.post('config/show', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
...options
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/config/profiles/apply.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ module.exports = configure(api => {
*/
async function apply (profile, options = {}) {
const res = await api.post('config/profile/apply', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: profile,
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/config/profiles/list.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ module.exports = configure(api => {
*/
async function list (options = {}) {
const res = await api.post('config/profile/list', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams(options),
headers: options.headers
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/config/replace.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,6 @@ module.exports = configure(api => {
const signal = abortSignal(controller.signal, options.signal)

const res = await api.post('config/replace', {
timeout: options.timeout,
signal,
searchParams: toUrlSearchParams(options),
...(
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/config/set.js
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,6 @@ module.exports = configure(api => {
}

const res = await api.post('config', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams(params),
headers: options.headers
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/dag/export.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ module.exports = configure(api => {
*/
async function * dagExport (root, options = {}) {
const res = await api.post('dag/export', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: root.toString()
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/dag/import.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,6 @@ module.exports = configure(api => {
const { headers, body } = await multipartRequest(source, controller, options.headers)

const res = await api.post('dag/import', {
timeout: options.timeout,
signal,
headers,
body,
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/dag/resolve.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ module.exports = configure(api => {
*/
const resolve = async (ipfsPath, options = {}) => {
const res = await api.post('dag/resolve', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: `${ipfsPath}${options.path ? `/${options.path}`.replace(/\/[/]+/g, '/') : ''}`,
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/dht/find-peer.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@ module.exports = configure(api => {
*/
async function findPeer (peerId, options = {}) {
const res = await api.post('dht/findpeer', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: peerId,
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/dht/find-provs.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@ module.exports = configure(api => {
*/
async function * findProvs (cid, options = {}) {
const res = await api.post('dht/findprovs', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: cid.toString(),
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/dht/get.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@ module.exports = configure(api => {
*/
async function get (key, options = {}) {
const res = await api.post('dht/get', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: key instanceof Uint8Array ? uint8ArrayToString(key) : key,
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/dht/provide.js
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,6 @@ module.exports = configure(api => {
const cidArr = Array.isArray(cids) ? cids : [cids]

const res = await api.post('dht/provide', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: cidArr.map(cid => cid.toString()),
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/dht/put.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,6 @@ module.exports = configure(api => {
const signal = abortSignal(controller.signal, options.signal)

const res = await api.post('dht/put', {
timeout: options.timeout,
signal,
searchParams: toUrlSearchParams({
arg: uint8ArrayToString(key),
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/dht/query.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@ module.exports = configure(api => {
*/
async function * query (peerId, options = {}) {
const res = await api.post('dht/query', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams({
arg: peerId.toString(),
Expand Down
1 change: 0 additions & 1 deletion packages/ipfs-http-client/src/diag/cmds.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ module.exports = configure(api => {
*/
async function cmds (options = {}) {
const res = await api.post('diag/cmds', {
timeout: options.timeout,
signal: options.signal,
searchParams: toUrlSearchParams(options),
headers: options.headers
Expand Down

0 comments on commit f11220e

Please sign in to comment.