meteorhacks:aggregate error - meteor

I'm trying to publish some data using meteorhacks:aggregate:
Meteor.publish('alleNascholingen',function() {
var self = this;
var nascholingenOverzicht = nascholingenCollectie.aggregate([
//{$match: {creatorId: this.userId}},
//{$project: {naam: 1, familienaam:1, nascholingen:1}},
{ $unwind : "$nascholingen" },
{ $sort: {
"nascholingen.inschrijfMoment": -1
}}
]);
_.each(nascholingenOverzicht, function(parent){
_.each(parent, function(child){
self.added('selectie', child._id, child);
});
});
self.ready()
});
I have two collections, one to store the aggregated data:
nascholingenCollectie = new Mongo.Collection('nascholingen');
nascholingenSelectie = new Mongo.Collection('selectie');
On my template I subscribe to the data:
Template.nascholingBeheer.onCreated(function() {
let self = Template.instance();
self.subscribe('alleNascholingen', function () {
setTimeout(function () {
}, 300)
})
})
});
I'm getting the following error in my chrome console:
collection.js:173 Uncaught Error: Expected to find a document to change
at Object.update (http://localhost:3000/packages/mongo.js?hash=c4281c0ff989ebee020f59f5a7b0735053cea5f7:246:29)
at Object.store.(anonymous function) [as update] (http://localhost:3000/packages/ddp-client.js?hash=bc32a166cd269e06a394f9418e0024d805bab379:3613:48)
at http://localhost:3000/packages/ddp-client.js?hash=bc32a166cd269e06a394f9418e0024d805bab379:4441:19
at Array.forEach (native)
at Function._.each._.forEach (http://localhost:3000/packages/underscore.js?hash=cde485f60699ff9aced3305f70189e39c665183c:149:11)
at http://localhost:3000/packages/ddp-client.js?hash=bc32a166cd269e06a394f9418e0024d805bab379:4440:13
at Function._.each._.forEach (http://localhost:3000/packages/underscore.js?hash=cde485f60699ff9aced3305f70189e39c665183c:157:22)
at Connection._performWrites (http://localhost:3000/packages/ddp-client.js?hash=bc32a166cd269e06a394f9418e0024d805bab379:4437:9)
at Connection._flushBufferedWrites (http://localhost:3000/packages/ddp-client.js?hash=bc32a166cd269e06a394f9418e0024d805bab379:4423:10)
at Connection._livedata_data (http://localhost:3000/packages/ddp-client.js?hash=bc32a166cd269e06a394f9418e0024d805bab379:4391:12)
What am I doing wrong here?

You can not use aggregation in Meteor publication, only in Meteor method. To work around that you could consider using this package (disclaimer: I am the author).

My bad...I found my error:
_.each(nascholingenOverzicht, function(parent){
_.each(parent, function(child){
self.added('selectie', child._id, child);
});
});
should be:
_.each(nascholingenOverzicht, function(parent){
self.added('selectie', parent._id, parent);
});

Related

SimpleSchema/Collection2 insert exception

I'm trying to get a single text field to insert a string into my collection. I'm getting this error:
Exception while invoking method 'categories.insert' TypeError: func is not a function
at /var/www/node/lover/node_modules/simpl-schema/dist/doValidation.js:359:18
at Array.forEach (native)
at doValidation (/var/www/node/lover/node_modules/simpl-schema/dist/doValidation.js:358:17)
at ValidationContext.validate (/var/www/node/lover/node_modules/simpl-schema/dist/ValidationContext.js:217:57)
at [object Object].doValidate (packages/aldeed:collection2-core/collection2.js:399:33)
at [object Object].Mongo.Collection.(anonymous function) [as insert] (packages/aldeed:collection2-core/collection2.js:187:25)
at [object Object].Meteor.methods.categories.insert (server/methods.js:14:21)
at maybeAuditArgumentChecks (packages/ddp-server/livedata_server.js:1737:12)
at packages/ddp-server/livedata_server.js:719:19
at [object Object]._.extend.withValue (packages/meteor.js:1122:17)
Here is my Schema:
import { Mongo } from 'meteor/mongo';
var Categories = new Mongo.Collection('categories');
const CategorySchema = new SimpleSchema({
title: {
type: String,
label: "Title",
max: 255,
optional: true
},
created: {
type: Date,
label: "Date Category Created",
autoValue: () => {
if(this.isInsert){
return new Date();
}
}
},
updated: {
type: Date,
label: "Date Category Modified",
autoValue: () => {
if(this.isUpdate){
return new Date();
}
}
}
});
Categories.attachSchema(CategorySchema);
export default Categories;
The method to be called:
import { check } from 'meteor/check';
import { Categories, Elections, Nominees, Users, Votes } from '../collections';
Meteor.methods({
'categories.insert'(title){
check(title, String);
return Categories.insert({title: title});
}
});
And then I call it:
...
Template.settings.events({
'click #newCategoryButton'(e){
let title = $("#newCategoryInput").val();
Meteor.call('categories.insert', title, (error, response) => {});
}
});
...
I can get it to work if I add {validate: false} to my insert statement, which leads me to believe that it's a validation issue. I've gone through all the docs and a few blogs and tuts but can't find any instructions on how to insert data to my collection when using collection2 and simple-schema if it's not that standard way. In fact, if you scroll a few lines up on the collection2 documenation, the insert call is shown in basically the same form as I've written it.
I don't want to pass {validate: false} in with my insert calls as it defeats the purpose of adding a schema to my collections in the first place.
Desperate for help, been stuck on this for hours.

Tinytest meteor mocking

I tried to mock Template.__create__ with the code below but I still get the error.
In package.js
Package.describe({
name: 'robwatkin:mypackage',
});
Package.onUse(function(api) {
api.versionsFrom('1.1.0.2');
api.use('meteor-platform');
api.use('iron:router');
api.use('reactive-var');
api.use('templating');
});
Package.onTest(function(api) {
api.use('tinytest');
api.addFiles('mocks.js');
api.use('robwatkin:mypackage');
api.addFiles('tests.js');
});
in mocks.js
Template = {
__create__: function() {console.log('STUB Template.__create__')}
};
in tests.js
Tinytest.add('example', function (test) {
test.equal(true, true);
});
Gives
Uncaught TypeError: Template.__create__ is not a function(anonymous function) # layout.js:286(anonymous function) # iron_layout.js?d62e492972d7f97328c54d2ba052d5adf0cf0d9a:534(anonymous function) # iron_layout.js? d62e492972d7f97328c54d2ba052d5adf0cf0d9a:541
It works fine if I comment out
api.use('robwatkin:mypackage');
Thanks

Meteor cfs standard packages - check Error

While trying to upload a File to my Database, I am getting a Match Error that is preventing the File to be stored.
Here is the Basic code:
The Initialization:
UserImages = new FS.Collection("userImages", {
stores: [new FS.Store.FileSystem("userImages", {path: "~/uploads"})],
filter: {
maxSize: 1048576, //in bytes
allow: {
contentTypes: ['image/*'],
extensions: ['png', 'jpg']
},
onInvalid: function (message) {
if (Meteor.isClient) {
alert(message);
} else {
console.log(message);
}
}
}
});
if(Meteor.isServer){
UserImages.allow({
insert:function(userId, doc){
return true;
},
update:function(userId, doc, fields, modifier){
check(doc, Object);
return true;
},
remove:function(){
return true;
}
})
}
The Client Code:
Template.editProfile.events({
'change #profileUpload':function(event, template){
var files = event.target.files;
for (var i = 0, ln = files.length; i < ln; i++) {
UserImages.insert(files[i], function (err, fileObj) {
if(err){
console.log(err);
}
});
}
}
});
Strangly enough, if i run a console.log(typeof file) it gives me back an Object. But when i check the File against an Object with check(file, Object) it gives me this Error:
This is the Stack from the Server:
Exception in setTimeout callback: Error: Match error: Expected plain object
at checkSubtree (packages/check/match.js:279:1)
at check (packages/check/match.js:32:1)
at UserImages.allow.update (app/server/allowances.js:91:7)
at packages/mongo/collection.js:1041:1
at Array.every (native)
at Function._.every._.all (packages/underscore/underscore.js:219:1)
at [object Object].Mongo.Collection._validatedUpdate (packages/mongo/collection.js:1038:1)
at [object Object].m.(anonymous function) (packages/mongo/collection.js:851:1)
at Object.methods.rateLimit.callFunctionsInQueue (packages/matteodem:easy-security/lib/easy-security.js:72:1)
at packages/matteodem:easy-security/lib/easy-security.js:116:1
Has anyone encountered this problem or has a solution for a workaround? I've tried all kinds of workarounds also with Match.Any but than I get an error telling me that all Arguments have not been run against the check();
I checked the issues in here:
https://github.com/CollectionFS/Meteor-cfs-base-package/issues
https://github.com/CollectionFS/Meteor-CollectionFS/issues
but could not find a solution so far.
Thanks for the help!

Meteor cannot access collection created in server/main.js

I defined the collection in lib/collection.js
var Tags = new Meteor.Collection("Tags");
Then trying to initialize it in server/main.js:
Tags.insert({name: tag["tag"], default_show: true});
Got error:
W20141028-01:26:53.647(11)? (STDERR) ReferenceError: Tags is not defined
W20141028-01:26:53.648(11)? (STDERR) at app/server/main.js:43:18
I cannot figure out why I got error here? Anyone could give me some hints?
Full source code:
server/main.js
Meteor.startup(function() {
var tagsJson = JSON.parse(Assets.getText("tags.json"));
var tagsMapJson = JSON.parse(Assets.getText("tags_map.json"));
tagsJson["lines"].map(function(line) {
line["tags"].map(function(tag){
if (!Tags.findOne({name: tag["tag"]})) {
Tags.insert({name: tag["tag"], default_show: true});
}
tagsMapJson[tag["tag"]].map(function(web) {
if (!Webs.findOne({url: web["url"]})) {
Webs.insert({url: web["url"], name: web["name"], brief: web["brief"]});
}
if (!TagWebs.findOne({tag: tag["tag"], url: web["url"]})) {
TagWebs.insert({tag: tag["tag"], url: web["url"]});
}
});
});
});
});
lib/collections.js
var Tags = new Meteor.Collection("Tags");
var Webs = new Meteor.Collection("Webs");
var TagWebs = new Meteor.Collection("TagWebs");
I think you should erase "var" so collection is seen to whole project

Error when trying to use async.concat to retrieve data from redis

I was following an example posted by the async author here but I'm getting an error.
redis-2.2.12
node v0.4.11-pre
Here's my code:
var async = require('async');
var redis = require('redis');
var keys = ['key1', 'key2', 'key3'];
var client = redis.createClient();
var multi = client.multi();
for (var key in keys) {
multi.hmset(key, {'some': 'value'});
}
multi.exec(function(err, res) {
if (err) throw err;
console.dir(res);
var myCallback = function(err, res) {
console.log('in myCallback');
console.dir(res);
client.quit();
process.exit();
};
async.concat(keys, client.hgetall, myCallback);
});
Produces the following output:
$ node redis_test.js
[ 'OK', 'OK', 'OK' ]
node.js:134
throw e; // process.nextTick error, or 'error' event on first tick
^
TypeError: Object #<Object> has no method 'send_command'
at /home/project/node_modules/redis/index.js:666:25
at /home/project/node_modules/async/lib/async.js:508:13
at /home/project/node_modules/async/lib/async.js:97:13
at Array.forEach (native)
at /home/project/node_modules/async/lib/async.js:26:24
at /home/project/node_modules/async/lib/async.js:96:9
at /home/project/node_modules/async/lib/async.js:507:9
at Object.concat (/home/project/node_modules/async/lib/async.js:141:23)
at /home/project/redis_test.js:21:9
at Command.callback (/home/project/node_modules/redis/index.js:827:13)
When async runs client.hgetall, it trashes the value of this inside of hgetall. You can either wrap up an anonymous function to glue this together, or use fn.bind() as shown below.
You also want to avoid using for .. in to iterate over an Array. Use either a regular for loop or arr.forEach(). Your example would have mysteriously failed as written. Here's a version that seems to do what you want:
var async = require('async');
var redis = require('redis');
var keys = ['key1', 'key2', 'key3'];
var client = redis.createClient();
var multi = client.multi();
keys.forEach(function (key) {
multi.hmset(key, {'some': 'value'});
});
multi.exec(function(err, res) {
if (err) throw err;
console.dir(res);
var myCallback = function(err, res) {
console.log('in myCallback');
console.dir(res);
client.quit();
process.exit();
};
async.concat(keys, client.hgetall.bind(client), myCallback);
});
This outputs:
[ 'OK', 'OK', 'OK' ]
in myCallback
[ { some: 'value' },
{ some: 'value' },
{ some: 'value' } ]
To debug the mysterious failure, you can turn on debug logging in node_redis by doing redis.debug_mode = true; before sending any Redis commands.

Resources