Using this.added


#1

I’m trying to transform a publication, and this is my code:

Meteor.publish('appointments.waiting', function () {
    var self = this,
        count = 0;

    Appointments.find().forEach(function (appointment) {
        var patients = Patients.find({_id: appointment.patient_id}).fetch();
        var first_name = patients[count].profile.first_name,
            middle_name = patients[count].profile.middle_name,
            surname = patients[count].profile.surname,
            name = surname + ', ' + first_name + ' ' + middle_name;

        self.added('appointments', appointment.names, name);

    });

    self.ready();
});

When I console.log(name), I can see the name in full but I’m not quite sure how to use this.added to add the new data. How do I go about this? And if I do enter this new data, will it overwrite the older data?

EDIT:
If there’s a better way to achieve this, I’d also like to know.


#2
self.added('appointments', appointment.names, {name: name});

#3

Thanks for replying.

It works, save for one thing. It only shows the first result then exits.


#4

Can you explain further?


#5

Right, sorry. I was very vague. What I mean is, I’ve subscribed to the publication like so,

Template.patientRow.onCreated(function () {
  this.subscribe("appointments");
});

Template.patientRow.helpers({
   appointments: function () {
       return Appointments.find();
    }
});

And in my template, I’ve tried to use the data like this:

{{#each appointments}}
    <tr>    
      <td>{{name}}</td>
    </tr>
{{/each}}

In the collection, there’s three entries that should match, but it’s only showing the first one. So I’m only getting one row in my table.


#6

Yeah, you need to observe the cursor for updates since .forEach isn’t reactive

...
forEach(function () {
  Appointments.find().forEach(...);
});

Appointments.find().observe({
  added: function () {
    forEach();
  },
  removed...
});

#7

Thanks! It works! :grin:


#8

As much as the publish is working, I keep getting this error in the console whenever I try to update a document:

I20160828-23:46:59.384(3)? Exception in queued task: ReferenceError: transform is not defined
I20160828-23:46:59.389(3)?     at Object.changed (server/publications/appointments-publications.js:11:59)
I20160828-23:46:59.394(3)?     at [object Object].observeChangesCallbacks.changed (packages/minimongo/observe.js:162:1)
I20160828-23:46:59.397(3)?     at self.applyChange.changed (packages/minimongo/observe.js:66:1)
I20160828-23:46:59.400(3)?     at packages/mongo/observe_multiplex.js:183:30
I20160828-23:46:59.402(3)?     at Array.forEach (native)
I20160828-23:46:59.405(3)?     at Function._.each._.forEach (packages/underscore/underscore.js:105:1)
I20160828-23:46:59.408(3)?     at Object.task (packages/mongo/observe_multiplex.js:177:9)
I20160828-23:46:59.411(3)?     at [object Object]._.extend._run (packages/meteor/fiber_helpers.js:147:1)
I20160828-23:46:59.415(3)?     at packages/meteor/fiber_helpers.js:125:1

I updated my pub to look like this:

/* appointments-publications.js */
Meteor.publish('appointments.waiting', function () {
// Transforming data in a collection

  var self = this;
  var observer = Appointments.find({status: 'Waiting'}).observe({
    added: function (document) {
        self.added('appointments', document._id, transformAppointments (document));
    },
    changed: function (newDocument, oldDocument) {
        self.changed('appointments', oldDocument._id, transform(newDocument));
    },
    removed: function (oldDocument) {
        self.removed('appointments', oldDocument._id);
    }
  });

  self.onStop(function () {
    observer.stop();
  });

  self.ready();
});

And this is how I update:

/* appointments.js */
 Meteor.call('UpdateAppointment', {
   _id: appointmentId,
   patient_id: patientId,
   status: status,
   booked: booked
 }, function (error, result) {
   if (error) return console.log('Error: ' + error.error);
 });

 /* methods.js */
 Meteor.methods({
   'UpdateAppointment': function (data) {
      check(data, {
        _id: String,
        patient_id: String,
        status: String,
        booked: Boolean
      });

      return Appointments.update(data._id, {
        $set: {
            patient_id: data.patient_id,
            status: data.status,
            booked: data.booked
        }
      });
   }
});

Do you, by any chance, know what’s happening here?


#9

From the docs: “Transforms are not applied for the callbacks of observeChanges or to cursors returned from publish functions.”


#10

Looks like you are trying to use a global transform function