2013-06-12 4 views
6

Друг задал интересный вопрос, и я пробовал несколько вещей, но безрезультатно, есть ли способ переопределить модуль Node JS?Node JS переопределить стандартный модуль

Например, я хочу переопределить функцию readFile, чтобы использовать ведро S3 вместо файловой системы. IE:

var fs = require('fs'); 

fs.readFile('my_text_file.txt', ...); 

На самом деле работает что-то вроде этого

FileSystem.readFile = function() { 
    // Connect to S3 and retrieve remote file 
} 

Я попытался прототип, но, кажется, они создали собственные модули без __proto__ объекта, они не имеют .constructor недвижимости это означает что угодно кому угодно.

Я думал об использовании Nodes VM, но это слишком строго, так как я хочу, чтобы пользователь мог устанавливать модули через npm и использовать их.

Ближайший я на самом деле пришел создаю новый модуль (так как я не могу поместить файл с именем fs.js в моей node_modules папки и требую ее, она просто игнорируется) и просто жесткой установку значения fs в что я хочу, но это не совсем правильно, я хочу, чтобы пользователь использовал require('fs') и использовал свою пользовательскую функцию.

Возможно ли это без компиляции собственной версии Node JS?

+0

Я не работал с node.js, так что это может вообще не работать. Вы можете попытаться увидеть, какая функция объявляет 'FileSystem', а затем использовать это как прототип для вашего настраиваемого объекта (« подкласс »). MyFS = {FileSystem.call (this);}; MyFs.prototype = new FileSystem(); Или используйте что-то вроде goog.base и goog.inherit для создания подкласса, который может вызывать его «родительские» функции и имеет дело с параметрами, переданными конструктору: http://docs.closure-library.googlecode.com/git/closure_goog_base. js.html Обратите внимание, что badse использует 'arguments.callee.caller', который не работает в ecma 5 strict, поэтому вам нужно его написать. – HMR

+0

Хорошая статья о goog.base и goog.inherits находится здесь: http://bolinfest.com/essays/googbase.html – HMR

+0

Я создал 'FileSystem' для иллюстративных целей, модули не имеют объекта' __proto__' и таким образом, никакого конструктора. Самое близкое, что я получил, - это прямое задание свойств объекта и включение другого скрипта, но я хочу «потребовать (« fs »)», и у него есть мои пользовательские функции. –

ответ

11

Я чувствую себя обязанным решительно предупреждать вас об отказе от нативных функций. Это, как говорится, это будет работать:

main.js:

var fs = require('fs'), 
    oldReadFile = fs.readFile; 

fs.readFile = function (filename, options, callback) { 
    console.log('hey!'); 
    oldReadFile(filename, options, callback) 
}; 

var other = require('./other'); 
other.test(); 

other.js:

var fs = require('fs'); 

exports.test = function() { 
    fs.readFile('./main.js', {encoding: 'utf8'}, function (err, data) { 
    console.log(err, data); 
    }); 
}; 

Вам нужно обернуть сценарий вашего пользователя с вашим собственным сначала переопределить то, что вы хотите.

+0

+1 Для предупреждения. Не связывайтесь с базовыми модулями. – aggsol

+0

Я знаю, я бы не стал лично. Не по крайней мере без 'vm', но это интересный вопрос. Это, тем не менее, то же, что и я уже пробовал, и не совсем то, что он хочет. –

+0

@Laurent какой-либо конкретной причины, чтобы избежать переопределения собственных функций? Я планирую сделать что-то подобное переопределению чтения и записи базы данных. – DanMatlin

Смежные вопросы