控制器 Angular 流星中的自动更新记录

Auto updating records in controller Angular meteor

我在我的 meteor 应用程序中使用 angular 并且当控制器变量中的记录在服务器上的记录发生更改时自动在客户端上更新时,我正在查看此行为,或者如果你从数据库本身改变它。下面是我的代码

Client.js

(function() {
    angular.module('testApp')
        .controller('TestController', TestController);

    //inject dependencies required    
    TestController.$inject = ['$state', '$mdDialog', '$reactive', '$scope'];

    function TestController($state, $mdDialog, $reactive, $scope) {
        var vm = this;
        vm.dineInArray = [];

        // to attach the scope to reactive var
        $reactive(vm).attach($scope);

        vm.helpers({
            tables: function() {
                return Tables.find({});
            }            
        });

        var tableOrderCompSubscription = vm.subscribe('tableOrders');

        Tracker.autorun(function() {
            if (tableOrderCompSubscription.ready()) {
                createDineInArray();
            }
        });

        function createDineInArray() {
            var tempArray = [];
            var order;
            vm.tables.forEach(function(table) {
                order = Orders.findOne({ tableId: table._id });
                if (order) {
                    table.orderId = order._id;
                    table.menuItems = order.menuItems;
                }
                tempArray.push(table);
            });            
            vm.dineInArray = tempArray;
        }
    }
})();

Server.js

Meteor.publishComposite('tableOrders', {
        find: function() {
            // Find top ten highest scoring posts
            return Tables.find({});
        },
        children: [{
            find: function(table) {
                // Find post author. Even though we only want to return
                // one record here, we use "find" instead of "findOne"
                // since this function should return a cursor.
                return Orders.find({ tableId: table._id }, { limit: 1 });
            }
        }]
    });

现在,在上面的代码中,我在 this meteor 包的帮助下发布了一个由两个集合组成的混合对象。我通过 Tables 中的 tableOrders 集合和客户端上的 Orders 集合获得了发布的数据,这是完美的。我对数据进行了一些处理,然后将所有数据添加到 createDineInArray() 函数内控制器的 vm.dineInArray 变量,该函数在订阅准备就绪时调用。下面是我的 html 使用 vm.dineInArray

HTML

<div flex layout="row" ng-controller="TestLayoutController as vm">
    <!--Title bar end-->
    <div layout="row" flex>
        <md-content flex layout="row" layout-wrap>
            <md-card class="table-card" md-ink-ripple ng-repeat="item in vm.dineInArray">
                <div flex layout="row" class="table-card-body" layout-align="center center">
                    <p>{{item.pending}} / {{item.quantity}}</p>
                </div>
                <div layout="row" class="table-card-footer" layout-align="center center">
                    <h4>{{ item.name }}</h4>
                </div>
            </md-card>
        </md-content>
    </div>
</div>

现在假设我在 Tables 集合中有 1 条记录,因此我在 dineInArray 中得到了 1 项呈现在我的视图中。当我通过一些 GUI 工具 Robomongo 直接从 mongo db 更改该记录中的值并更新它时,会发生什么情况,dineInArray 中的相应记录会自动更新,而无需我做任何事情。

我知道,如果每次更改时都会调用辅助函数,但生成我的数组的函数不会从辅助函数中调用。我在 Tracker 指示订阅已准备就绪时调用它,因此我无法弄清楚数组中的记录如何使用来自服务器的最新值更新自身。

我可能遗漏了一些明显的东西,但我想知道发生这种情况的原因以及我如何 benefit/damage 从它

有什么帮助吗?

查看 Meteor 文档,其中详细解释了该过程。

Collection.find() returns 一个游标。

Cursors are a reactive data source. On the client, the first time you retrieve a cursor's documents with fetch, map, or forEach inside a reactive computation (eg, a template or autorun), Meteor will register a dependency on the underlying data. Any change to the collection that changes the documents in a cursor will trigger a recomputation. To disable this behavior, pass {reactive: false} as an option to find.

为您的 angular 控制器添加了提示:无论您如何创建数据或是否在单独的函数中创建数据,只要您在代码中的任何地方直接从 meteor 的集合中提取数据,它会在 db 中更改时更新。