Comparing version 1.6.0 to 1.6.1
@@ -62,8 +62,2 @@ #!/usr/bin/env node | ||
console.error(err.stack || err); | ||
if (err.response) { | ||
console.error(err.response.statusCode); | ||
console.error(err.response.statusText); | ||
console.error(err.response.headers); | ||
console.error(err.response.body); | ||
} | ||
}); |
170
dashsight.js
@@ -8,2 +8,12 @@ (function (exports) { | ||
/** | ||
* @type {RequestInit} defaultOpts | ||
*/ | ||
let defaultOpts = { | ||
headers: { | ||
Accept: "application/json", | ||
"Content-Type": "application/json", | ||
}, | ||
}; | ||
const DUFFS = 100000000; | ||
@@ -22,6 +32,10 @@ | ||
/** @typedef {import('./').GetCoreUtxos} GetCoreUtxos */ | ||
/** @typedef {import('./').GetMultiCoreUtxos} GetMultiCoreUtxos */ | ||
/** @typedef {import('./').InstantBalance} InstantBalance */ | ||
/** @typedef {import('./').GetInstantBalance} GetInstantBalance */ | ||
/** @typedef {import('./').GetInstantBalances} GetInstantBalances */ | ||
/** @typedef {import('./').GetTx} GetTx */ | ||
/** @typedef {import('./').GetTxs} GetTxs */ | ||
/** @typedef {import('./').GetUtxos} GetUtxos */ | ||
/** @typedef {import('./').GetAllUtxos} GetAllUtxos */ | ||
/** @typedef {import('./').ToCoreUtxo} ToCoreUtxo */ | ||
@@ -103,2 +117,35 @@ /** @typedef {import('./').ToCoreUtxos} ToCoreUtxos */ | ||
/** @type {GetInstantBalances} */ | ||
insight.getInstantBalances = async function (addresses) { | ||
let utxos = await insight.getAllUtxos(addresses); | ||
/** @type {Record<String, InstantBalance>} */ | ||
let balanceOfAddrs = {} | ||
utxos?.forEach(function (utxo) { | ||
let balanceDuffs = utxo.satoshis || 0 | ||
let balanceDash = (balanceDuffs / DUFFS).toFixed(8); | ||
/** @type {InstantBalance | any} */ | ||
let utxoAddrSum = balanceOfAddrs[utxo.address] || {} | ||
let balance = utxoAddrSum.balance || 0 | ||
let balanceSat = utxoAddrSum.balanceSat || 0 | ||
let _utxoCount = utxoAddrSum._utxoCount || 0 | ||
let _utxoAmounts = utxoAddrSum._utxoAmounts || [] | ||
_utxoAmounts.push(utxo.satoshis) | ||
utxoAddrSum = { | ||
addrStr: utxo.address, | ||
balance: balance + parseFloat(balanceDash), | ||
balanceSat: balanceSat + balanceDuffs, | ||
_utxoCount: _utxoCount + 1, | ||
_utxoAmounts: _utxoAmounts, | ||
} | ||
balanceOfAddrs[utxo.address] = utxoAddrSum | ||
}); | ||
return Object.values(balanceOfAddrs); | ||
}; | ||
/** @type {GetUtxos} */ | ||
@@ -110,6 +157,39 @@ insight.getUtxos = async function (address) { | ||
/** @type Array<InsightUtxo> */ | ||
let utxos = utxoResp.body; | ||
let utxos = await utxoResp.json(); | ||
return utxos; | ||
}; | ||
/** @type {(addresses: string | string[]) => String} */ | ||
insight._joinAddrs = function (addresses) { | ||
let addrs = addresses | ||
if (Array.isArray(addrs)) { | ||
addrs = addrs.join(",") | ||
} | ||
return addrs | ||
}; | ||
/** @type {GetAllUtxos} */ | ||
insight.getAllUtxos = async function (addresses) { | ||
let addrs = insight._joinAddrs(addresses) | ||
// GET `${insightBaseUrl}/addrs/${addrs}/utxo` | ||
// also works unless you have too many addrs | ||
// then you get a `414 URI Too Long` error | ||
let utxoUrl = `${insightBaseUrl}/addrs/utxo`; | ||
// thus POST is used | ||
let utxoResp = await Dashsight.fetch(utxoUrl, { | ||
method: 'POST', | ||
body: { | ||
// @ts-ignore | ||
addrs, | ||
}, | ||
}); | ||
/** @type Array<InsightUtxo> */ | ||
let utxos = await utxoResp.json(); | ||
return utxos; | ||
}; | ||
/** @type {GetCoreUtxos} */ | ||
@@ -127,2 +207,8 @@ insight.getCoreUtxos = async function (address) { | ||
/** @type {GetMultiCoreUtxos} */ | ||
insight.getMultiCoreUtxos = async function (addresses) { | ||
let utxos = await insight.getAllUtxos(addresses); | ||
return insight.toCoreUtxos(utxos); | ||
}; | ||
/** @type {GetTx} */ | ||
@@ -133,5 +219,4 @@ insight.getTx = async function (txid) { | ||
/** @type {InsightTx} */ | ||
//@ts-ignore | ||
let data = txResp.body; | ||
/** @type InsightTx */ | ||
let data = await txResp.json(); | ||
return data; | ||
@@ -146,4 +231,3 @@ }; | ||
/** @type {InsightTxResponse} */ | ||
//@ts-ignore | ||
let body = txResp.body; | ||
let body = await txResp.json(); | ||
@@ -165,7 +249,7 @@ let data = await getAllPages(body, addr, maxPages); | ||
); | ||
let nextBody = nextResp.body; | ||
nextResp = await nextResp.json(); | ||
// Note: this could still be wrong, but I don't think we have | ||
// a better way to page so... whatever | ||
// @ts-ignore | ||
body.txs = body.txs.concat(nextBody?.txs); | ||
body.txs = body.txs.concat(nextResp?.txs); | ||
} | ||
@@ -192,3 +276,3 @@ return body; | ||
} | ||
return txResp.body; | ||
return txResp.json(); | ||
}; | ||
@@ -225,4 +309,4 @@ | ||
// consumed as an input | ||
tx.vout.forEach(addUnspentOutputs); | ||
tx.vin.forEach(removeSpentOutputs); | ||
tx.vout.forEach(addUnspentOutputs); | ||
@@ -287,68 +371,15 @@ /** | ||
/** @type {HeadersInit} */ | ||
let defaultHeaders = { | ||
Accept: "application/json", | ||
"Content-Type": "application/json", | ||
}; | ||
/** | ||
* @param {String | URL | Request} url | ||
* @param {RequestInit} [_opts] | ||
* @param {RequestInit} [opts] | ||
*/ | ||
Dashsight.fetch = async function dashfetch(url, _opts) { | ||
let opts = Object.assign({ headers: {} }, _opts); | ||
Object.assign(opts.headers, defaultHeaders, _opts?.headers); | ||
Dashsight.fetch = async function dashfetch(url, opts) { | ||
opts = Object.assign({}, defaultOpts, opts); | ||
if (opts.body) { | ||
//@ts-ignore | ||
let contentType = opts.headers["Content-Type"] || ""; | ||
let isJson = contentType.startsWith("application/json"); | ||
if (isJson) { | ||
opts.body = JSON.stringify(opts.body); | ||
} | ||
opts.body = JSON.stringify(opts.body); | ||
} | ||
let resp = await fetch(url, opts); | ||
let headers = Object.fromEntries(resp.headers.entries()); | ||
let rawBody = await resp.text(); | ||
let contentType = resp.headers.get("content-type") || ""; | ||
let isJson = contentType.startsWith("application/json"); | ||
/** @type {Object|Array<any>|String} */ | ||
let body = rawBody; | ||
if (isJson) { | ||
try { | ||
body = JSON.parse(rawBody); | ||
} catch (e) { | ||
// ignore | ||
} | ||
} | ||
let response = { | ||
ok: resp.ok, | ||
statusCode: resp.status, // backwards compat | ||
statusText: resp.statusText, | ||
headers: headers, | ||
body: body, | ||
toJSON: function () { | ||
return { | ||
ok: response.ok, | ||
statusCode: response.statusCode, | ||
statusText: response.statusText, | ||
headers: headers, | ||
body: body, | ||
}; | ||
}, | ||
get status() { | ||
console.warn( | ||
"deprecated: please use either 'statusText' or 'statusCode' (node.js and browser both have 'status', but flipped)", | ||
); | ||
return resp.statusText; | ||
}, | ||
_request: opts, | ||
_response: resp, | ||
}; | ||
if (resp.ok) { | ||
return response; | ||
return resp; | ||
} | ||
@@ -359,5 +390,4 @@ | ||
); | ||
// @ts-ignore | ||
err.response = response; | ||
err.response = resp.json(); | ||
throw err; | ||
@@ -364,0 +394,0 @@ }; |
@@ -11,3 +11,3 @@ (function (exports) { | ||
* @prop {String} [baseUrl] - (deprecated by dashsocketBaseUrl) ex: https://insight.dash.org | ||
* @prop {import('./').CookieStore?} cookieStore - only needed for insight APIs hosted behind an AWS load balancer | ||
* @prop {CookieStore} cookieStore - only needed for insight APIs hosted behind an AWS load balancer | ||
* @prop {Boolean} debug | ||
@@ -51,6 +51,9 @@ * @prop {Function} onClose | ||
let sidResp = await Ws.fetch(sidUrl); | ||
let sidResp = await window.fetch(sidUrl, { | ||
mode: "cors", | ||
credentials: "include", | ||
}); | ||
if (!sidResp.ok) { | ||
let err = new Error("bad response"); | ||
//@ts-ignore | ||
// TODO make error type consistent between browser and node? | ||
err.response = sidResp; | ||
@@ -61,3 +64,4 @@ throw err; | ||
// ex: `97:0{"sid":"xxxx",...}` | ||
let session = parseSession(sidResp.body || ""); | ||
let msg = await sidResp.text(); | ||
let session = parseSession(msg); | ||
return session; | ||
@@ -77,4 +81,6 @@ }; | ||
let subResp = await Ws.fetch(subUrl, { | ||
let subResp = await window.fetch(subUrl, { | ||
method: "POST", | ||
mode: "cors", | ||
credentials: "include", | ||
headers: { | ||
@@ -92,3 +98,3 @@ "Content-Type": "text/plain;charset=UTF-8", | ||
return subResp.body; | ||
return await subResp.text(); | ||
}; | ||
@@ -293,3 +299,3 @@ | ||
* @param {String} msg | ||
* @returns {import('./').SocketIoHello} | ||
* @returns {SocketIoHello} | ||
*/ | ||
@@ -454,58 +460,2 @@ function parseSession(msg) { | ||
}; | ||
/** @type {RequestInit} */ | ||
let defaultRequest = { | ||
mode: "cors", | ||
credentials: "include", | ||
}; | ||
/** | ||
* @param {String | URL | Request} url | ||
* @param {RequestInit} [_opts] | ||
*/ | ||
Ws.fetch = async function dashfetch(url, _opts) { | ||
let opts = Object.assign(defaultRequest, _opts); | ||
let resp = await fetch(url, opts); | ||
// this will not have arrays, only strings | ||
let headers = Object.fromEntries(resp.headers.entries()); | ||
let body = await resp.text(); | ||
let response = { | ||
ok: resp.ok, | ||
statusCode: resp.status, // backwards compat | ||
statusText: resp.statusText, | ||
headers: headers, | ||
body: body, | ||
toJSON: function () { | ||
return { | ||
ok: response.ok, | ||
statusCode: response.statusCode, | ||
statusText: response.statusText, | ||
headers: headers, | ||
body: body, | ||
}; | ||
}, | ||
get status() { | ||
console.warn( | ||
"deprecated: please use either 'statusText' or 'statusCode' (node.js and browser both have 'status', but flipped)", | ||
); | ||
return resp.statusText; | ||
}, | ||
_request: opts, | ||
_response: resp, | ||
}; | ||
if (resp.ok) { | ||
return response; | ||
} | ||
let err = new Error( | ||
`http request was ${resp.status}, not ok. See err.response for details.`, | ||
); | ||
// @ts-ignore | ||
err.response = response; | ||
throw err; | ||
}; | ||
})(("undefined" !== typeof module && module.exports) || window); |
25
index.js
@@ -9,6 +9,9 @@ "use strict"; | ||
* @prop {GetCoreUtxos} getCoreUtxos | ||
* @prop {GetMultiCoreUtxos} getMultiCoreUtxos | ||
* @prop {GetInstantBalance} getInstantBalance | ||
* @prop {GetInstantBalances} getInstantBalances | ||
* @prop {GetTx} getTx | ||
* @prop {GetTxs} getTxs | ||
* @prop {GetUtxos} getUtxos | ||
* @prop {GetAllUtxos} getAllUtxos | ||
* @prop {InstantSend} instantSend | ||
@@ -33,2 +36,9 @@ * @prop {ToCoreUtxos} toCoreUtxos | ||
/** | ||
* Instant Balance is accurate with Instant Send | ||
* @callback GetInstantBalances | ||
* @param {String | Array<String>} addresses | ||
* @returns {Promise<Array<InstantBalance>>} | ||
*/ | ||
/** | ||
* @callback GetUtxos | ||
@@ -40,2 +50,8 @@ * @param {String} address | ||
/** | ||
* @callback GetAllUtxos | ||
* @param {String | Array<String>} addresses | ||
* @returns {Promise<Array<InsightUtxo>>} | ||
*/ | ||
/** | ||
* @callback GetCoreUtxos | ||
@@ -49,2 +65,11 @@ * @param {String} address | ||
/** | ||
* @callback GetMultiCoreUtxos | ||
* @param {String | Array<String>} addresses | ||
* @returns {Promise<Array<CoreUtxo>>} | ||
* | ||
* @TODO handle multiple input addresses | ||
*/ | ||
/** | ||
* @callback GetTx | ||
@@ -51,0 +76,0 @@ * @param {String} txid |
{ | ||
"name": "dashsight", | ||
"version": "1.6.0", | ||
"version": "1.6.1", | ||
"description": "SDK for Dash's flavor of the Insight API", | ||
@@ -53,6 +53,7 @@ "main": "index.js", | ||
"optionalDependencies": { | ||
"dotenv": "^16.0.1", | ||
"tough-cookie": "^4.1.2", | ||
"ws": "^8.13.0" | ||
"dotenv": "^16.0.1" | ||
}, | ||
"dependencies": { | ||
"dashtx": "^0.9.0-3" | ||
}, | ||
"devDependencies": { | ||
@@ -62,6 +63,4 @@ "@dashincubator/base58check": "^1.3.1", | ||
"@dashincubator/secp256k1": "^1.7.1-1", | ||
"@types/tough-cookie": "^4.0.2", | ||
"dashtx": "^0.9.0-3" | ||
}, | ||
"dependencies": {} | ||
"@types/tough-cookie": "^4.0.2" | ||
} | ||
} |
@@ -7,12 +7,6 @@ # [dashsight.js](https://github.com/dashhive/dashsight.js) | ||
```sh | ||
npm install --save dashsight@1.x | ||
```bash | ||
npm install --save dashsight | ||
``` | ||
To use `WebSocket`s in Node.js: | ||
```sh | ||
npm install --save tough-cookie@4.x ws@8.x | ||
``` | ||
# Usage | ||
@@ -298,80 +292,8 @@ | ||
Send a signed transaction to Dash's Insight API for relay and broadcast to the | ||
Send a _signed transaction_ to Dash's Insight API for relay and broadcast to the | ||
Dash network. | ||
See **full examples** in: | ||
- [./examples/balance-transfer.js](/examples/balance-transfer.js). | ||
- [./examples/multi-send.js](/examples/multi-send.js). | ||
Abridged Example: | ||
```js | ||
"use strict"; | ||
let txHex = 'xxxxxxxx...'; | ||
let DashTx = require("dashtx"); | ||
let dashTx = DashTx.create({ | ||
version: 3, | ||
sign: signTx, | ||
toPublicKey: toPublicKey, | ||
addrToPubKeyHash: addrToPubKeyHash, | ||
}); | ||
async function signTx({ privateKey, hash }) { | ||
let sigOpts = { canonical: true }; | ||
let sigBuf = await Secp256k1.sign(hash, privateKey, sigOpts); | ||
return sigBuf; | ||
} | ||
async function toPublicKey(privKeyBuf) { | ||
let Secp256k1 = require("@dashincubator/secp256k1"); | ||
let isCompressed = true; | ||
let pubBuf = Secp256k1.getPublicKey(privKeyBuf, isCompressed); | ||
return pubBuf; | ||
} | ||
async function addrToPubKeyHash(addr) { | ||
let Base58Check = require("@dashincubator/base58check").Base58Check; | ||
let b58c = Base58Check.create({ | ||
pubKeyHashVersion: "4c", | ||
privateKeyVersion: "cc", | ||
}); | ||
let parts = await b58c.verify(addr); | ||
return parts.pubKeyHash; | ||
} | ||
// keys that correspond to the available utxos | ||
let privateKeys = { | ||
XmCyQ6qARLWXap74QubFMunngoiiA1QgCL: "YOUR_PRIVATE_KEY_HERE", | ||
}; | ||
let coreUtxos = [ | ||
{ | ||
address: "XmCyQ6qARLWXap74QubFMunngoiiA1QgCL", | ||
outputIndex: 0, | ||
satoshis: 99809, | ||
script: "76a91473640d816ff4161d8c881da78983903bf9eba2d988ac", | ||
txId: "f92e66edc9c8da41de71073ef08d62c56f8752a3f4e29ced6c515e0b1c074a38", | ||
}, | ||
]; | ||
let payments = [ | ||
{ address: `Xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx`, satoshis: 10000000 }, | ||
]; | ||
let txInfo = { | ||
inputs: coreUtxos, | ||
outputs: payments, | ||
}; | ||
let keys = coreUtxos.map(function (utxo) { | ||
let privHex = privateKeys[utxo.address]; | ||
let privBuf = Tx.utils.hexToU8(privHex); | ||
return privBuf; | ||
}); | ||
let tx = dashTx.hashAndSignAll(txInfo, keys); | ||
let txHex = tx.transaction; | ||
let result = await dashsight.instantSend(txHex); | ||
@@ -382,7 +304,6 @@ | ||
Example transaction hex: | ||
Example transaction hex (input): \ | ||
(inspect at <https://live.blockcypher.com/dash/decodetx/>) | ||
```txt | ||
```text | ||
030000000187ab81e88e2c19ca354f33f14d5b43b60d171ac851eb97dddd271b510cadbdb0000000 | ||
@@ -400,1 +321,7 @@ 006b483045022100ec38c77b9f285d4c9aeeba36c1fac51bb88f7443185caf7eec21b170cc5d4062 | ||
``` | ||
Guides & Code Examples for creating and signing `txHex`: | ||
- [How to create a txHex with DashTx + DashKeys](https://github.com/dashhive/DashSight.js/issues/27) | ||
- [Balance Transfer + DashSight: ./examples/balance-transfer.js](/examples/balance-transfer.js). | ||
- [Multi-Payout + DashSight: ./examples/multi-send.js](/examples/multi-send.js). |
"use strict"; | ||
/** @type {import('../').CookieStore} */ | ||
/** @type CookieStore */ | ||
let Cookies = module.exports; | ||
@@ -11,5 +11,3 @@ | ||
let jar = new Cookie.CookieJar(/*cookies_store*/); | ||
//@ts-ignore | ||
jar.setCookieAsync = require("util").promisify(jar.setCookie); | ||
//@ts-ignore | ||
jar.getCookiesAsync = require("util").promisify(jar.getCookies); | ||
@@ -24,25 +22,19 @@ //cookies_store.saveAsync = require("util").promisify(cookies_store.save); | ||
Cookies.set = async function _setCookie(url, resp) { | ||
/** @type {Array<String>} */ | ||
let cookies; | ||
let moreCookies = resp.headers["set-cookie"]; | ||
if (!moreCookies) { | ||
return; | ||
if (resp.headers["set-cookie"]) { | ||
if (Array.isArray(resp.headers["set-cookie"])) { | ||
cookies = resp.headers["set-cookie"].map(Cookie.parse); | ||
} else { | ||
cookies = [Cookie.parse(resp.headers["set-cookie"])]; | ||
} | ||
} | ||
if (!Array.isArray(moreCookies)) { | ||
moreCookies = [moreCookies]; | ||
} | ||
//@ts-ignore | ||
cookies = moreCookies.map(Cookie.parse); | ||
// let Cookie = //require('set-cookie-parser'); | ||
// Cookie.parse(resp, { decodeValues: true }); | ||
let ps = cookies.map(async function (cookie) { | ||
//console.log('DEBUG cookie:', cookie.toJSON()); | ||
let jarOpts = { now: new Date() }; | ||
//@ts-ignore | ||
await jar.setCookieAsync(cookie, url, jarOpts); | ||
}); | ||
await Promise.all(ps); | ||
await Promise.all( | ||
cookies.map(async function (cookie) { | ||
//console.log('DEBUG cookie:', cookie.toJSON()); | ||
await jar.setCookieAsync(cookie, url, { now: new Date() }); | ||
}), | ||
); | ||
//await cookies_store.saveAsync(); | ||
@@ -56,6 +48,3 @@ }; | ||
Cookies.get = async function _getCookie(url) { | ||
//@ts-ignore | ||
let cookieObj = await jar.getCookiesAsync(url); | ||
let cookieStr = cookieObj.toString(); | ||
return cookieStr; | ||
return (await jar.getCookiesAsync(url)).toString(); | ||
}; |
189
ws/index.js
@@ -12,3 +12,3 @@ "use strict"; | ||
* @prop {String} [baseUrl] - (deprecated by dashsocketBaseUrl) ex: https://insight.dash.org | ||
* @prop {import('../').CookieStore} cookieStore - only needed for insight APIs hosted behind an AWS load balancer | ||
* @prop {CookieStore} cookieStore - only needed for insight APIs hosted behind an AWS load balancer | ||
* @prop {Boolean} debug | ||
@@ -52,15 +52,18 @@ * @prop {Function} onClose | ||
let cookiesStr = await cookieStore.get(sidUrl); | ||
let sidResp = await Ws.fetch(sidUrl, { | ||
let cookies = await cookieStore.get(sidUrl); | ||
let sidResp = await fetch(sidUrl, { | ||
//agent: httpAgent, | ||
//@ts-ignore - request function is not typed correctly | ||
headers: { | ||
Cookie: cookiesStr, | ||
Cookie: cookies, | ||
}, | ||
}); | ||
if (!sidResp.ok) { | ||
console.error(await sidResp.json()); | ||
throw new Error("bad response"); | ||
} | ||
await cookieStore.set(sidUrl, sidResp); | ||
// ex: `97:0{"sid":"xxxx",...}` | ||
let msg = sidResp.body || ""; | ||
let msg = await sidResp.json(); | ||
let colonIndex = msg.indexOf(":"); | ||
@@ -97,4 +100,4 @@ // 0 is CONNECT, which will always follow our first message | ||
let cookiesStr = await cookieStore.get(subUrl); | ||
let subResp = await Ws.fetch(subUrl, { | ||
let cookies = await cookieStore.get(subUrl); | ||
let subResp = await fetch(subUrl, { | ||
//agent: httpAgent, | ||
@@ -104,11 +107,14 @@ method: "POST", | ||
"Content-Type": "text/plain;charset=UTF-8", | ||
Cookie: cookiesStr, | ||
Cookie: cookies, | ||
}, | ||
body: body, | ||
}); | ||
if (!subResp.ok) { | ||
console.error(await subResp.json()); | ||
throw new Error("bad response"); | ||
} | ||
await cookieStore.set(subUrl, subResp); | ||
// "ok" | ||
return subResp.body; | ||
return await subResp.json(); | ||
}; | ||
@@ -148,5 +154,4 @@ | ||
let url = `ws${dashsocketBaseUrlPart}/?EIO=3&transport=websocket&sid=${sid}`; | ||
let sidUrl = `${dashsocketBaseUrl}/`; | ||
let cookiesStr = await cookieStore.get(sidUrl); | ||
let cookies = await cookieStore.get(`${dashsocketBaseUrl}/`); | ||
let ws = new WSClient(url, { | ||
@@ -157,3 +162,3 @@ //agent: httpAgent, | ||
headers: { | ||
Cookie: cookiesStr, | ||
Cookie: cookies, | ||
}, | ||
@@ -173,23 +178,8 @@ }); | ||
onError(err); | ||
return; | ||
} else { | ||
console.error("WebSocket Error:"); | ||
console.error(err); | ||
} | ||
console.error("WebSocket Error:"); | ||
console.error(err); | ||
}); | ||
ws.once("unexpected-response", function (req, res) { | ||
let err = new Error("unexpected-response"); | ||
//@ts-ignore | ||
err.response = res; | ||
if (onError) { | ||
onError(err); | ||
return; | ||
} | ||
console.error("WebSocket Unexpected Response:"); | ||
console.error(err); | ||
}); | ||
ws.once("message", function message(data) { | ||
@@ -281,3 +271,3 @@ if ("3probe" === data.toString()) { | ||
/** @type {import('../').InsightPush} */ | ||
/** @type {InsightPush} */ | ||
let [evname, data] = JSON.parse(msg.slice(2)); | ||
@@ -324,3 +314,3 @@ if (onMessage) { | ||
* @param {String} evname | ||
* @param {import('../').InsightSocketEventData} data | ||
* @param {InsightSocketEventData} data | ||
*/ | ||
@@ -381,4 +371,4 @@ | ||
* @param {Number} [maxTxLockWait] | ||
* @param {Partial<WsOpts>} [opts] | ||
* @returns {Promise<import('../').SocketPayment>} | ||
* @param {WsOpts} [opts] | ||
* @returns {Promise<SocketPayment>} | ||
*/ | ||
@@ -397,3 +387,3 @@ Ws.waitForVout = async function ( | ||
// Listen for Response | ||
/** @type {import('../').SocketPayment} */ | ||
/** @type SocketPayment */ | ||
let mempoolTx; | ||
@@ -404,3 +394,3 @@ return await Ws.listen(dashsocketBaseUrl, findResponse, opts); | ||
* @param {String} evname | ||
* @param {import('../').InsightSocketEventData} data | ||
* @param {InsightSocketEventData} data | ||
*/ | ||
@@ -422,33 +412,30 @@ function findResponse(evname, data) { | ||
// TODO should fetch tx and match hotwallet as vin | ||
data.vout.some( | ||
/** @param {Record<String,Number>} vout */ | ||
function (vout) { | ||
if (!(addr in vout)) { | ||
return false; | ||
} | ||
data.vout.some(function (vout) { | ||
if (!(addr in vout)) { | ||
return false; | ||
} | ||
let duffs = vout[addr]; | ||
if (amount && duffs !== amount) { | ||
return false; | ||
} | ||
let duffs = vout[addr]; | ||
if (amount && duffs !== amount) { | ||
return false; | ||
} | ||
let newTx = { | ||
address: addr, | ||
timestamp: now, | ||
txid: data.txid, | ||
satoshis: duffs, | ||
txlock: data.txlock, | ||
}; | ||
let newTx = { | ||
address: addr, | ||
timestamp: now, | ||
txid: data.txid, | ||
satoshis: duffs, | ||
txlock: data.txlock, | ||
}; | ||
if ("txlock" !== evname) { | ||
if (!mempoolTx) { | ||
mempoolTx = newTx; | ||
} | ||
return false; | ||
if ("txlock" !== evname) { | ||
if (!mempoolTx) { | ||
mempoolTx = newTx; | ||
} | ||
return false; | ||
} | ||
result = newTx; | ||
return true; | ||
}, | ||
); | ||
result = newTx; | ||
return true; | ||
}); | ||
@@ -459,76 +446,2 @@ return result; | ||
/** @type {RequestInit} */ | ||
let defaultRequest = { | ||
mode: "cors", | ||
credentials: "include", | ||
}; | ||
/** | ||
* @param {String | URL | Request} url | ||
* @param {RequestInit} [_opts] | ||
*/ | ||
Ws.fetch = async function dashfetch(url, _opts) { | ||
let opts = Object.assign(defaultRequest, _opts); | ||
let resp = await fetch(url, opts); | ||
/** @type {Record<String,String|Array<String>>} */ | ||
let headers = {}; | ||
// for the Set-Cookie headers through AWS load balancer | ||
let headerEntries = resp.headers.entries(); | ||
for (let [key, value] of headerEntries) { | ||
if (!headers[key]) { | ||
headers[key] = value; | ||
continue; | ||
} | ||
let isArray = Array.isArray(headers[key]); | ||
if (!isArray) { | ||
//@ts-ignore | ||
headers[key] = [headers[key]]; | ||
} | ||
//@ts-ignore | ||
headers[key].push(value); | ||
} | ||
let body = await resp.text(); | ||
let response = { | ||
ok: resp.ok, | ||
statusCode: resp.status, // backwards compat | ||
statusText: resp.statusText, | ||
headers: headers, | ||
body: body, | ||
toJSON: function () { | ||
return { | ||
ok: response.ok, | ||
statusCode: response.statusCode, | ||
statusText: response.statusText, | ||
headers: response.headers, | ||
body: response.body, | ||
}; | ||
}, | ||
get status() { | ||
console.warn( | ||
"deprecated: please use either 'statusText' or 'statusCode' (node.js and browser both have 'status', but flipped)", | ||
); | ||
return resp.statusText; | ||
}, | ||
_request: opts, | ||
_response: resp, | ||
}; | ||
if (resp.ok) { | ||
return response; | ||
} | ||
let err = new Error( | ||
`http request was ${resp.status}, not ok. See err.response for details.`, | ||
); | ||
// @ts-ignore | ||
err.response = response; | ||
throw err; | ||
}; | ||
/* | ||
@@ -535,0 +448,0 @@ async function sleep(ms) { |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
2
4
72685
2187
324
+ Addeddashtx@^0.9.0-3
+ Addeddashtx@0.9.0(transitive)
- Removedpsl@1.9.0(transitive)
- Removedpunycode@2.3.1(transitive)
- Removedquerystringify@2.2.0(transitive)
- Removedrequires-port@1.0.0(transitive)
- Removedtough-cookie@4.1.4(transitive)
- Removeduniversalify@0.2.0(transitive)
- Removedurl-parse@1.5.10(transitive)
- Removedws@8.18.0(transitive)