我认为使用手动发布(this.added
)仍然可以消除服务器观察数据更改所产生的开销。观察者要么需要手动添加,要么通过返回 Collection.curser 创建。
如果数据集很大,您可能还会担心为每个客户端保存数据副本的合并框的开销。要摆脱它,您可以在本地复制集合并停止订阅。
var staticData = new Meteor.Collection( "staticData" );
if (Meteor.isServer ){
var dataToPublish = staticData.find().fetch(); // query mongo when server starts
Meteor.publish( "publishOnce" , function () {
var self = this;
dataToPublish.forEach(function (doc) {
self.added("staticData", doc._id, doc); //sends data to client and will not continue to observe collection
});
});
}
if ( Meteor.isClient ){
var subHandle = Meteor.subscribe( "publishOnce" ); // fills client 'staticData' collection but also leave merge box copy of data on server
var staticDataLocal = new Meteor.Collection( null ); // to store data after subscription stops
Deps.autorun( function(){
if ( subHandle.ready() ){
staticData.find( {} ).forEach( function ( doc ){
staticDataLocal.insert( doc ); // move all data to local copy
});
subHandle.stop(); // removes 'publishOnce' data from merge box on server but leaves 'staticData' collection empty on client
}
});
}
更新:我在代码中添加了注释以使我的方法更清晰。订阅句柄上的流星文档stop()
说“这通常会导致服务器指示客户端从客户端的缓存中删除订阅的数据”所以也许有一种方法可以停止留下数据的订阅(从合并框中删除)在客户端。这将是理想的,并且避免了客户端的复制开销。
无论如何,原始方法set
和flush
也将数据留在合并框中,所以也许没关系。