Meteor.startup(function () {
Posts.find().observe({
added: function (doc) {
// why does this get called on startup for every document?
}
});
});
What am i trying to do
Listen for new added posts and update another collection.
But why
does my oberve.added code run every time i start my meteor application? I just need it to run when there is is a new post added
Thank you
There's kind of an example in the docs on how to accomplish this. It is written under Meteor.publish. The idea is the following:
var initializing = true;
// observeChanges only returns after the initial `added` callbacks
// have run.
var handle = <Collection>.find(<selector>).observeChanges({
added: function (id) {
if(!initializing){
// A new was added!
}
}
});
initializing = false;
Related
Here is my template onCreated and helper function. I have provided inline comments to add some clarity. I can see that self.post is eventually set because it shows up on my console when I log Template.instance(). However, when I log Template.instance().post, it is always undefined.
Template.default.onCreated(function() {
var self = this;
self.autorun(function() {
var postId = FlowRouter.getParam('post_id');
self.subscribe('onePost', postId);
self.post = Posts.findOne(FlowRouter.getParam('post_id'));
});
});
Template.default.helpers({
poststage: function(stage) {
console.log(Template.instance()); // I can see post object here
console.log(Template.instance().post; //always undefined
if(Template.instance().post) {
// never true
return Template.instance().post.stage == stage;
}
}
});
Template.default.events({
'submit form':function(event, instance) {
Meteor.call('someFunc', instance.post.anotherField);
}
});
Edit: I should add, I'm trying to avoid writing the query twice because I'm also using it in the Template events. (see code).
This feels like a timing issue. You are subscribing to the onePost publication but you aren't waiting for that subscription to be .ready() before assigning self.post The autorun also seems superfluous. You shouldn't need to rerun that block of code in the onCreated block. I suggest:
Template.default.onCreated(function() {
this.postId = FlowRouter.getParam('post_id');
self.subscription = subscribe('onePost', this.postId);
});
Template.default.helpers({
poststage: function(stage) {
if ( this.subscription.ready() ){
return Posts.findOne(this.postId).stage;
}
}
});
I'm stumped here. I can't get it to find a collection from the onCreated method. If I log the data.source_id right before the call and then do the same lookup in the console, it finds it. Is there something special about onCreated or something? Am I just doing it wrong?
client/setup.js
Meteor.subscribe('source_elements');
Meteor.subscribe('internal_elements');
client/submit.js
Router.route('/element/submit', function() {
this.render('submit', {
data: {
source_id: this.params.query.source_id,
},
});
});
Template.submit.onCreated(function() {
var data = Template.instance().data;
var source_element = SourceElements.findOne({'_id': data.source_id});
console.log(source_element); // EMPTY!!
});
Template.submit.helpers({
element: function() {
var data = Template.instance().data;
var source_element = SourceElements.findOne({'_id': data.source_id});
console.log(source_element); // RESULT!!
return source_element;
},
});
Subscriptions are asynchronous. It looks like you are creating the template before the data has arrived at the client. By the time you execute the find in the console, the client has received the data.
Inside your onCreated function, you could use Tracker.autorun to specify a function that will be rerun when the SourceElements collection changes (that's what all template helpers do behind the scenes):
Tracker.autorun(function() {
var element = SourceElements.findOne({'_id': data.source_id});
console.log(element);
});
This function will be called immediately. At this point, findOne will probably return undefined because the subscription is not ready yet. Once the data has arrived, the function will be called again and you can process the returned elements.
I update reactive var on autorun. The same reactive var is used in helper. But helper values doesn't refresh by autorun function. My below code will explain you clearly.
Template.home.onCreated(function () {
var self = this;
self.ITEMS_INCREMENT = 2;
self.itemsLimit = new ReactiveVar(2);
});
Template.home.onRendered(function () {
var self = this;
this.autorun(function(){
if( true ){
self.itemsLimit.set(self.itemsLimit.get()+self.ITEMS_INCREMENT);
console.log(self.itemsLimit.get()); // set values are fine
}
});
});
Template.home.helpers({
testHelper: function(){
console.log(Template.instance().itemsLimit.get()); // console returns 2 and 4 only. no more update :(
return true;
}
});
Anything wrong in handling of data or usage? How to make helpers are workable?
Well well well, I don't see where are you going to change the value of reactive variable. It gets changed only ones, when first computation runs in your tracker. So only ones you see the update. The idea of using ReactiveVar is that when you change it, it gets changed inside helper or inside autorun.
Briefly, what you can do to test it is:
Template.home.onRendered(function () {
var self = this;
Meteor.setInterval(function(){
self.itemsLimit.set(self.itemsLimit.get()+self.ITEMS_INCREMENT);
}, 500);
});
I need to know about the Sessions.Actually we using default sessions like session.set(key,value) and session.get(key). In this default session are cleared some cases like refresh and etc.
First i am using meteor add u2622:persistent-session Pkg.Use of this pkg gets one error i.e "Uncaught Error: Meteor does not currently support objects other than ObjectID as ids".
To overcome those problems to use amplify Sessions. But did one sample to using amplify Sessions as shown below code :
Js Code :
Messages = new Meteor.Collection("messages");
if (Meteor.isClient) {
var AmplifiedSession = _.extend({}, Session, {
keys: _.object(_.map(amplify.store(), function (value, key) {
return [key, JSON.stringify(value)];
})),
set: function (key, value) {
Session.set.apply(this, arguments);
amplify.store(key, value);
}
});
// counter starts at 0
Session.setDefault('counter', 0);
AmplifiedSession.set('no', 1);
Template.hello.helpers({
counter: function () {
return Session.get('counter');
}
});
Template.hello.helpers({
no: function () {
return AmplifiedSession.get('no');
}
});
Template.hello.events({
'click button': function () {
// increment the counter when button is clicked
console.log("Btn Clicked");
Session.set('counter', Session.get('counter') + 1);
AmplifiedSession.set('no',AmplifiedSession.get('no') + 1);
}
});
}
if (Meteor.isServer) {
Meteor.startup(function () {
// code to run on server at startup
});
}
Even not working.amplify Sessions also cleared at the time of Refresh.I didn't get any idea about this.So please suggest me what to do for this.
Thanks in Advance.
Try this package on atmosphere and let me know if it helped.
meteor add u2622:persistent-session
In this particular example, on every page load, you are running AmplifiedSession.set('no', 1);, therefore setting 'no' to be 1. This is why on page refreshes, 'no' is getting set to 1. Remove this line, and then change this line AmplifiedSession.set('no',AmplifiedSession.get('no') + 1); to set the value of 'no' if it does not exist.
Context : I am using a Collection Params to call method from the Server to a C app. The C app does its stuff and then calls the server by RPC to send me the results. With the result, I get the Params ID to delete the corresponding element.
With the deletion of the Element of Params, the C app gets a removed message. I want to prevent this behavior to avoid overloading the C app of messages.
I've thinked about implementing the removed event into the Publish method on the server to prevent the server from informing the C app. I just want the C app to be inform about added events.
On the Meteor Doc, there is an example of implementation of added and removed but I don't understand it. Can someone help me ?
I've tried this (don't work at all) :
Meteor.publish('expert_mode_parameters', function ()
{
var self = this;
var handle = Expert_Mode_Parameters.find().observeChanges({
added: function ()
{
return Expert_Mode_Parameters.find();
},
removed: function ()
{
return [];
}
});
self.ready();
self.onStop(function () {
handle.stop();
});
}
It looks like your goal is to subscribe to a data set but only receive added messages, not changed or removed.
The below code should do this:
Meteor.publish('expert_mode_parameters', function () {
var self = this;
var handle = Expert_Mode_Parameters.find().observe({
added: function (document) {
self.added("expert_mode_parameters", document._id, document);
}
});
self.ready();
self.onStop(function () {
handle.stop();
});
}
The concept is, you're watching the results of Expert_Mode_Parameters.find() and then calling self.added(document) when there is a new item. The same thing can easily be expanded to include changed.