在WebWorker中,我使用ReactDOMServer.renderToString
然后我将该字符串传递回主UI线程:
[HttpGet, Route("GetAccountInformation")]
public IActionResult Get([FromUri]GetAccountInformationParamsObj @params)
{
var retVal = _repository.GetAccountInformation(@params.StartDate, @params.EndDate, @params.Count)
return Ok(retVal);
}
但是回到主UI线程中,我不确定如何实际渲染该字符串...我需要使用 lines = lines.map(function(line){
return ReactDOMServer.renderToString(ContactItem({line: line}));
});
postMessage({
testResult: 'pass',
testLines: lines
});
还是有更好的方法?
WebWorker消息的字符串结果当然是这样的:
React.dangerouslySetInnerHTML
答案 0 :(得分:2)
dangerouslySetInnerHTML
似乎在这种情况下有效,但正如文档中所述:
(1)此功能主要用于与DOM字符串的协作 操纵库[...]
这似乎不是这种情况。
此外,您正在从外部操纵组件的内部。根据我的经验,这可能会更难以追查意外行为的来源。
更好的方法是继续处理WebWorker线程中的列表(我想你想在那里做一些大的计算)但是将处理过的属性传递回主UI线程,这样它们就可以传递给列表容器,然后可以在内部生成列表。
例如,在Flux(2)体系结构中,您的商店可能负责接收WebWorker的结果,然后将其传递给您的View,从而触发组件呈现。
答案 1 :(得分:0)
我有一个初步的答案,我认为这是有效的,但我不确定它是否充分利用了React虚拟DOM的强大功能,即使它是React库的一部分。
在我的主UI线程中,我有这个:
render: function() {
var self = this;
var lines = this.state.testLines.map(function (line, i) {
return React.createElement('div', {key: i, dangerouslySetInnerHTML: {__html: line}});
});
return React.createElement('div', {}, lines);
}
在工人中,我有这个:
if (typeof importScripts === 'function') {
importScripts('//cdnjs.cloudflare.com/ajax/libs/react/0.14.3/react.js');
importScripts('//cdnjs.cloudflare.com/ajax/libs/react/0.14.3/react-dom.js');
importScripts('/js/vendor/react-dom-server.js');
importScripts('//cdnjs.cloudflare.com/ajax/libs/underscore.js/1.8.3/underscore.js');
}
onmessage = function (msg) {
var data = msg.data;
var lines = doTheThing(data);
lines = lines.map(function(line){
return ReactDOMServer.renderToString(ContactItem({line: line}));
});
postMessage({
testResult: 'pass',
testLines: lines
});
close();
};
所以让这个工作的关键是使用dangerouslySetInnerHTML,如下所示:
https://facebook.github.io/react/tips/dangerously-set-inner-html.html
上面的这一行是重要的一行:
return React.createElement('div', {key: i, dangerouslySetInnerHTML: {__html: line}});
...这是我知道渲染使用WebWorker在前端生成的字符串的唯一方法。