'use strict';

var q = require("q");
var MongoConnection = require('./MongoConnection');
var UtilDocumentId = require('../../../../shared/utils/UtilDocumentId');
var logger = require('../../../utils/Logger').loggers.get('db');
var SharedConstants = require('../../../../shared/constants/SharedConstants');
var queryProjection = require('./MongoQueryProjection');
var DataService = require("../../DataService");

var updateCounter = function(documentId, counterFieldName){
    var deferred = q.defer();

    if (!documentId || !counterFieldName) {
        logger.debug("documentId or counterFieldName not provided in updateCounter");
        deferred.reject(new Error("A documentId and counterFieldName must be provided in the updateCounter function"));
    } else {
        MongoConnection.getCollection(function (err, collection) {
            if (err) {
                var errorMsg = "Error creating collection to updateCounter: " + err;
                logger.error(errorMsg);
                deferred.reject(new Error(errorMsg));
            } else {

                // Filter
                // - Counter documents now require "systemHeader.currentVersion" field
                var filter = {"documentId": documentId, "systemHeader.currentVersion": true};

                // Update
                // - use $inc to ensure counter value set correctly in multi-user environment
                var incUpdate = {};
                incUpdate[counterFieldName] = 1;
                var update = {
                    $set: {'systemHeader.serverUpdatedDate': new Date()},
                    $inc: incUpdate
                };

                // Options
                // - queryProjection (to exclude _id)
                // - returnOriginal to false (so that we can retrieve and use the updated counter value)
                var options = {};
                //options.projection = queryProjection;
                options.returnOriginal = false;

                // Use findOneAndUpdate function to find document and update it in one atomic operation
                collection.findOneAndUpdate(filter, update, options,
                    function(err, results) {
                        if(err) {
                            var errorMsg = "Error updating counter document." +
                                " Ensure counter document exists: " + documentId +
                                " - " + err;
                            logger.error(errorMsg);
                            deferred.reject(new Error(errorMsg));
                        } else if (results) {
                            deferred.resolve(results);
                        } else {
                            var errorMsg = "Error while calling findOneAndUpdate function on counter document." +
                                " documentId: " + documentId +
                                " counterFieldName: " + counterFieldName;
                            logger.error(errorMsg);
                            deferred.reject(new Error(errorMsg));
                        }
                    });
            }
        });
    }

    return deferred.promise;
};

module.exports = {
    updateCounter: updateCounter,

    getIndexId : function(document){
        var _id = document._id ;
        return _id.toHexString();
    }
};