@celo/network-utils
Version:
Utilities for fetching static information about the Celo network
122 lines • 5.89 kB
JavaScript
;
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.StaticNodeUtils = void 0;
const debug_1 = __importDefault(require("debug"));
const google_storage_utils_1 = require("./google-storage-utils");
const timezone_1 = require("./utils/timezone");
const debug = (0, debug_1.default)('network-utils:static-node-utils');
// The bucket where we store static_nodes information for all the networks.
const StaticNodesGoogleStorageBucketName = `static_nodes`;
/**
* Checks whether the given coordinates are in the given region.
* @remarks Latitudes are assumed to be normalized to the range [-90, 90],
* and longitudes to the range [-180, 180].
*/
function inRegion(coords, region) {
// Check that x in is the range, wrapping if range min is greater than the max.
const rangeCheck = (x, range) => range === undefined ||
(range.min <= range.max ? range.min <= x && x < range.max : range.min <= x || x < range.max);
return (rangeCheck(coords.latitude, region.latitude) && rangeCheck(coords.longitude, region.longitude));
}
/**
* Region names for groups of static nodes deployed around the world for each network.
* Used as a suffix to the blob name when fetching to get region specific nodes.
*/
const mainnetRegions = [
{
name: 'gcp-asia-east1',
longitude: { min: 60, max: -170 },
},
{
name: 'gcp-europe-west1',
longitude: { min: -25, max: 60 },
},
{
name: 'gcp-southamerica-east1',
latitude: { min: -90, max: 0 },
longitude: { min: -170, max: -25 },
},
{
name: 'gcp-us-east1',
latitude: { min: 0, max: 90 },
longitude: { min: -105, max: -25 },
},
{
name: 'gcp-us-west1',
latitude: { min: 0, max: 90 },
longitude: { min: -170, max: -105 },
},
];
const StaticNodeRegions = {
mainnet: mainnetRegions,
// Alias for mainnet
rc1: mainnetRegions,
};
class StaticNodeUtils {
static getStaticNodesGoogleStorageBucketName() {
return StaticNodesGoogleStorageBucketName;
}
/**
* Resolves the best region to use for static node connections.
* @param networkName Name of the network to get a region for.
* @remarks This method currently uses the interpreter's timezone and the
* IANA timezone database to establish what region of the world the client is
* in, then map that to a static list of static node clusters run by cLabs.
* If the timezone is not set according to the user's location, this method
* may route them to suboptimal set of static nodes. The resolution method
* may be replaced in the future.
*/
static getStaticNodeRegion(networkName, tz) {
var _a, _b, _c;
// Get the latitude and longitude of the timezone locations.
// Note: This is the location of the city that the user has the timzone set to.
const tzInfo = (0, timezone_1.timezone)(tz);
const coords = tzInfo === null || tzInfo === void 0 ? void 0 : tzInfo.coordinates;
if (coords === undefined) {
debug('Could not resolve region from timezone %s', tzInfo === null || tzInfo === void 0 ? void 0 : tzInfo.name);
return ''; // Use the default region of static nodes
}
const regions = (_a = StaticNodeRegions[networkName]) !== null && _a !== void 0 ? _a : [];
const result = (_c = (_b = regions.find((region) => inRegion(coords, region))) === null || _b === void 0 ? void 0 : _b.name) !== null && _c !== void 0 ? _c : '';
debug('Resolved region %q from timezone %s', result, tzInfo === null || tzInfo === void 0 ? void 0 : tzInfo.name);
return result;
}
/**
* Fetches the static nodes (as JSON data) from Google Storage corresponding
* to the best available region for this caller.
* If the network is not working, the method will reject the returned promise
* along with the response data from Google API.
* @param networkName Name of the network to fetch config for
*/
static getRegionalStaticNodesAsync(networkName, region) {
const resolvedRegion = region !== null && region !== void 0 ? region : this.getStaticNodeRegion(networkName);
const bucketName = StaticNodesGoogleStorageBucketName;
const fileName = resolvedRegion ? `${networkName}.${resolvedRegion}` : networkName;
return google_storage_utils_1.GoogleStorageUtils.fetchFileFromGoogleStorage(bucketName, fileName);
}
/**
* Fetches the static nodes (as JSON data) from Google Storage.
* If the network is not working, the method will reject the returned promise
* along with the response data from Google API.
* @param networkName Name of the network to fetch config for
*/
static getStaticNodesAsync(networkName) {
return __awaiter(this, void 0, void 0, function* () {
return this.getRegionalStaticNodesAsync(networkName, '');
});
}
}
exports.StaticNodeUtils = StaticNodeUtils;
//# sourceMappingURL=static-node-utils.js.map