/* 
 * To change this license header, choose License Headers in Project Properties.
 * To change this template file, choose Tools | Templates
 * and open the template in the editor.
 */

define(['jquery', 'underscore', 'backbone', 'classes/cache'],
        function ($, _, Backbone, Cache) {

            var CachedCollection = Backbone.Collection.extend({
                cacheName: null,
                fetch: function (options) {
                    options = _.defaults(options || {}, {parse: true});
                    var deferred = new $.Deferred(),
                            self = this;

                    var cachedItem = Cache.get(this.cacheName);

                    if (cachedItem !== null)
                    {
                        window.setTimeout(function () {
                            self[options.reset ? 'reset' : 'set'](false, options);
                            //deferred.resolve(cachedItem);

                            deferred.notify(self);
                            if(self.length == 1)
                                self.remove(self.models[0]);
                            self.push(cachedItem);
                            if (_.isFunction(options.success)) {
                                options.success(self, false, options);
                            }
                            deferred.resolve(cachedItem);
                            self.trigger('sync', self, false, options);
                            return deferred;
                        }, 0);
                    }
                    else
                    {
                        // Delegate to the actual fetch method and store the attributes in the cache
                        var jqXHR = Backbone.Collection.prototype.fetch.apply(this, arguments);
                        // resolve the returned promise when the AJAX call completes
                        jqXHR.done(_.bind(deferred.resolve, this, this))
                                // Set the new data in the cache
                                .done(_.bind(
                                        function (a, b, c) {
                                            Cache.set(self.cacheName, a);
                                        }
                                , null, this, options))
                                // Reject the promise on fail
                                .fail(_.bind(deferred.reject, this, this));

                        deferred.abort = jqXHR.abort;
                        // return a promise which provides the same methods as a jqXHR object
                        return deferred;
                    }
                },
                isCached: function () {
                    var cachedItem = Cache.get(this.cacheName);

                    return (cachedItem !== null);
                }
            });
            return CachedCollection;
        });
