local json = require "cjson"
local request = require "luis.request"
local luis_models = require("luis.models"):GetModels()
local utils = require "luis.utils"
require "socket" 

module(..., package.seeall)

local m_instanceOwner
function SetOwner (instanceOwner)
	m_instanceOwner = instanceOwner
end

local m_defaultApiVersion = "2022-10-01-preview"

local function GetBaseURI (id)
	id = id or "APPS"
	return m_instanceOwner:GetBaseURI(id)
end

local function MakeCompleteURI (uriBaseId, uri, apiVersion, ...)
	uriBaseId = uriBaseId or "APPS"
	return m_instanceOwner:MakeCompleteURI(m_defaultApiVersion, uriBaseId, uri, apiVersion, ...) 
end

local function MakePagingParameters (params)
	local api = require "luis"
	return api.MakePagingParameters(params)
end

function LoadAllAppEntities (appId, versionId, paginated)
	assert(appId)
	assert(versionId)

	local uri = MakeCompleteURI("APPS", "%s/versions/%s/prebuilts", appId, versionId)
	uri = uri .. MakePagingParameters(paginated)

	local success, response = request.Get(uri)
	if not success then
		LogError("[LUIS_ENTITIES_PREBUILT:LoadAllAppEntities] Error loading all APP PREBUILT ENTITIES on appId '%s' versionId: '%s'. Error: '%s'", appId, versionId, json.encode(response))
		return false, response
	end

	LogInfo("[LUIS_ENTITIES_PREBUILT:LoadAllAppEntities] Success loaded all APP PREBUILT ENTITIES on appId '%s' versionId: '%s'.", appId, versionId)

	local encodedEntities = table.concat(response)
	return true, encodedEntities
end

function CreateAppEntity (info)
	assert(type(info) == "table")
	assert(info.appId)
	assert(info.versionId)
	assert(info.entity)

	local uri = MakeCompleteURI("APPS", "%s/versions/%s/prebuilts", info.appId, info.versionId)
	local data = info.entity.list

	local success, response = request.Post(uri, data)
	if not success then
		LogError("[LUIS_ENTITIES_PREBUILT:CreateAppEntity] Error Adding APP PREBUILT ENTITIES on appId '%s' versionId: '%s'. Response: '%s'", info.appId, info.versionId, json.encode(response))
		return false, response
	end

	local entityId = table.concat(response)
	LogInfo("[LUIS_ENTITIES_PREBUILT:CreateAppEntity] Success Added APP PREBUILT ENTITIES on appId '%s', entityId: '%s' versionId: '%s'.", info.appId, entityId, info.versionId)

	return true, entityId
end

function DeleteAppEntity (appId, entityId, versionId)
	assert(appId)
	assert(entityId)
	assert(versionId)

	local uri = MakeCompleteURI("APPS", "%s/versions/%s/prebuilts/%s", appId, versionId, entityId)

	local success, response = request.Delete(uri)
	if not success then
		LogError("[LUIS_ENTITIES_PREBUILT:DeleteAppEntity] Error deleting APP PREBUILT ENTITIES '%s' versionId: '%s' on appId '%s'. Response: '%s'", entityId, versionId, appId, json.encode(response))
		return false, response
	end

	LogInfo("[LUIS_ENTITIES_PREBUILT:DeleteAppEntity] Success deleted APP PREBUILT ENTITIES '%s' versionId: '%s' on appId '%s'.", entityId, versionId, appId)

	return true, response
end

function GetLanguageStudioAccount (vcc)

	LogInfo(" ------> GetLanguageStudioAccount - vcc: %s", vcc)

	local vccAzureLanguageStudioAccounts, totalVCCAzureLanguageStudioAccounts = LoadVCCAzureLanguageStudioAccount(vcc) 
	local azureLanguageStudio = {} 
	if totalVCCAzureLanguageStudioAccounts > 0 then 
		local firstKey = next(vccAzureLanguageStudioAccounts) 
  		azureLanguageStudio = vccAzureLanguageStudioAccounts[firstKey] 
	else
		azureLanguageStudio = {} 
	end 

    return azureLanguageStudio.resource_name, azureLanguageStudio.subscription_key_1
	
end

function LoadVCCAzureLanguageStudioAccount (vcc, vcc_id)
	
	if type(vcc) == "table" then
		vcc = vcc_id
	end

	local vccAzureLanguageStudioAccounts = luis_models.VCCs.GetAzureLanguageStudioAccountsMsCognitiveServices(vcc)

	local total = utils.GetRowCount(vccAzureLanguageStudioAccounts)
	return vccAzureLanguageStudioAccounts, total
end

function LoadAvailablePrebuiltList (appId, versionId, vcc)
	assert(appId)
	assert(versionId)
	assert(vcc)

	local resource_name, subscription_key_1 = GetLanguageStudioAccount(vcc)

	local uri = MakeCompleteURI("APPS", "global/prebuilt-entities?api-version=2022-10-01-preview&language=en-us&multilingual=true")	
	uri = uri:gsub("resourcename", resource_name)

	LogInfo("[LUIS_APPS40:LoadAvailablePrebuiltList] uri: %s", uri)

	local additionalHeaders = {
		["Ocp-Apim-Subscription-Key"] = subscription_key_1
	}

	local success, response, headers = request.Get(uri, additionalHeaders)

	if not success then
		LogError("[LUIS_APPS40:LoadAvailablePrebuiltList] Error: '%s'", json.encode(response))
		return false, response
	end

	local encodedResponse = table.concat(response)			
	local parsedResponse = json.decode(encodedResponse)

	for i, item in ipairs(parsedResponse.value) do
		item.name = item.category
	end

	LogInfo("[LUIS_APPS40:LoadAvailablePrebuiltList] response: %s", json.encode(parsedResponse.value))

	return true, parsedResponse.value

end
