Как опубликовать представление / преобразование коллекции в Meteor?
Я сделал compilation
var Words = new Meteor.Collection("words");
и опубликовал его:
Meteor.publish("words", function() { return Words.find(); });
так что я могу получить к нему доступ на клиенте. Проблема в том, что эта коллекция будет очень большой, и я просто хочу опубликовать ее преобразование. Например, предположим, что я хочу опубликовать сводку под названием «num words by length», которая представляет собой массив из int, где index – это длина слова, а item – количество слов этой длины. Так
- Метеор: разница между именами для коллекций, переменных, публикаций и подписки?
- Понимание «Не разрешено. Неверный код может обновлять документы только по идентификатору.
- Как я могу развернуть узловые модули в приложении Meteor на meteor.com?
- Как я могу сортировать коллекцию Метеор по времени вставки?
- Метеор: Как я могу узнать, когда firebase database готова?
wordsByLength[5] = 12;
означает, что имеется 12 слов длины 5. В терминах SQL это простой GROUP BY / COUNT над исходным набором данных. Я пытаюсь создать шаблон на клиенте, который скажет что-то вроде
- У вас есть N слов длины X
для каждой длины. Мой вопрос сводится к «У меня есть данные в форме A, и я хочу опубликовать преобразованную версию B».
- Как развернуть meteorное приложение на моем собственном сервере?
- Как запустить meteorитный сервер на другом IP-адресе?
- Как использовать существующий MongoDB в проекте Meteor?
- Как получить IP-адрес пользователя на сервере Meteor?
- Как открыть веб-службу RESTful с помощью Meteor
- Обратный вызов после обновления DOM в Meteor.js
- 2013 Meteor NPM Packages
- Meteor.methods возвращает неопределенные
UPDATE Вы можете преобразовать коллекцию на сервере следующим образом:
Words = new Mongo.Collection("collection_name"); Meteor.publish("yourRecordSet", function() { //Transform function var transform = function(doc) { doc.date = new Date(); return doc; } var self = this; var observer = Words.find().observe({ added: function (document) { self.added('collection_name', document._id, transform(document)); }, changed: function (newDocument, oldDocument) { self.changed('collection_name', oldDocument._id, transform(newDocument)); }, removed: function (oldDocument) { self.removed('collection_name', oldDocument._id); } }); self.onStop(function () { observer.stop(); }); self.ready(); });
Чтобы обернуть преобразования, упомянутые в других ответах, вы можете использовать пакет, который я разработал, meteor-middleware . Для этого он обеспечивает хороший API-интерфейс для подключения. Поэтому вместо простого преобразования вы можете складывать их один на другой. Это позволяет повторное использование кода, проверку прав доступа (например, удаление или объединение полей на основе разрешений) и т. Д. Таким образом, вы можете создать class, который позволяет собирать документы так, как вы хотите.
Но для вашего конкретного случая вы, возможно, захотите изучить конвейер агрегации MongoDB . Если действительно есть много слов, вы, вероятно, не хотите передавать их все с сервера MongoDB на сервер Meteor. С другой стороны, в конвейере агрегации отсутствует реактивность, которую вы, возможно, захотите. Так что опубликованные документы меняются, когда слова приходят и уходят.
Чтобы решить, что вы можете использовать другой пакет, который я разработал, PeerDB . Это позволяет вам указывать триггеры, которые будут называться реакционно называемыми изменениями данных и храниться в базе данных. Затем вы можете просто использовать обычную публикацию для отправки счета клиенту. Недостатком является то, что все пользователи должны быть заинтересованы в одной коллекции. Он работает глобально, а не для пользователя. Но если вас интересует количество слов в целом коллекции, вы можете сделать что-то вроде (в CoffeesScript):
class WordCounts extends Document @Meta name: 'WordCounts' class Words extends Document @Meta name: 'Words' triggers: => countWords: @Trigger ['word'], (newDocument, oldDocument) -> # Document has been removed. if not newDocument._id WordCounts.update length: oldDocument.word.length , $inc: count: -1 # Document has been added. else if not oldDocument._id WordCounts.update length: newDocument.word.length , $inc: count: 1 # Word length has changed. else if newDocument.word.length isnt oldDocument.word.length WordCounts.update length: oldDocument.word.length , $inc: count: -1 WordCounts.update length: newDocument.word.length , $inc: count: 1
И тогда вы можете просто публиковать документы WordCounts
:
Meteor.publish 'counts', -> WordCounts.documents.find()
Вы можете собрать подсчеты, пройдя каждый документ в Словах ( курсор для каждого )
var countingCursor = Words.find({}); var wordCounts = {}; countingCursor.forEach(function (word) { wordCounts[word.length].count += 1; wordCounts[word.length].words = wordCounts[word.length].words || [] wordCounts[word.length].words.push(word); });
создать локальную коллекцию,
var counts = new Meteor.Collection('local-counts-collection', {connection: null});
и вставьте свои ответы
var key, value; for (key in wordCounts) { value = object[key]; counts.insert({ length: key, count: value.count, members: value.words }); }
Графы теперь представляют собой коллекцию, которая просто не хранится в Монго.
Не испытано!