module(..., package.seeall)

require("socket")
local http = require("socket.http")
local ltn12 = require("ltn12")
local m_utils = require "helpers.utils"

--[[

]]--
function Get (url, headers, cookie, callbackErr)
	assert(type(url) == "string")
	callbackErr = callbackErr or function() end
	--print("helpers.request.Get -> url: ".. tostring(url))
	--print("helpers.request.Get -> cookie: ".. tostring(cookie))
	headers = headers or {}
	if cookie and string.len(cookie) then
		headers["Cookie"] = cookie
	end
	local response_body = {}
	local result, code, header = socket.http.request{
		url = url,
		method = "GET",
		headers = headers,
		sink = ltn12.sink.table(response_body)
	}
	local response = table.concat(response_body, "")
	if code == 200 then
		return true, response
	end
	-- error
	local encodedError = response
	callbackErr()
	print ("error getting url " .. url .. ", result code:" .. code .. "\nbody:" .. encodedError)
	return false, encodedError, code
end

--[[

]]--
function Post (url, body, headers, cookie, callbackErr)
	assert(type(url) == "string")
	callbackErr = callbackErr or function() end
	--print("helpers.request.Post -> url: ".. tostring(url))
	--print("helpers.request.Post -> cookie: ".. tostring(cookie))
	headers = headers or {}
	headers["content-length"] = body and string.len(body) or 0
	if cookie and string.len(cookie) then
		headers["Cookie"] = cookie
	end
	local response_body = {}
	local result, code, header, statusline = socket.http.request{
		url = url,
		method = "POST",
		headers = headers,
		source = ltn12.source.string(body),
		sink = ltn12.sink.table(response_body)
	}
	local response = table.concat(response_body, "")
	if code == 200 then
		return true, response
	end
	-- error
	local encodedError = response
	callbackErr()
	print ("Error posting request, result code:" .. code .. "\nbody:" .. encodedError .. "\nstatusline:" .. tostring(statusline))
	return false, encodedError, code, statusline
end

--------------------------------------
--[[

]]--
local function MakeShortUrlkey (uid)
	assert(type(uid) == "string")
	local URLS_PARAMS_MAPPED_BY_UUID = "URLS_PARAMS_MAPPED_BY_UUID"
	local redisKey = string.format("%s:%s", URLS_PARAMS_MAPPED_BY_UUID, uid)
	--LogDebug("[HELPERS.request:MakeShortUrlkey] redisKey: %s", redisKey)
	return redisKey
end

--[[
	Convierte los parametros de una URL en tipo SHORT.

		Lo que queda como short son los parametros de URL NO toda la URL.
			como primer retorno llega el shortURL
			como segundo retorno la longURL (por si se necesita realizar algo)
		Ejemplo:
			parametros
				url = https://webdesigner-testubu.i6.inconcertcc.com/inconcert/apps/webdesigner/encuesta1
				parametros = interaction_id=96B1B85F62B74C283894461298DA5D00&campaignAtVCC=campmail1@vcc1&token=F38DF44B51FB21F21FBD54E0A8C4B007
			retorno
				short url: https://webdesigner-testubu.i6.inconcertcc.com/inconcert/apps/webdesigner/encuesta1?uuid=470e21c63c834ad8bc3dfcee8da7ffda
				long url : https://webdesigner-testubu.i6.inconcertcc.com/inconcert/apps/webdesigner/encuesta1?interaction_id=96B1B85F62B74C283894461298DA5D00&campaignAtVCC=campmail1@vcc1&token=F38DF44B51FB21F21FBD54E0A8C4B007

	El mapeo de los short parametros quedan en REDIS bajo la clave URLS_PARAMS_MAPPED_BY_UUID:el_id
		Ejemplo:
			La key de Redis
				URLS_PARAMS_MAPPED_BY_UUID:470e21c63c834ad8bc3dfcee8da7ffda
			queda con el valor
				interaction_id=96B1B85F62B74C283894461298DA5D00&campaignAtVCC=campmail1@vcc1&token=F38DF44B51FB21F21FBD54E0A8C4B007
]]--
function MakeShortURL (url, parameters, redis, info)
	assert(type(url) == "string")
	assert(type(parameters) == "string")
	assert(redis)
	info = info or {}
	assert(type(info) == "table")
	-- 1. el parametro es para que genere el UUID sin separadores.
	local urlParamsUUID = m_utils:Uuid(true):lower()
	local redisKey = MakeShortUrlkey(urlParamsUUID)
	redis:set(redisKey, parameters)
	if info.expireTimeSec then
		redis:expire(redisKey, info.expireTimeSec)
	end
	--LogDebug("[HELPERS.request:MakeShortURL] -saved RedisValue: %s", redis:get(redisKey))
	-- 2. short url - genero los short parametros que mapearan contra los parametros reales de la URL.
	local shortUrl = ("%s?uuid=%s"):format(url, urlParamsUUID)
	-- 3. long url - utilizada solo para el log.
	local longSurveyURL = ("%s?%s"):format(url, parameters)
	LogInfo("[HELPERS.request:MakeShortURL] Short URL expire in %s seconds.\nSHORT-> SURVEY_URL: '%s'\nLONG-> SURVEY_URL: '%s'.", info.expireTimeSec or "NONE", shortUrl, longSurveyURL)
	-- si llegamos a necesitar el long URL se envia como segundo parametro
	return shortUrl, longSurveyURL
end

--[[

]]--
function GetLongParamsUrlById (urlParamsUUID, redis)
	assert(type(urlParamsUUID) == "string")
	assert(redis)
	-- el parametro es para que genere el UUID sin separadores.
	local redisKey = MakeShortUrlkey(urlParamsUUID)
	local parameters = redis:get(redisKey)
	LogInfo("[HELPERS.request:GetLongParamsUrlById] urlParamsUUID: '%s' parameters: '%s'.", redisKey, parameters)
	return parameters
end
