Rethinkdb 使用 jQuery 更改提要渲染

Rethinkdb change feed rendering with jQuery

我目前正在尝试弄清楚如何使用 RethinkDB 的更改源。

我有一个名为 Calls 的 table,在插入、删除和更新它时,我想流式传输更改。

现在,我有最初加载调用的功能,然后 return 更改:

r.db('test').table('Calls').run(function(err, cursor) {
    if (err) throw err;
    socket.emit('load calls', cursor);
});

r.db('test').table('Calls').orderBy({index: r.desc('call_number')})
.changes().run(function(err, cursor) {
    if (err) throw err;
    cursor.each(function(err, record) {
        socket.emit('load calls', record);
    });
});

在前端我将 HTML 附加到页面:

socket.on('load calls', function(docs) {
    docs.map((call) => {
    $('.calls-list').append(`
    <tr id="call_${call.call_number}">
      <td>${call.call_number}</td>
      <td>${call.time}</td>
      <td>${call.type}</td>
      <td>${call.status}</td>
      <td>

     </td>
      <td>${call.location} - ${call.location_cross}</td>
      <td>${call.notes}</td>
      <td><a id="update-call-${call.call_number}" href=""><i class="edit icon yellow text"></i></a> <a id="archive-call-${call.call_number}" href=""><i class="delete icon red text"></i></a></td>
    </tr>
`);
    }
});

这里的问题是附加的 HTML 或多或少是永久的,而 "independent" 来自数据库;我希望它是实时的并且依赖于数据库更改提要,就像 this video 中一样。在那种情况下,数据库插入和 orderBy 是即时的。所以在我当前的问题中,如果有人想删除一个调用,那么我将不得不发出一个套接字事件并通过引用 ID 删除相应的 HTML 元素。

我不确定我是否正确理解了您的问题,但我会尝试解决一些问题。首先,当您调用 changefeed 时获得 returned 的文档与您调用 r.db.table(您的第一次调用)时不同。您的第一次调用将 return 数据库中的所有 "Call" 文档,但更改提要 return 是一个包含先前 "Call" 文档和新 "Call" 文档的文档文档。例如,当一个新的 "Call" 添加到数据库时,您会看到以下内容:

{
    old_val: null,
    new_val: {id: 1, call_number: x, time: y, ...}
}

对于现有 "Call" 的更新,您会看到:

{
    old_val: {id: 1, call_number: x, time: y, ...},
    new_val: {id: 1, call_number: x2, time: y2, ...}
}

当 "Call" 被删除时,您会看到:

{
    old_val: {id: 1, call_number: x2, time: y2, ...},
    new_val: null
}

您将不得不以不同的方式处理每种情况。您可以在前端通过检查每个文档中是否存在 old_val and/or 和 new_val 来执行此操作。像这样:

socket.on('load calls', function(docs) {
    docs.map((call) => {
        if (! call.old_val && ! call.new_val) {
            // this is a call returned from from r.db.table, not the changefeed
            // add call to the dom
        }
        else if (! call.old_val) {
            call = call.new_val;
            // this is a new call added to the db and returned from r.db.table.changes
            // add call.new_val to the dom
        }
        else if (! call.new_val) {
            // this is a delete - remove the row from the dom
        }
        else {
            // this is an update - update the existing row
        }
    }
});

或者您可以在服务器上进行某种级别的过滤并向客户端发出不同的事件。像这样:

r.db('test').table('Calls').orderBy({index: r.desc('call_number')})
.changes().run(function(err, cursor) {
    if (err) throw err;
    cursor.each(function(err, record) {
        if (! record.old_val) {
            // new call added
            socket.emit('load calls', record);
        }
        else if (! call.new_val) {
            // call deleted
            socket.emit('delete calls', record);
        }
        else {
            // call updated
            socket.emit('edit calls', record);
        }
    });
});

然后在客户端上您将订阅每个事件:

socket.on('load calls', function(docs) {
    // add docs to dom
});

socket.on('edit calls', function(docs) {
    // update docs in dom
});

socket.on('delete calls', function(docs) {
    // delete docs from dom
});

希望这对您有所帮助。仅供参考,我是您引用的 video/sample 应用程序的作者:) 感谢收看!