node-darts
Version:
Node.js Native Addon for Darts (Double-ARray Trie System)
310 lines • 12.8 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 __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
o["default"] = v;
});
var __importStar = (this && this.__importStar) || (function () {
var ownKeys = function(o) {
ownKeys = Object.getOwnPropertyNames || function (o) {
var ar = [];
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
return ar;
};
return ownKeys(o);
};
return function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
__setModuleDefault(result, mod);
return result;
};
})();
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.dartsNative = exports.DartsNativeWrapper = void 0;
const bindings_1 = __importDefault(require("bindings"));
const fs = __importStar(require("fs"));
const path = __importStar(require("path"));
const errors_1 = require("./errors");
// Load native module
let native;
try {
// Try standard bindings approach first
native = (0, bindings_1.default)('node_darts');
}
catch (originalError) {
// Only attempt fallback in Windows CI environment
const isWindows = process.platform === 'win32';
const isCI = process.env.CI === 'true' || process.env.GITHUB_ACTIONS === 'true';
if (isWindows && isCI) {
console.warn(`WARNING: Failed to load native module using standard bindings in Windows CI environment: ${originalError}`);
console.warn('Attempting to use fallback mechanism to locate the module...');
// Try to find the module in common locations
const possiblePaths = [
// Standard build paths
path.join(process.cwd(), 'build', 'Release', 'node_darts.node'),
path.join(process.cwd(), 'build', 'Debug', 'node_darts.node'),
path.join(process.cwd(), 'build', 'node_darts.node'),
path.join(process.cwd(), 'build', 'default', 'node_darts.node'),
// Output paths
path.join(process.cwd(), 'out', 'Release', 'node_darts.node'),
path.join(process.cwd(), 'out', 'Debug', 'node_darts.node'),
// Direct paths
path.join(process.cwd(), 'Release', 'node_darts.node'),
path.join(process.cwd(), 'Debug', 'node_darts.node'),
// Addon build paths
path.join(process.cwd(), 'addon-build', 'release', 'install-root', 'node_darts.node'),
path.join(process.cwd(), 'addon-build', 'debug', 'install-root', 'node_darts.node'),
path.join(process.cwd(), 'addon-build', 'default', 'install-root', 'node_darts.node'),
// Node version specific paths
path.join(process.cwd(), 'lib', 'binding', `node-v${process.versions.modules}-${process.platform}-${process.arch}`, 'node_darts.node'),
path.join(process.cwd(), 'compiled', process.version.slice(1), process.platform, process.arch, 'node_darts.node'),
// Legacy paths
path.join(process.cwd(), 'build', 'lib', 'binding', 'node_darts.node'),
path.join(process.cwd(), 'lib', 'binding', 'node-v115-win32-x64', 'node_darts.node'),
];
// Log all paths we're checking
console.warn('Checking the following paths:');
possiblePaths.forEach((p) => console.warn(` - ${p}`));
// Initialize a variable to track if we found the module
let foundModule = false;
// Use forEach instead of for...of to satisfy ESLint
possiblePaths.forEach((modulePath) => {
if (!foundModule && fs.existsSync(modulePath)) {
console.warn(`Found native module at: ${modulePath}`);
try {
// We need to use dynamic require here, but ESLint doesn't like it
// So we'll disable the relevant rules for this specific line
// eslint-disable-next-line @typescript-eslint/no-require-imports, @typescript-eslint/no-var-requires, import/no-dynamic-require, global-require
const dynamicModule = require(modulePath);
native = dynamicModule;
foundModule = true;
console.warn('Successfully loaded native module using fallback mechanism');
}
catch (requireError) {
console.warn(`Failed to require module at ${modulePath}: ${requireError}`);
}
}
});
if (!foundModule) {
console.error('ERROR: Native module not found in any alternative paths');
throw new Error(`Failed to load native module using fallback mechanism. Original error: ${originalError}`);
}
}
else {
// In non-Windows or non-CI environments, just throw the original error
throw originalError;
}
}
/**
* Wrapper class for native module
* Adds error handling and provides a TypeScript-friendly interface
*/
class DartsNativeWrapper {
/**
* Creates a dictionary object
* @returns dictionary handle
*/
// eslint-disable-next-line class-methods-use-this
createDictionary() {
try {
const handle = native.createDictionary();
if (handle === null || handle === undefined) {
throw new errors_1.DartsError('Failed to create dictionary');
}
return handle;
}
catch (error) {
if (error instanceof errors_1.DartsError) {
throw error;
}
throw new errors_1.DartsError(`Failed to create dictionary: ${error instanceof Error ? error.message : String(error)}`);
}
}
/**
* Destroys a dictionary object
* @param handle dictionary handle
*/
// eslint-disable-next-line class-methods-use-this
destroyDictionary(handle) {
try {
native.destroyDictionary(handle);
}
catch (error) {
throw new errors_1.DartsError(`Failed to destroy dictionary: ${error instanceof Error ? error.message : String(error)}`);
}
}
/**
* Loads a dictionary file
* @param handle dictionary handle
* @param filePath path to the dictionary file
* @returns true if successful, false otherwise
*/
// eslint-disable-next-line class-methods-use-this
loadDictionary(handle, filePath) {
// Check if the file exists
if (!fs.existsSync(filePath)) {
throw new errors_1.FileNotFoundError(filePath);
}
try {
const result = native.loadDictionary(handle, filePath);
if (result === false) {
throw new errors_1.InvalidDictionaryError(`Failed to load dictionary from ${filePath}`);
}
return result;
}
catch (error) {
if (error instanceof errors_1.DartsError) {
throw error;
}
// Detect file not found error from error message
const errorMessage = error instanceof Error ? error.message : String(error);
if (errorMessage.includes('not found') || errorMessage.includes('No such file')) {
throw new errors_1.FileNotFoundError(filePath);
}
throw new errors_1.InvalidDictionaryError(errorMessage);
}
}
/**
* Saves a dictionary file
* @param handle dictionary handle
* @param filePath destination file path
* @returns true if successful, false otherwise
*/
// eslint-disable-next-line class-methods-use-this
saveDictionary(handle, filePath) {
try {
const result = native.saveDictionary(handle, filePath);
if (result === false) {
throw new errors_1.DartsError(`Failed to save dictionary to ${filePath}`);
}
return result;
}
catch (error) {
if (error instanceof errors_1.DartsError) {
throw error;
}
throw new errors_1.DartsError(`Failed to save dictionary: ${error instanceof Error ? error.message : String(error)}`);
}
}
/**
* Performs an exact match search
* @param handle dictionary handle
* @param key search key
* @returns the corresponding value if found, -1 otherwise
*/
// eslint-disable-next-line class-methods-use-this
exactMatchSearch(handle, key) {
try {
return native.exactMatchSearch(handle, key);
}
catch (error) {
throw new errors_1.DartsError(`Failed to perform exact match search: ${error instanceof Error ? error.message : String(error)}`);
}
}
/**
* Performs a common prefix search
* @param handle dictionary handle
* @param key search key
* @returns array of found values
*/
// eslint-disable-next-line class-methods-use-this
commonPrefixSearch(handle, key) {
try {
return native.commonPrefixSearch(handle, key);
}
catch (error) {
throw new errors_1.DartsError(`Failed to perform common prefix search: ${error instanceof Error ? error.message : String(error)}`);
}
}
/**
* Traverses the trie
* @param handle dictionary handle
* @param key search key
* @param callback callback function
*/
// eslint-disable-next-line class-methods-use-this
traverse(handle, key, callback) {
try {
native.traverse(handle, key, callback);
}
catch (error) {
throw new errors_1.DartsError(`Failed to traverse: ${error instanceof Error ? error.message : String(error)}`);
}
}
/**
* Builds a Double-Array
* @param keys array of keys
* @param values array of values (indices are used if omitted)
* @returns dictionary handle
*/
// eslint-disable-next-line class-methods-use-this
build(keys, values) {
try {
if (!Array.isArray(keys) || keys.length === 0) {
throw new errors_1.BuildError('Empty keys array');
}
// Ensure keys are strings
keys.forEach((key) => {
if (typeof key !== 'string') {
throw new errors_1.BuildError('All keys must be strings');
}
});
// Ensure values are numbers
if (values !== undefined) {
if (!Array.isArray(values) || values.length !== keys.length) {
throw new errors_1.BuildError('Values array length must match keys array length');
}
values.forEach((value) => {
if (typeof value !== 'number') {
throw new errors_1.BuildError('All values must be numbers');
}
});
}
const handle = native.build(keys, values);
if (handle === null || handle === undefined) {
throw new errors_1.BuildError('Failed to build dictionary');
}
return handle;
}
catch (error) {
if (error instanceof errors_1.DartsError) {
throw error;
}
throw new errors_1.BuildError(error instanceof Error ? error.message : String(error));
}
}
/**
* Gets the size of the dictionary
* @param handle dictionary handle
* @returns size of the dictionary
*/
// eslint-disable-next-line class-methods-use-this
size(handle) {
try {
return native.size(handle);
}
catch (error) {
throw new errors_1.DartsError(`Failed to get dictionary size: ${error instanceof Error ? error.message : String(error)}`);
}
}
}
exports.DartsNativeWrapper = DartsNativeWrapper;
// Export singleton instance
exports.dartsNative = new DartsNativeWrapper();
//# sourceMappingURL=native.js.map