1

Backbonejs 集合具有重置集合以进行批量更新的功能。当我与来自服务器的 JSON 数据同步时,我想在 Titanium Alloy 中使用此功能,但看起来好像没有提交/保存到 SQLite - 我正在使用 sql 适配器。

config: {
        columns: {
            // stuff
            name: "TEXT"
        },
        adapter: {
            type: "sql",
            collection_name: "pony",
            db_name: Alloy.CFG.db_name
        }
    }

我有一些茉莉花测试一直失败。仅供参考,我有用于开发的迁移脚本,它向集合中添加了 7 个项目,以便我可以使用一些东西。

describe("pony model", function () {
    var Alloy = require("alloy")
            data = {name: "My little pony"},
        collection,
        item;

    beforeEach(function(){
        collection = Alloy.createCollection('pony');
        item = Alloy.createModel('pony');
    });

    // PASSES
    it('can reset all data', function () {
        collection.fetch();
        expect(collection.length).toEqual(7);

        collection.reset(data)
        expect(collection.length).toEqual(1);
     })

     // FAILS
     it('saves reset data', function () {
        collection.fetch();
        expect(collection.length).toEqual(7);

        collection.reset(data)
        collection.fetch()
        expect(collection.length).toEqual(1);
     })

     afterEach(function () {
         item.destroy();
     });
})

这个错误在 UI 中显示的方式是,当我保存它时,当我与服务器同步数据时,TableView 会显示新记录,然后当我转到另一个视图并返回同一个 TableView 时,同步的数据就消失了,取而代之的是默认数据。

4

1 回答 1

3

我发现的最好的方法(我很遗憾不记得我从哪里复制代码)是手动进行重置。我发布了执行此操作的代码:https ://gist.github.com/sukima/8321859

基本上我先做我自己的 SQLDELETE然后是 Backbone reset(),然后 looped INSERT INTO,最后完成一个主干trigger("fetch")事件。通过骨干网的同步执行此操作会很慢。无论如何,正常reset()都不会运行同步。

exports.definition = {

  config: {
    columns: {
      // ...
    },
    adapter: {
      type:            "sql",
      collection_name: "MyModels"
    }
  },

  extendCollection: function(Collection) {

    Collection.prototype.destroyAll = function(opt) {
      var db = Ti.Database.open(this.config.adapter.db_name);
      db.execute("DELETE FROM " + this.config.adapter.collection_name);
      db.close();
      this.models = [];
      if (!opt || !opt.silent) { this.trigger("reset"); }
      return this;
    };

    Collection.prototype.saveAll = function(opt) {
      var util    = require("alloy/sync/util");
      var dbName  = this.config.adapter.db_name;
      var table   = this.config.adapter.collection_name;
      var columns = this.config.columns;
      var db      = Ti.Database.open(dbName);

      db.execute("BEGIN;");

      this.forEach(function (model) {
        if (!model.id) {
          model.id = util.guid();
          model.attributes[model.idAttribute ] = model.id;
        }
        var names = [], values = [], q = [];
        for (var k in columns) {
          names.push(k);
          values.push(model.get(k));
          q.push("?");
        }
        var sqlInsert = "INSERT INTO " + table + " (" + names.join(",") + ") VALUES (" + q.join(",") + ");";

        db.execute(sqlInsert, values);
      });

      db.execute("COMMIT;");
      db.close();

      if (!opt || !opt.silent) { this.trigger("reset"); }
      return this;
    };

    Collection.prototype.refreshFromData = function refreshFromData(data) {
      this.destroyAll({silent:true});
      this.reset(data, {silent:true});
      this.saveAll({silent: true});
      this.trigger("fetch");
    };

  }

};
于 2014-01-08T18:45:19.410 回答