Closed cramhead closed 10 years ago
I don't know if the answer to your question specifically is yes, but there are two workarounds:
direct
operations when you don't want to activate hooksWhen you register a hook, it returns an object with .remove and .replace. In your case you're looking for .remove
Oh, that's awesome. Basically a handle that I can hold onto and remove handler later. I expect that will be much easier then adjusting all the collection call. Thanks so much to both of you.
So I think I may have stumbled across a more significant problem, assume that my code below is doing what is expected. I'm assuming that I simply call the remove method on the object returned add hood methods. Below, when adding a handlers I add push the returned object into an array when a call to initCollectionHooks is called and when disableCollectionHooks is called objects are popped from the array and their remove method is called, with no arguments.
var hookHandles = [];
var initCollectionHooks = function() {
console.log('enable');
//once the seed process is complete or no seeding takes place add the listener
hookHandles.push(
Collectibles.after.insert(function(userId, doc) {
// get the imageIds and set them as being linked
App.emitter.emit('collectible.added', userId, doc);
})
);
hookHandles.push(
Collectibles.after.update(function(userId, doc, fieldNames, modifier, options) {
if (fieldNames.indexOf("favs") > -1) {
if (modifier.$push) {
collectibleFaved(userId, doc);
}
// no notification on $pop
}
})
);
};
var disableCollectionHooks = function() {
console.log('disable');
for (var i = hookHandles.length - 1; i >= 0; i--) {
console.log('removing collectible hooks');
var hookHandle = hookHandles.pop();
hookHandle.remove();
};
};
// start with hooks enabled
initCollectionHooks();
// listen for seed events and turn off/on collection hooks
App.emitter.on('seeding.started', disableCollectionHooks);
App.emitter.on('seeding.completed', initCollectionHooks);
My issue seems to be an interaction between collectionFS and collection-hooks, when I attempt insert seed images. I've tried disabling the hooks and never adding them, but I still get the error below. CollectionFS fails, but when we look further down there is a CollectionHooks.defineAdvice.arg entry in the stack. Any thoughts?
I20140625-14:25:17.948(-7)? at Request.pipe (/Users/cram/.meteorite/packages/data-man/CollectionFS/Meteor-data-man/c42e97728b38c29522d59db58d290e928df831ba/.build/npm/node_modules/request/request.js:1299:13)
I20140625-14:25:17.948(-7)? at beginStorage (packages/cfs-collection/api.common.js:32)
I20140625-14:25:17.948(-7)? at packages/cfs-collection/api.common.js:61
I20140625-14:25:17.948(-7)? at _.each.Meteor.Collection.(anonymous function).wrappedCallback (packages/mongo-livedata/collection.js:431)
I20140625-14:25:17.949(-7)? at CollectionHooks.defineAdvice.args.(anonymous function) (packages/collection-hooks/insert.js:35)
I20140625-14:25:17.949(-7)? at Meteor.bindEnvironment.runWithEnvironment (packages/meteor/dynamics_nodejs.js:108)
I20140625-14:25:17.949(-7)? at Meteor.bindEnvironment (packages/meteor/dynamics_nodejs.js:121)
I20140625-14:25:17.950(-7)? at writeCallback (packages/mongo-livedata/mongo_driver.js:293)
I20140625-14:25:17.950(-7)? at Meteor.bindEnvironment.runWithEnvironment (packages/meteor/dynamics_nodejs.js:108)
I believe the CollectionHooks.defineAdvice.args
always runs if collection-hooks are added, even if there are no hooks configured on the collection. Otherwise it wouldn't be able to intercept them. Why don't you look into the specific message Error: You cannot pipe after data has been emitted from the response.
? That seems to be what's causing this.
That what I'm in process of doing. It's pretty complicated code with all the futures calls and bindEnvironment. I figure I should try disabling collection-hooks to remove it form being a potential problem first.
Any luck @cramhead?
For your specific use-case, could you wrap all of your hooks in a function that checks a variable (probably using Meteor.EnvironmentVariable
) so as to decide whether or not to run the hooks?
The idea would be that when you set this flag to false
, the function wrapping your hooks would simply short-circuit and not execute the hook. If the flag is true
, calls the hook as per normal.
@cramhead: See https://github.com/mizzao/meteor-partitioner/blob/master/grouping.coffee#L140 for an example of how to implement @matb33's suggestion.
Hi guys, Thanks so much for your help. Sorry I forgot to close the issue.
I've a sample of the approach up in a gist at https://gist.github.com/cramhead/dc431ab0417fce7aa965. The code basically listens for events emitted when seeding data and when seeding is complete. The event handlers look in a list of collection-hook handlers to determine what functions need to be removed and removes them.
I do think the issue rests in collectionFS. I'll be pursuing the collectionFS issue when I can find a small block of time.
Is there a good approach for disabling a collection hook after it has been set. I've tried setting the listeners to null or an empty function, e.g.
Collectibles.after.insert(function(){});
andCollectibles.after.insert(null);
as well asCollectibles.after.insert = null;
but the handlers I had previously set still get called or when I attempt re-enable listenersTypeError: Property 'insert' of object #<Object> is not a function
.Thanks