骨干模型保存和回调问题

时间:2013-04-27 20:36:21

标签: javascript backbone.js callback backbone-model

我刚开始使用Backbone。根据以下代码,我有两个问题要问。

第一个问题是在我填写表单并单击按钮后,应该使用一些默认属性创建模型对象。但是,在我将模型传递给新视图对象之前,console.log使用我填写的表单中的最新属性打印模型。

第二个问题是我可以成功将数据保存到db,但是我的成功回调函数没有被调用。有人可以帮我回答这些问题吗?

var form = document.forms[0];

var RetailerModel = Backbone.Model.extend({
    urlRoot: ' retailer.php',
    defaults: {
        name: 'company-name',
        address: 'company-address',
        phone: 'company-phone',
        icon: 'http://localhost/icon.png'
    }
});

var RetailerCollection = Backbone.Collection.extend({

});

var RetailerView = Backbone.View.extend({

    className: 'retailer',

    template: _.template($('#retailer-template').html()),

    initialize: function() {
        //this.listenTo(this.model, 'change', this.render);

        var obj = {
            name: form.name.value,
            address: form.address.value,
            phone: form.phone.value
        };

        this.model.set(obj);
        //why the successful callback does not work????
        this.model.save(null, {success: function(model, response){console.log('successful');}});
    },

    render: function() {
        $('#retailer-list').append(this.$el.html(this.template(this.model.toJSON())));

        return this;
    }
});

var RetailerViews = Backbone.View.extend({

});

$('#submit').click(function(e){
    var retailer_model = new RetailerModel();
    console.log(retailer_model); // this prints out the new changed attributes instead of the default ones, why???
    var retailer_view = new RetailerView({model: retailer_model});
    form.reset();
});

2 个答案:

答案 0 :(得分:3)

1获取模型的正确状态

console.log(retailer_model)不会显示模型属性,它会显示整个模型,但console.log(retailer_model.attributes)会显示。另请注意,console.log 并不总是正确的,尤其是如果您在记录之后修改对象,这可能会导致混淆!

要获取模型的实际当前状态,您应该对其进行浅或深复制。因此,console.log(model)可以使用underscores clone方法进行浅层复制:

console.log(_(model).clone());

2保存成功回拨

为了帮助我们,我们真的需要更多地了解您的情况。我要寻找的第一件事是你的服务器是否正在返回正确的反馈。 Backbone是一个基于REST标准的系统。您确定您的服务器正在返回正确的响应代码吗?如果您使用chrome,请打开您的开发人员工具,然后打开网络选项卡,以检查您在发布模型时获得的响应。为了触发成功回调,服务器应返回200或201的状态。

另一种测试方法是查看错误回调是否正在激活:)。

答案 1 :(得分:1)

我试图看到你的错误,我意识到你错过了这些东西:
1。当DOM就绪事件被触发时,你应该做与DOM相关的事情:

$(function() { 
    form = document.forms[0];
    $(form).live('submit', function(e){
        // ...
    });
});


2。您可以使用submit表单。它还会在表单中捕获enter点击:

$(form).live('submit',function(){
    //...
});


3。您应该在提交表单中使用return false;。它可以防止默认表单数据发送到操作URL。

$(form).live('submit', function(e){
    // ...
    return false;
});

所以,它看起来像这样。我没有检查成功回调,但我希望它会起作用。

<html>
<head>
<script src="jquery-1.7.2.js" type="text/javascript"></script>
<script type="text/javascript" src="underscore.js"></script>
<script type="text/javascript" src="backbone.js"></script>
<script type="text/javascript">

var RetailerModel = Backbone.Model.extend({
    urlRoot: ' retailer.php',
    defaults: {
        name: 'company-name',
        address: 'company-address',
        phone: 'company-phone',
        icon: 'http://localhost/icon.png'
    }
});

var RetailerCollection = Backbone.Collection.extend({});

var RetailerView = Backbone.View.extend({

    className: 'retailer',

    //template: _.template($('#retailer-template').html()),

    initialize: function() {
        //this.listenTo(this.model, 'change', this.render);

        var obj = {
            name: form.name.value,
            address: form.address.value,
            phone: form.phone.value
        };

        this.model.set(obj);
        //why the successful callback does not work????
        this.model.save(null, {
            success: function(model, response){
                console.log('successful');
            }
        });
    },

    render: function() {
        $('#retailer-list').append(this.$el.html(this.template(this.model.toJSON())));
        return this;
    }
});

var RetailerViews = Backbone.View.extend({});
$(function() { // you should do DOM related things when DOM ready event fired
    form = document.forms[0];
    $(form).live('submit', function(e){
        var retailer_model = new RetailerModel();
        console.log(retailer_model);
        var retailer_view = new RetailerView({model: retailer_model});
        form.reset();

        return false; // to prevent form data sending return false
    });
});
</script>

</head>
<body>
    <form action="#" id="#submit">
        <input type="submit" value="submit"/>
        <input type="text" name="address"/>
        <input type="text" name="name"/>
        <input type="text" name="phone"/>
    </form>
</body>
</html>