2012-08-23 40 views
5

node.js中require(...)的參數是一個文件名。如果我有一個模塊源代碼字符串code,我可以以某種方式調用require(code)並從該字符串中加載函數?在nodejs中需要

+1

http://nodejs.org/api/modules.html#modules_modules(什麼是荒謬的uri) – jAndy

+0

@jAndy哪裏是一個字符串中的源代碼?我只看到從文件加載。 – Cartesius00

+0

http://nodejs.org/api/modules.html – Thomas

回答

1

解決辦法可能是將模塊源代碼寫入臨時文件./tmp-file.js,然後require('./tmp-file'),然後刪除該文件。

這可能不是最優的,因爲您要麼必須同步地阻止和寫入文件,要麼將所有需要該模塊的內容都放入異步寫回調中。

用於異步文件寫入(gist - also includes sync file write)工作的示例:

var http = require('http'); 
var fs = require('fs'); 

var helloModuleString = "exports.world = function() { return 'Hello World\\n'; }"; 
fs.writeFile('./hello.js', helloModuleString, function (err) { 
    if (err) return console.log(err); 
    var hello = require('./hello'); 

    http.createServer(function (req, res) { 
    res.writeHead(200, {'Content-Type': 'text/plain'}); 
    res.end(hello.world()); 
    }).listen(1337, '127.0.0.1'); 

    console.log('Server running at http://127.0.0.1:1337/'); 
}); 

結果:

$ curl 127.0.0.1:1337 
> Hello World 
+0

謝謝,聽起來像一個很好的基準解決方案。 – Cartesius00

+0

總的來說,我同意,但這需要允許節點應用程序在文件系統上創建文件。如果你啓動節點應用程序的多個實例,你必須以某種方式決定如何處理文件或命名空間。我試圖添加一個自定義的擴展,但現在已經棄用。沒有其他好的解決方案嗎? –

2

我把這個變成一個功能重用。它根據隨機哈希在os臨時目錄中創建一個文件,需要它然後刪除它。

var fs  = require('fs'), 
    os  = require('os'), 
    crypto = require('crypto'); 

function requireString(moduleString) { 
    var token   = crypto.randomBytes(20).toString('hex'), 
     filename  = os.tmpdir() + '/' + token + '.js', 
     requiredModule = false; 

    // write, require, delete 
    fs.writeFileSync(filename, moduleString); 
    requiredModule = require(filename); 
    fs.unlinkSync(filename); 

    return requiredModule; 
} 

然後,你可以這樣做:

var carString = "exports.start = function(){ console.log('start'); };", 
    car  = requireString(carString); 

console.log("Car:", car); 

這是更一種解決辦法,但使用起來比較方便,我想。

+1

不錯,謝謝 – Cartesius00