@btc-helpers/rpc
Version:
A somewhat typesafe Bitcoin RPC library
119 lines (117 loc) • 3.49 kB
JavaScript
;
var __defProp = Object.defineProperty;
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
var __getOwnPropNames = Object.getOwnPropertyNames;
var __hasOwnProp = Object.prototype.hasOwnProperty;
var __export = (target, all) => {
for (var name in all)
__defProp(target, name, { get: all[name], enumerable: true });
};
var __copyProps = (to, from, except, desc) => {
if (from && typeof from === "object" || typeof from === "function") {
for (let key of __getOwnPropNames(from))
if (!__hasOwnProp.call(to, key) && key !== except)
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
}
return to;
};
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
// lib/index.ts
var lib_exports = {};
__export(lib_exports, {
default: () => RpcClient
});
module.exports = __toCommonJS(lib_exports);
var import_polyfill = require("cross-fetch/polyfill");
var import_base = require("@scure/base");
var RpcClient = class {
hostname;
port;
protocol;
auth;
constructor(opts) {
if (typeof opts === "string") {
opts = decodeUrl(opts);
}
const defaultOptions = {
host: "127.0.0.1",
port: 8332,
user: "devnet",
pass: "devnet",
protocol: "http"
};
const options = Object.assign(defaultOptions, opts || {});
this.hostname = options.host;
this.port = options.port;
this.protocol = options.protocol;
this.auth = import_base.base64.encode(
new TextEncoder().encode(`${options.user}:${options.pass}`)
);
}
get Typed() {
return new Proxy(this, {
get(target, property, receiver) {
if (property in target)
return Reflect.get(target, property, receiver);
return async function(params) {
return await target.call({
jsonrpc: "2.0",
method: property.toString().toLowerCase(),
params,
id: getRandomId()
});
};
}
});
}
async call(body) {
const options = {
method: "POST",
headers: {
Authorization: `Basic ${this.auth}`,
"Content-Type": "application/json"
},
body: JSON.stringify(body)
};
const errorPrefix = "Bitcoin JSON-RPC: ";
const res = await fetch(
`${this.protocol}//${this.hostname}:${this.port}`,
options
);
if (res.status === 401) {
throw new Error(errorPrefix + "Connection Rejected: 401 Unnauthorized");
}
if (res.status === 403) {
throw new Error(errorPrefix + "Connection Rejected: 403 Forbidden");
}
const text = await res.text();
if (res.status === 500) {
if (text === "Work queue depth exceeded") {
const exceededError = new Error(errorPrefix + text);
exceededError.code = 429;
throw exceededError;
}
}
const json = JSON.parse(text);
if (!res.ok)
throw new Error(
`${errorPrefix}${json?.error?.code} ${json?.error?.message}`
);
return json.result;
}
};
function decodeUrl(url) {
const parsedUrl = new URL(url);
return {
host: parsedUrl.hostname,
port: parseInt(parsedUrl.port, 10),
protocol: parsedUrl.protocol,
user: parsedUrl.username,
pass: parsedUrl.password
};
}
function getRandomId() {
return parseInt(Math.random() * 1e5);
}
// Annotate the CommonJS export names for ESM import in node:
0 && (module.exports = {});