2010-10-07 63 views
1

我想制作一个node.js函数,它在调用时读取文件并返回内容。我很难做到这一点,因为'FS'已经完成了。因此,我的函数看起来像这样:Node.js返回文件的结果

function render_this() { 
    fs.readFile('sourcefile', 'binary', function(e, content) { 
     if(e) throw e; 
     // I have the content here, but how do I tell people? 
    }); 
    return /* oh no I can't access the contents! */; 
}; 

我知道,有可能是一个办法做到这一点使用非事件触发IO,但我更喜欢一个答案,让我对事件触发功能等这么如果我遇到需要做同样事情的情况,而不是IO,我不会再被卡住。我知道这打破了“一切都是平衡”的想法,我不打算经常使用它。但是,有时候我需要一个实用的函数来动态地呈现haml模板或其他东西。

最后,我知道我可以在早期调用fs.readFile并缓存结果,但这样做不起作用,因为在这种情况下'sourcefile'可能会随时更改。

回答

4

好的,所以你想让你的开发版本自动加载并重新渲染文件,每次它的变化,对吧?

您可以使用fs.watchFile来监视文件,然后在每次更改模板时重新呈现模板,我想您的某个全局变量表示服务器是以开发模式还是生产模式运行:

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

// Let's encapsulate all the nasty bits! 
function cachedRenderer(file, render, refresh) { 
    var cachedData = null; 
    function cache() { 

     fs.readFile(file, function(e, data) { 
      if (e) { 
       throw e; 
      } 
      cachedData = render(data); 
     }); 

     // Watch the file if, needed and re-render + cache it whenever it changes 
     // you may also move cachedRenderer into a different file and then use a global config option instead of the refresh parameter 
     if (refresh) { 
      fs.watchFile(file, {'persistent': true, 'interval': 100}, function() { 
       cache(); 
      }); 
      refresh = false; 
     } 
    } 

    // simple getter 
    this.getData = function() { 
     return cachedData; 
    } 

    // initial cache 
    cache(); 
} 


var ham = new cachedRenderer('foo.haml', 

    // supply your custom render function here 
    function(data) { 
     return 'RENDER' + data + 'RENDER'; 
    }, 
    DEV_MODE 
); 


// start server 
http.createServer(function(req, res) { 
    res.writeHead(200); 
    res.end(ham.getData()); 

}).listen(8000); 

创建cachedRenderer,然后访问它需要的时候getData财产,如果你在开发MOD是它会自动在每次发生变化时重新渲染文件。

0
function render_this(cb) { 
    fs.readFile('sourcefile', 'binary', function(e, content) { 
     if(e) throw e; 
     cb(content); 
    }); 
}; 


render_this(function(content) { 
    // tell people here 
}); 
+0

我宁愿不用回调来做这件事。在这种情况下,我试图编写一个呈现haml模板的函数。在生产服务器上,它应该在服务器statup上缓存模板并在调用时渲染它,但在开发服务器上它应该读取每次调用的文件以防万一它改变了。因此,我想要一个读取文件的开发函数,但假设它没有。回调改变了我的功能的类型签名,这使得切换到生产模式变得非常困难。 – So8res 2010-10-07 01:41:28