我在Utils.js中有一个名为“sendAndWaitCommand”的全局函数 当我尝试从Worker(名称'uploadToDevice.js')调用此函数时,工作程序崩溃。
工人初始化
var worker = new Worker('uploadToDevice.js');
worker.postMessage(SplitedFile);
工人(uploadToDevice.js)
self.addEventListener('message', function (e)
{
var SplitedFile = e.data;
sendAndWaitCommand(SplitedFile[0].substring(1));//crash here
}, false);
Utils.js
function sendAndWaitCommand(commandToSend)
{
...//Some heavy stuff to do.
}
有没有办法在没有工人崩溃的情况下调用全局函数? 如果没有,是否有解决方法如何从工作人员外部调用对象?
答案 0 :(得分:3)
JavaScript模型当然不是基于线程的,而是基于事件的。在多线程环境中无法锁定数据并确保其完整性。
这就是为什么多线程方案(其中包括webworkers)不允许数据共享(“全局”功能是一些数据并且通常通过闭包指向数据)。您无法从您的网络工作者调用“全局”功能。 You communicate with messages
您可以设置一个事件监听器来代替全局函数:
var myWorker = new Worker("my_task.js");
myWorker.onmessage = function (oEvent) {
// the implementation of your "global function", for example :
sendAndWaitCommand(oEvent.data.commandToSend);
};
答案 1 :(得分:0)
如果要使用util.js中的代码,则必须使用importScripts命令导入它:
MDF的例子:
importScripts(); /* imports nothing */
importScripts('foo.js'); /* imports just "foo.js" */
importScripts('foo.js', 'bar.js'); /* imports two scripts */
请注意,如果util.js与全局范围交互,则这将无效,因为在导入之后,它仍将与您的工作者位于同一范围内。如果util.js包含执行sendAndWaitCommand所需的所有代码,那么这可能是一个不错的选择。
如果sendAndWaitCommand与您的其他代码(jquery.ajax,您的错误处理代码等)交互,那么设置消息和事件系统可能会更好,如下所示:
var worker = new Worker('uploadToDevice.js');
worker.onMessage = function (message) {
if (// Test here to see if message is result
message && message[0] == "!")
myApp.onDone(message.substr(1)) // Removes the ! and calls a function to handel the worker being done
else // assume the message is a sendAndWaitCommand request
sendAndWaitCommand(message).then(function (a) {
worker.postMessage(a); // Send the worker the result
});
worker.postMessage(SplitedFile); // Start the worker
第二种方法可能涉及对代码进行更多重构,但可能需要正确使用工作程序。