define(["dojo/_base/kernel", "dojo/_base/xhr", "dojo/request/xhr", "dojo/topic", "obno/core/Configuration", "dojo/when", "dojo/_base/Deferred",
        "obnogen/service/com/obno/core/SSOService"],
function(dojo, xhr, _xhr, topic, Configuration, when, Deferred, SSOSvc){

	var plainXhr = dojo._defaultXhr || xhr;
	var _plainXhr = _xhr;
	
	dojo[dojo._defaultXhr ? "_defaultXhr" : "xhr"] = function(/*String*/ method, /*dojo.__XhrArgs*/ args, /*Boolean?*/ hasBody){
		
		var doXHR = function(outer){
			args.headers = args.headers || {}; 
			args.headers["X-Session-Verify"] = "OBNO";
			var dfd = plainXhr(method, args, hasBody);
			if (outer){
				outer.ioArgs = dfd.ioArgs;
			}
			return dfd.addErrback(function(error){
				if (error.response){
					var response = error.response;
					if (response.status == 401){
						if (response.getHeader("X-oBno-Authenticate")){
							topic.publish("com.obno.application.global", {name: "obno-authenticate", url: response.url});
						}
					}
				}
			});			
		}
		
		//check whether we need to do something fancy with SSO tokens
		var conf = new Configuration();
		if ((true == conf.getValidateSSOTokenBeforeXHR()) &&
			args['url'] && 
		    args['url'].indexOf("obno/service/jsonrpc/com/obno/core/SSOService") == -1 &&
		    args['url'].indexOf("obno/service/jsonrpc/com/obno/core/ConfigurationService") == -1){
			var isSync = (true == args['sync']);
			var ssoSvc = new SSOSvc();
			var deferred = new Deferred();
			if (isSync){
				dojox.rpc._sync = true;
			}
			ssoSvc.getSSOSessionStatus().then(function(ret){
				return ret[0];
			}, function(err){
			}, function(update){
			}).then(function(status){
				if ("TERMINATED" == status){
					location.reload(true);
				}
				else {
					doXHR(deferred).then(function(ret){
						deferred.resolve(ret);
					}, function(err){
						deferred.reject(err);
					});
				}								
			}, function(err){
				doXHR(deferred).then(function(ret){
					deferred.resolve(ret);
				}, function(err){
					deferred.reject(err);
				});
			});
			if (isSync){
				delete dojox.rpc._sync;
			}
			return deferred;
		} else {
			//execute original service
			return doXHR(null);
		}
	};
	
	
	
});