maxmind
Version:
IP lookup using Maxmind databases
118 lines • 4.55 kB
JavaScript
;
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
var desc = Object.getOwnPropertyDescriptor(m, k);
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
desc = { enumerable: true, get: function() { return m[k]; } };
}
Object.defineProperty(o, k2, desc);
}) : (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
o[k2] = m[k];
}));
var __exportStar = (this && this.__exportStar) || function(m, exports) {
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
};
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.Reader = exports.validate = exports.init = exports.openSync = exports.open = void 0;
const assert_1 = __importDefault(require("assert"));
const mmdb_lib_1 = require("mmdb-lib");
Object.defineProperty(exports, "Reader", { enumerable: true, get: function () { return mmdb_lib_1.Reader; } });
const tiny_lru_1 = require("tiny-lru");
const fs_1 = __importDefault(require("./fs"));
const ip_1 = __importDefault(require("./ip"));
const is_gzip_1 = __importDefault(require("./is-gzip"));
const utils_1 = __importDefault(require("./utils"));
const LARGE_FILE_THRESHOLD = 512 * 1024 * 1024;
const STREAM_WATERMARK = 8 * 1024 * 1024;
const readLargeFile = async (filepath, size) => new Promise((resolve, reject) => {
let buffer = Buffer.allocUnsafe(size);
let offset = 0;
const stream = fs_1.default.createReadStream(filepath, {
highWaterMark: STREAM_WATERMARK,
});
stream.on('data', (chunk) => {
if (Buffer.isBuffer(chunk)) {
chunk.copy(buffer, offset);
offset += chunk.length;
}
else {
const bufferChunk = Buffer.from(chunk);
bufferChunk.copy(buffer, offset);
offset += bufferChunk.length;
}
});
stream.on('end', () => {
stream.close();
resolve(buffer);
});
stream.on('error', (err) => {
reject(err);
});
});
const readFile = async (filepath) => {
const fstat = await fs_1.default.stat(filepath);
return fstat.size < LARGE_FILE_THRESHOLD
? fs_1.default.readFile(filepath)
: readLargeFile(filepath, fstat.size);
};
const open = async (filepath, opts, cb) => {
(0, assert_1.default)(!cb, utils_1.default.legacyErrorMessage);
const database = await readFile(filepath);
if ((0, is_gzip_1.default)(database)) {
throw new Error('Looks like you are passing in a file in gzip format, please use mmdb database instead.');
}
const cache = (0, tiny_lru_1.lru)(opts?.cache?.max || 10000);
const reader = new mmdb_lib_1.Reader(database, { cache });
if (opts && !!opts.watchForUpdates) {
if (opts.watchForUpdatesHook &&
typeof opts.watchForUpdatesHook !== 'function') {
throw new Error('opts.watchForUpdatesHook should be a function');
}
const watcherOptions = {
persistent: opts.watchForUpdatesNonPersistent !== true,
};
fs_1.default.watchFile(filepath, watcherOptions, async () => {
const waitExists = async () => {
for (let i = 0; i < 3; i++) {
if (fs_1.default.existsSync(filepath)) {
return true;
}
await new Promise((a) => setTimeout(a, 500));
}
return false;
};
if (!(await waitExists())) {
return;
}
const updatedDatabase = await readFile(filepath);
cache.clear();
reader.load(updatedDatabase);
if (opts.watchForUpdatesHook) {
opts.watchForUpdatesHook();
}
});
}
return reader;
};
exports.open = open;
const openSync = () => {
throw new Error(utils_1.default.legacyErrorMessage);
};
exports.openSync = openSync;
const init = () => {
throw new Error(utils_1.default.legacyErrorMessage);
};
exports.init = init;
exports.validate = ip_1.default.validate;
__exportStar(require("mmdb-lib"), exports);
exports.default = {
init: exports.init,
open: exports.open,
openSync: exports.openSync,
validate: ip_1.default.validate,
};
//# sourceMappingURL=index.js.map