Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/node.js/41.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 从子进程执行node.js中的代码_Javascript_Node.js_Firebase_Firebase Realtime Database - Fatal编程技术网

Javascript 从子进程执行node.js中的代码

Javascript 从子进程执行node.js中的代码,javascript,node.js,firebase,firebase-realtime-database,Javascript,Node.js,Firebase,Firebase Realtime Database,我是node.js的新手,我正在尝试从一个模块的子进程中执行一些代码 让我解释一下,我的简单服务器在index.js中 var server = http.createServer(handleRequest); server.listen(PORT, function(){ console.log("Server listening on: http://localhost:%s", PORT); }); 获取url后,我将启动一个子进程: function handleReque

我是node.js的新手,我正在尝试从一个模块的子进程中执行一些代码

让我解释一下,我的简单服务器在index.js中

var server = http.createServer(handleRequest);

server.listen(PORT, function(){
    console.log("Server listening on: http://localhost:%s", PORT);
});
获取url后,我将启动一个子进程:

function handleRequest(req, res){  
    console.log('Request path = ' + req.url)
    launchWorker(req.url)
    res.end('Path Hit: ' + req.url);
}

// workers execution 
function launchWorker(path) {
    const worker = child_process.spawn('node', ['./worker.js', path.substring(1)])

    worker.stdout.on('data', function(data) {
        console.log('worker: ' + data.toString())
    }); 

    worker.stderr.on('data', function(data) {
        console.log('stderr : ' + data)
    }); 

    worker.on('close', function(code, signal) {
        console.log('child process exited with code: ' + code)
    }); 
}  
因此,我有一个worker.js文件来执行一些代码,我使用
['./worker.js',path.substring(1)]

我使用firebase执行一些操作,因此在my worker.js中,我初始化了我的firebase管理员、凭据和数据库:

var admin = require("firebase-admin");

var serviceAccount = require("./service_account.json");

var defaultApp = admin.initializeApp({
  credential: admin.credential.cert(serviceAccount),
  databaseURL: "http://myAdress.firebase"
});

var db = admin.database()

performWork()

function performWork() {

    var arg = process.argv[2]
    var ref = db.ref("something");
    ref.once("value", function(snapshot) {
      console.log(arg);
      process.exit(1); 
    });

}
我将每分钟启动一个进程,所以我想做的是将firebase数据库作为参数提供给我的孩子,这样我就不会在每次启动进程时创建对firebase的访问。 这就是我在index.js中尝试做的:

var admin = require("firebase-admin");

var serviceAccount = require("./service_account.json");

var defaultApp = admin.initializeApp({
  credential: admin.credential.cert(serviceAccount),
  databaseURL: "http://myAdress.firebase"
});

var db = admin.database()

我只是将数据库作为参数传递给我的工作人员。 然后在我的工人身上,我得到了fb:

function performWork() {

    var arg = process.argv[2]
    var db = process.argv[3]
    var ref = db.ref("something");
    ref.once("value", function(snapshot) {
      console.log(arg);
      process.exit(1); 
    });

}
但是当我到达一个url时,我得到一个错误:

TypeError: db.ref is not a function
    at performWork (/home/user/worker.js:12:15)
    at Object.<anonymous> (/home/user/worker.js:6:1)
    at Module._compile (module.js:635:30)
    at Object.Module._extensions..js (module.js:646:10)
    at Module.load (module.js:554:32)
    at tryModuleLoad (module.js:497:12)
    at Function.Module._load (module.js:489:3)
    at Function.Module.runMain (module.js:676:10)
    at startup (bootstrap_node.js:187:16)
    at bootstrap_node.js:608:3
TypeError:db.ref不是函数
在performWork(/home/user/worker.js:12:15)
反对。(/home/user/worker.js:6:1)
在模块处编译(Module.js:635:30)
在Object.Module.\u extensions..js(Module.js:646:10)
在Module.load(Module.js:554:32)
在tryModuleLoad时(module.js:497:12)
在Function.Module.\u加载(Module.js:489:3)
位于Function.Module.runMain(Module.js:676:10)
启动时(bootstrap_node.js:187:16)
在bootstrap_node.js:608:3
我认为worker.js根本不了解firebase,无法访问函数.ref。即使db不是null(我可以打印它的值) 所以我的问题是,我需要在worker.js中导入/执行什么,这样它才能执行firebase模块中的代码?我试图要求用户。。。但是什么都没用。 我的问题也更一般,我想在另一个文件中编写一些帮助程序(创建、读取、删除),但我会遇到同样的问题。
谢谢你的帮助

不能将活动Javascript对象传递给另一个进程。如果对象仅包含Javascript数据,则可以使用JSON对其进行序列化,并将其传递给另一个进程,在该进程中,副本将被反序列化,但这对于具有本机代码或TCP连接的对象不起作用,后者很可能就是您的开放数据库句柄所表示的。在某些情况下,您可以将TCP连接传递给另一个进程(集群可以做到这一点),但如果您将它包装在另一个连接对象中(通常是这样),那么在另一个进程中用传递的TCP连接重新构建一个活动连接对象需要大量的工作。就我个人而言,我宁愿避免所有这些麻烦

除非您的子进程中正在进行大量CPU工作,否则我看不出有任何理由需要在这里使用子进程。当请求传入时,您可以在主进程中执行您想要的任何数据库工作。数据库工作应该主要是异步的,因此不应该明显地阻塞main node.js线程,您应该能够同时处理多个请求。对于大量请求,您的数据库将成为瓶颈,而不是主node.js进程

如果您有合理的理由使用子进程,并且不想为每个子进程打开和关闭新的DB连接,那么您可能希望创建一组工作进程,这些进程打开后保持打开状态。然后,他们可以打开自己与数据库的连接并保持其打开状态。当一个新的请求到达main node.js进程时,您可以使用某种形式的IPC(可能只是写入子进程的stdin)向它发送一个新的作业,它就在那里等待处理。您可以通过决定需要多少个工作进程来优化吞吐量来优化事情。然后,当一个新作业进入时,您只需将该作业放入队列中。如果有空闲工人,则将队列中的下一个作业发送给该工人。每次工作人员完成作业时,您都会检查队列中是否有其他项目要发送给该工作人员


这样做,您就不会一直创建和终止到数据库的新连接,每个工作进程都可以拥有并保持自己的数据库连接。

为什么您认为有必要使用子进程?我看不到有任何迹象表明它们是必要的,并且使用子进程会带来不可忽略的性能损失。我需要使用子进程来释放内存,这是一项非常繁重的任务,调用次数超过了调用次数,这是我发现的在进程完成时真正释放内存的唯一方法。好吧,谢谢你的解释,是的,我有大量的进程要运行(每30秒一次、每分钟一次、每5次、每10次……)处理大量数据,我有16 gb ram,这是我找到的唯一释放内存的方法,当子进程结束时,一切都被释放,由于内存不足错误,我的服务器可以在不重新启动的情况下运行此进程一个月。谢谢
TypeError: db.ref is not a function
    at performWork (/home/user/worker.js:12:15)
    at Object.<anonymous> (/home/user/worker.js:6:1)
    at Module._compile (module.js:635:30)
    at Object.Module._extensions..js (module.js:646:10)
    at Module.load (module.js:554:32)
    at tryModuleLoad (module.js:497:12)
    at Function.Module._load (module.js:489:3)
    at Function.Module.runMain (module.js:676:10)
    at startup (bootstrap_node.js:187:16)
    at bootstrap_node.js:608:3