local function _loaded_mod_src_ao_yield_agent_libs_constants()local mod={PERMASWAP_AO_WAR_POOL_ID="FRF1k0BSv0gRzNA2n-95_Fpz9gADq9BGi5PyXKFp6r8",PERMASWAP_AO_WUSDC_POOL_ID="gjnaCsEd749ZXeG2H8akvf8wzbl7CQ4Ox-KYEBAdONk",BOTEGA_AO_WAR_POOL_ID="B6qAwHi2OjZmyFCEU8hV6FZDSHbAOz8r0yy-fBbuTus",BOTEGA_AO_WUSDC_POOL_ID="TYqlQ2vqkF0H6nC0mCgGe6G12pqq9DsSXpvtHYc6_xY",BOTEGA_AMM_FACTORY_ID="3XBGLrygs11K63F_7mldWz4veNx6Llg6hI2yZs8LKHo",AO_PROCESS_ID="0syT13r0s0tgPmIed95bJnuSqaD29HQNN8D3ElLSrsc",WAR_PROCESS_ID="xU9zFkq3X2ZQ6olwNVvr1vUWIjc3kXTWr7xKQD6dh10",WUSDC_PROCESS_ID="7zH9dlMNoxprab9loshv3Y7WG45DOny_Vrq9KrXObdQ"}mod.PERMASWAP_POOL_IDS={[mod.WAR_PROCESS_ID]=mod.PERMASWAP_AO_WAR_POOL_ID,[mod.WUSDC_PROCESS_ID]=mod.PERMASWAP_AO_WUSDC_POOL_ID}mod.BOTEGA_POOL_IDS={[mod.WAR_PROCESS_ID]=mod.BOTEGA_AO_WAR_POOL_ID,[mod.WUSDC_PROCESS_ID]=mod.BOTEGA_AO_WUSDC_POOL_ID}return mod end;_G.package.loaded["src.ao_yield_agent.libs.constants"]=_loaded_mod_src_ao_yield_agent_libs_constants()local function _loaded_mod_src_commonlibs_aolibs()local mod={}local mod_json;local mod_bint;local jsonstatus,json=pcall(require,"json")if jsonstatus then mod_json=json else if not mod_json then print("Library 'json' does not exist. Using fallback dkjson.")end;local dkjsonstatus,dkjson=pcall(require,"dkjson")mod_json=dkjson end;local bintstatus,bint=pcall(require,".bint")if bintstatus then mod_bint=bint else if not mod_bint then print("Library '.bint' does not exist. Using fallback https://github.com/permaweb/aos/blob/main/process/bint.lua")end;local copiedbintstatus,copiedbint=pcall(require,"src.commonlibs.bint")mod_bint=copiedbint end;mod.bint=function(bits,word_bits)if not bits or type(bits)~="number"then bits=1024 end;local instance=mod_bint(bits,word_bits)return instance end;mod.json=mod_json;return mod end;_G.package.loaded["src.commonlibs.aolibs"]=_loaded_mod_src_commonlibs_aolibs()local function _loaded_mod_src_ao_yield_agent_libs_enums()local DexType={PERMASWAP="Permaswap",BOTEGA="Botega",Auto="Auto"}local AgentStatus={ACTIVE="Active",CANCELLED="Cancelled",COMPLETED="Completed"}local enums={DexType=DexType,AgentStatus=AgentStatus}return enums end;_G.package.loaded["src.ao_yield_agent.libs.enums"]=_loaded_mod_src_ao_yield_agent_libs_enums()local function _loaded_mod_src_ao_yield_agent_utils()local aolibs=require('src.commonlibs.aolibs')local enums=require('src.ao_yield_agent.libs.enums')local bint=aolibs.bint(1024)local utils={add=function(a,b)return tostring(bint(a)+bint(b))end,subtract=function(a,b)return tostring(bint(a)-bint(b))end,mul=function(a,b)return tostring(bint.__mul(bint(a),bint(b)))end,div=function(a,b)return tostring(bint.udiv(bint(a),bint(b)))end,lt=function(a,b)return bint.__lt(bint(a),bint(b))end,lte=function(a,b)return bint.__lt(bint(a),bint(b))or bint.__eq(bint(a),bint(b))end,gt=function(a,b)return bint.__lt(bint(b),bint(a))end,gte=function(a,b)return bint.__lt(bint(b),bint(a))or bint.__eq(bint(b),bint(a))end,isZero=function(a)return bint.__eq(bint(a),bint("0"))end}function utils.isAddress(addr)if type(addr)~="string"then return false end;if string.len(addr)~=43 then return false end;if string.match(addr,"^[A-z0-9_-]+$")==nil then return false end;return true end;function utils.isValidNumber(val)return type(val)=="number"and val==val and val~=math.huge and val~=-math.huge end;function utils.isValidInteger(val)return utils.isValidNumber(val)and val%1==0 end;function utils.isBintRaw(val)local success,result=pcall(function()if type(val)~="number"and type(val)~="string"and not bint.isbint(val)then return false end;if type(val)=="number"and not utils.isValidInteger(val)then return false end;return true end)return success and result end;function utils.isTokenQuantity(qty)local numVal=tonumber(qty)if not numVal or numVal<=0 then return false end;if not utils.isBintRaw(qty)then return false end;if type(qty)=="number"and qty<0 then return false end;if type(qty)=="string"and string.sub(qty,1,1)=="-"then return false end;return true end;function utils.isPercentage(val)if not val or type(val)~="number"then return false end;return val//1==val and val>=0 and val<=100 end;function utils.isValidDex(val)return val==enums.DexType.PERMASWAP or val==enums.DexType.BOTEGA or val==enums.DexType.Auto end;function utils.isValidSlippage(val)if not val or type(val)~="number"then return false end;return val//1==val and val>=0.5 and val<=10 end;function utils.isValidRunningTime(startDate,endDate)if not startDate or not endDate then return false end;return startDate<=endDate end;function utils.isValidBoolean(val)return val=="true"or val=="false"end;function utils.isValidStatus(val)return val==enums.AgentStatus.ACTIVE or val==enums.AgentStatus.CANCELLED or val==enums.AgentStatus.COMPLETED end;function utils.hasReachedEndDate()if not EndDate then return false end;local currentTime=os.time()local swappedOrProcessed=SwappedUpToDate or ProcessedUpToDate or 0;return currentTime>=EndDate and currentTime>=swappedOrProcessed end;function utils.isValidAgentVersion(version)if not version or type(version)~="string"then return false end;local major,minor,patch=version:match("^(%d+)%.(%d+)%.(%d+)$")if not major then return false end;major=tonumber(major)minor=tonumber(minor)patch=tonumber(patch)if not major or not minor or not patch then return false end;if major<0 or minor<0 or patch<0 then return false end;return true end;return utils end;_G.package.loaded["src.ao_yield_agent.utils"]=_loaded_mod_src_ao_yield_agent_utils()local function _loaded_mod_src_ao_yield_agent_libs_token()local constants=require('src.ao_yield_agent.libs.constants')local utils=require('src.ao_yield_agent.utils')local mod={}function mod.getBalance(tokenId)local result=ao.send({Target=tokenId,Action="Balance"}).receive()return result.Tags.Balance end;function mod.getAOBalance()return mod.getBalance(constants.AO_PROCESS_ID)end;function mod.transferToRecipient(tokenId,quantity,recipient)ao.send({Target=tokenId,Action="Transfer",Recipient=recipient,Quantity=quantity})end;function mod.transferToSelf(tokenId,quantity)mod.transferToRecipient(tokenId,quantity,Owner)end;function mod.transferRemainingBalanceToSelf()local aoBalance=mod.getAOBalance()if(not utils.isZero(aoBalance))then mod.transferToSelf(constants.AO_PROCESS_ID,aoBalance)end;local warBalance=mod.getBalance(constants.WAR_PROCESS_ID)if(not utils.isZero(warBalance))then mod.transferToSelf(constants.WAR_PROCESS_ID,warBalance)end;local wusdcBalance=mod.getBalance(constants.WUSDC_PROCESS_ID)if(not utils.isZero(wusdcBalance))then mod.transferToSelf(constants.WUSDC_PROCESS_ID,wusdcBalance)end end;return mod end;_G.package.loaded["src.ao_yield_agent.libs.token"]=_loaded_mod_src_ao_yield_agent_libs_token()local function _loaded_mod_src_ao_yield_agent_libs_permaswap()local utils=require('src.ao_yield_agent.utils')local json=require('json')local mod={}local function isSwapConfirmation(msg,noteSettle)return msg.Tags.Action=='Credit-Notice'and msg.Tags.Sender==noteSettle and msg.Tags["X-FFP-For"]=="Settled"end;local function isSwapRefund(msg,noteSettle)return msg.Tags.Action=='Credit-Notice'and msg.Tags.Sender==noteSettle and msg.Tags["X-FFP-For"]=="Refund"end;function mod._awaitSwap(noteSettle)local response=Receive(function(msg)return isSwapConfirmation(msg,noteSettle)or isSwapRefund(msg,noteSettle)end)if isSwapConfirmation(response,noteSettle)then return true,response else return false,response end end;function mod.getExpectedOutput(poolId,tokenIn,amountIn)local swapOutput=ao.send({Target=poolId,Action="GetAmountOut",AmountIn=amountIn,TokenIn=tokenIn}).receive()local amountOut=(swapOutput and swapOutput.AmountOut)or"0"local adjustedSlippage=math.floor(Slippage*100)local expectedMinOutput=utils.div(utils.mul(amountOut,utils.subtract(10000,adjustedSlippage)),10000)return{amountOut=tostring(amountOut),expectedMinOutput=tostring(expectedMinOutput)}end;function mod.requestOrder(poolId,tokenIn,tokenOut,amountIn,amountOut)local requestOrder=ao.send({Target=poolId,Action="RequestOrder",TokenIn=tokenIn,TokenOut=tokenOut,AmountIn=tostring(amountIn),AmountOut=tostring(amountOut)}).receive()return requestOrder end;function mod.swap(result)ao.send({Target=result.tokenIn,Action="Transfer",Recipient=result.noteSettle,Quantity=result.amountIn,["X-FFP-For"]="Settle",["X-FFP-NoteIDs"]=json.encode({result.noteId})})return mod._awaitSwap(result.noteSettle)end;return mod end;_G.package.loaded["src.ao_yield_agent.libs.permaswap"]=_loaded_mod_src_ao_yield_agent_libs_permaswap()local function _loaded_mod_src_ao_yield_agent_libs_botega()local utils=require("src.ao_yield_agent.utils")local constants=require("src.ao_yield_agent.libs.constants")local mod={}local function isSwapConfirmation(msg,poolId)return msg.From==constants.BOTEGA_AMM_FACTORY_ID and msg.Tags["Relayed-From"]==poolId and msg.Tags["Relay-To"]==ao.id and msg.Tags.Action=='Order-Confirmation'end;local function isSwapRefund(msg,poolId)return msg.Tags.Action=='Credit-Notice'and msg.Tags.Sender==poolId and msg.Tags["X-Refunded-Order"]~=nil end;function mod._awaitSwap(poolId)local response=Receive(function(msg)return isSwapConfirmation(msg,poolId)or isSwapRefund(msg,poolId)end)if isSwapConfirmation(response,poolId)then return true,response else return false,response end end;function mod.getExpectedOutput(poolId,tokenIn,amountIn)local swapOutput=ao.send({Target=poolId,Action="Get-Swap-Output",Tags={Token=tokenIn,Quantity=tostring(amountIn),Swapper=ao.id}}).receive()local amountOut=(swapOutput and swapOutput.Output)or"0"local adjustedSlippage=math.floor(Slippage*100)local expectedMinOutput=utils.div(utils.mul(amountOut,utils.subtract(10000,adjustedSlippage)),10000)return{amountOut=tostring(amountOut),expectedMinOutput=tostring(expectedMinOutput)}end;function mod.getSwapNonce()return os.time().."-"..math.random(100000000,999999999)end;function mod.swap(result)ao.send({Target=result.tokenIn,Action="Transfer",Recipient=result.poolId,Quantity=result.amountIn,["X-Expected-Min-Output"]=result.expectedMinOutput,["X-Swap-Nonce"]=mod.getSwapNonce(),["X-Action"]="Swap"})return mod._awaitSwap(result.poolId)end;return mod end;_G.package.loaded["src.ao_yield_agent.libs.botega"]=_loaded_mod_src_ao_yield_agent_libs_botega()local function _loaded_mod_src_ao_yield_agent_libs_swap()local constants=require('src.ao_yield_agent.libs.constants')local permaswap=require('src.ao_yield_agent.libs.permaswap')local botega=require('src.ao_yield_agent.libs.botega')local utils=require('src.ao_yield_agent.utils')local enums=require('src.ao_yield_agent.libs.enums')local aolibs=require('src.commonlibs.aolibs')local token=require('src.ao_yield_agent.libs.token')local json=require('json')local bint=aolibs.bint(1024)local mod={}function mod.getFeeInfo(quantity)local result=ao.send({Target=FeeProcessId,Action="Get-Fee",Tags={Target=Owner,Quantity=quantity or"0",["Fee-Type"]="defi"}}).receive()local swapFeePercent=tonumber(result.Tags["Final-Fee-Percent"])local adjustedSwapFeePercent=math.floor(swapFeePercent*100)local feeSavings=utils.subtract(result.Tags["Original-Fee"],result.Tags["Final-Fee"])return{SwapFeePercent=tostring(adjustedSwapFeePercent),FeeRecipient=result.Tags["Fee-Recipient"],FeeSavings=feeSavings}end;function mod.retrySwap(msg,params)local dex=params.dex;local feeInfo=params.feeInfo;local pushedFor=params.pushedFor;local balance=params.balance;local retry=params.retry;if retry and Dex==enums.DexType.Auto then if dex==enums.DexType.PERMASWAP then mod.swapAOTokenWithPermaswap(msg,nil,feeInfo,pushedFor,balance,false)elseif dex==enums.DexType.BOTEGA then mod.swapAOTokenWithBotega(msg,nil,feeInfo,pushedFor,balance,false)end end end;function mod.swapAOToken(msg,pushedFor)local tokenIn=constants.AO_PROCESS_ID;local tokenOut=msg.Tags["Token-Out"]or TokenOut;local permaswapPoolId=constants.PERMASWAP_POOL_IDS[tokenOut]local botegaPoolId=constants.BOTEGA_POOL_IDS[tokenOut]local amountIn=token.getAOBalance()or msg.Tags.Quantity;assert(bint.__lt(0,bint(amountIn)),'Quantity must be greater than 0')local dex=(utils.isValidDex(msg.Tags["X-Dex"])and msg.Tags["X-Dex"])or Dex;if dex==enums.DexType.PERMASWAP then mod.swapAOTokenWithPermaswap(msg,nil,nil,pushedFor,amountIn,true)elseif dex==enums.DexType.BOTEGA then mod.swapAOTokenWithBotega(msg,nil,nil,pushedFor,amountIn,true)else local permaswapOutput=permaswap.getExpectedOutput(permaswapPoolId,tokenIn,amountIn)local botegaOutput=botega.getExpectedOutput(botegaPoolId,tokenIn,amountIn)local feeInfo=mod.getFeeInfo(amountIn)if(utils.isZero(permaswapOutput.amountOut)and utils.isZero(botegaOutput.amountOut))then mod.replyWithSwapError(msg,"Amount out is zero")return end;if utils.lt(permaswapOutput.amountOut,botegaOutput.amountOut)then mod.swapAOTokenWithBotega(msg,botegaOutput,feeInfo,pushedFor,amountIn,true)else mod.swapAOTokenWithPermaswap(msg,permaswapOutput,feeInfo,pushedFor,amountIn,true)end end end;function mod.swapAOTokenWithPermaswap(msg,expectedOutput,feeInfo,pushedFor,balance,retry)local tokenIn=constants.AO_PROCESS_ID;local tokenOut=msg.Tags["Token-Out"]or TokenOut;local poolId=constants.PERMASWAP_POOL_IDS[tokenOut]local quantity=balance or token.getAOBalance()assert(bint.__lt(0,bint(quantity)),'Quantity must be greater than 0')feeInfo=feeInfo or mod.getFeeInfo(quantity)local fee=utils.div(utils.mul(quantity,feeInfo.SwapFeePercent),10000)local amountIn=utils.subtract(quantity,fee)local output=expectedOutput or permaswap.getExpectedOutput(poolId,tokenIn,amountIn)local retryParams={feeInfo=feeInfo,pushedFor=pushedFor,balance=quantity,retry=retry,dex=enums.DexType.BOTEGA}if(not utils.lte(output.expectedMinOutput,"0"))then local requestOrder=permaswap.requestOrder(poolId,tokenIn,tokenOut,amountIn,output.expectedMinOutput)local result={noteId=requestOrder.NoteID,noteSettle=requestOrder.NoteSettle,tokenIn=tokenIn,tokenOut=tokenOut,amountIn=tostring(amountIn),amountOut=tostring(output.amountOut),poolId=poolId,expectedMinOutput=tostring(output.expectedMinOutput)}if result.noteId and result.noteSettle then local success,swapResult=permaswap.swap(result)if(success)then token.transferToSelf(tokenOut,swapResult.Tags.Quantity)mod.swapSuccess(msg,{tokenOut=tokenOut,amountIn=quantity,amountOut=swapResult.Tags.Quantity,fee=fee,feeRecipient=feeInfo.FeeRecipient,dex=enums.DexType.PERMASWAP,swapDateFrom=msg.Tags["X-Swap-Date-From"],swapDateTo=msg.Tags["X-Swap-Date-To"],pushedFor=pushedFor,feeSavings=feeInfo.FeeSavings})else SwapInProgress=false;mod.replyWithSwapError(msg,result)mod.retrySwap(msg,retryParams)end else SwapInProgress=false;mod.replyWithSwapError(msg,result)mod.retrySwap(msg,retryParams)end else SwapInProgress=false;mod.replyWithSwapError(msg,"Amount out is zero")mod.retrySwap(msg,retryParams)end end;function mod.swapAOTokenWithBotega(msg,expectedOutput,feeInfo,pushedFor,balance,retry)local tokenIn=constants.AO_PROCESS_ID;local tokenOut=msg.Tags["Token-Out"]or TokenOut;local poolId=constants.BOTEGA_POOL_IDS[tokenOut]local quantity=balance or token.getAOBalance()assert(bint.__lt(0,bint(quantity)),'Quantity must be greater than 0')feeInfo=feeInfo or mod.getFeeInfo(quantity)local fee=utils.div(utils.mul(quantity,feeInfo.SwapFeePercent),10000)local amountIn=utils.subtract(quantity,fee)local output=expectedOutput or botega.getExpectedOutput(poolId,tokenIn,amountIn)local result={tokenIn=tokenIn,tokenOut=tokenOut,amountIn=tostring(amountIn),amountOut=tostring(output.amountOut),expectedMinOutput=tostring(output.expectedMinOutput),poolId=poolId}local retryParams={feeInfo=feeInfo,pushedFor=pushedFor,balance=quantity,retry=retry,dex=enums.DexType.PERMASWAP}if(not utils.lte(result.expectedMinOutput,"0"))then local success,swapResult=botega.swap(result)if(success)then mod.swapSuccess(msg,{tokenOut=tokenOut,amountIn=quantity,amountOut=swapResult.Tags["To-Quantity"],fee=fee,feeRecipient=feeInfo.FeeRecipient,dex=enums.DexType.BOTEGA,swapDateFrom=msg.Tags["X-Swap-Date-From"],swapDateTo=msg.Tags["X-Swap-Date-To"],pushedFor=pushedFor,feeSavings=feeInfo.FeeSavings})else SwapInProgress=false;mod.replyWithSwapError(msg,result)mod.retrySwap(msg,retryParams)end else SwapInProgress=false;mod.replyWithSwapError(msg,"Amount out is zero")mod.retrySwap(msg,retryParams)end end;function mod.swapSuccess(msg,swapInfo)local amountIn=swapInfo.amountIn;local fee=swapInfo.fee;local feeRecipient=swapInfo.feeRecipient;local currentTime=msg.Timestamp;local swapUpToDate=tonumber(swapInfo.swapDateTo)or currentTime;if(not SwappedUpToDate)then SwappedUpToDate=swapUpToDate else SwappedUpToDate=math.max(SwappedUpToDate,swapUpToDate)end;TotalTransactions=TotalTransactions+1;TotalAOSold=utils.add(TotalAOSold,amountIn)TotalWanderFee=utils.add(TotalWanderFee,fee)TotalBought[swapInfo.tokenOut]=utils.add(TotalBought[swapInfo.tokenOut]or"0",swapInfo.amountOut)SwapInProgress=false;if(utils.hasReachedEndDate())then Status=enums.AgentStatus.COMPLETED;ao.send({Target=ao.id,Action="Finalize-Agent"})end;token.transferToRecipient(constants.AO_PROCESS_ID,fee,feeRecipient)mod.replyWithSwapSuccess({amountIn=amountIn,amountOut=swapInfo.amountOut,tokenIn=constants.AO_PROCESS_ID,tokenOut=swapInfo.tokenOut,fee=fee,swapDateFrom=swapInfo.swapDateFrom,swapDateTo=swapInfo.swapDateTo,dex=swapInfo.dex,parentTxId=swapInfo.pushedFor,feeSavings=swapInfo.feeSavings})end;function mod.replyWithSwapSuccess(swapResult)local tags={["Amount-In"]=swapResult.amountIn,["Amount-Out"]=swapResult.amountOut,["Swap-Fee"]=swapResult.fee,["Token-In"]=swapResult.tokenIn,["Token-Out"]=swapResult.tokenOut,["Agent-Version"]=AgentVersion,["Dex"]=swapResult.dex,["Parent-Tx-Id"]=swapResult.parentTxId,["Fee-Savings"]=swapResult.feeSavings,["Agent-Owner"]=Owner}if swapResult.swapDateFrom and swapResult.swapDateTo then tags["Swap-Date-From"]=swapResult.swapDateFrom;tags["Swap-Date-To"]=swapResult.swapDateTo end;ao.send({Target=Owner,Data="Swap request processed successfully",Action="Swap-Success",Tags=tags})end;function mod.replyWithSwapError(msg,result)msg.reply({Data="Failed to process swap: "..(json.encode(result)or"Unknown error occurred"),Action="Swap-Error",Tags={Error="SwapProcessingFailed",Status="Failed",["Agent-Version"]=AgentVersion}})end;return mod end;_G.package.loaded["src.ao_yield_agent.libs.swap"]=_loaded_mod_src_ao_yield_agent_libs_swap()local function _loaded_mod_src_ao_yield_agent_libs_assertions()local utils=require("src.ao_yield_agent.utils")local enums=require("src.ao_yield_agent.libs.enums")local mod={}function mod.isTokenQuantity(name,quantity)local numQuantity=tonumber(quantity)assert(utils.isTokenQuantity(numQuantity),"Invalid quantity `"..name.."`. Must be a valid token quantity.")end;mod.isAddress=function(name,value)assert(utils.isAddress(value),"Invalid address `"..name.."`. Must be a valid Arweave address.")end;mod.isPercentage=function(name,value)assert(utils.isPercentage(value),"Invalid percentage `"..name.."`. Must be a valid percentage.")end;mod.checkWalletForPermission=function(msg,errorMessage)assert(ao.id==msg.From or Owner==msg.From,errorMessage or"Wallet does not have permission to update.")end;mod.isValidDex=function(name,value)assert(utils.isValidDex(value),"Invalid dex `"..name.."`. Must be a valid dex.")end;mod.isValidSlippage=function(name,value)assert(utils.isValidSlippage(value),"Invalid slippage `"..name.."`. Must be a valid slippage.")end;mod.isValidRunningTime=function(name1,name2,startDate,endDate)assert(utils.isValidRunningTime(startDate,endDate),"Invalid running time `"..name1.."` and `"..name2.."`. Must be a valid running time.")end;mod.isAgentActive=function()assert(Status==enums.AgentStatus.ACTIVE,"Agent is not active.")end;return mod end;_G.package.loaded["src.ao_yield_agent.libs.assertions"]=_loaded_mod_src_ao_yield_agent_libs_assertions()local constants=require('src.ao_yield_agent.libs.constants')local token=require('src.ao_yield_agent.libs.token')local swap=require('src.ao_yield_agent.libs.swap')local assertions=require('src.ao_yield_agent.libs.assertions')local utils=require('src.ao_yield_agent.utils')local enums=require('src.ao_yield_agent.libs.enums')local json=require('json')Status=Status or enums.AgentStatus.ACTIVE;Dex=Dex or ao.env.Process.Tags["Dex"]or enums.DexType.Auto;TokenOut=TokenOut or ao.env.Process.Tags["Token-Out"]or constants.WAR_PROCESS_ID;Slippage=Slippage or tonumber(ao.env.Process.Tags["Slippage"])or 0.5;StartDate=StartDate or tonumber(ao.env.Process.Tags["Start-Date"])or os.time()EndDate=EndDate or tonumber(ao.env.Process.Tags["End-Date"])or math.huge;RunIndefinitely=RunIndefinitely or ao.env.Process.Tags["Run-Indefinitely"]=="true"ConversionPercentage=ConversionPercentage or tonumber(ao.env.Process.Tags["Conversion-Percentage"])or 50;TotalTransactions=TotalTransactions or 0;TotalAOSold=TotalAOSold or"0"TotalWanderFee=TotalWanderFee or"0"TotalBought=TotalBought or{}ProcessedUpToDate=ProcessedUpToDate or nil;SwapInProgress=SwapInProgress or false;SwappedUpToDate=SwappedUpToDate or nil;FeeProcessId=FeeProcessId or"rkAezEIgacJZ_dVuZHOKJR8WKpSDqLGfgPJrs_Es7CA"AgentVersion=AgentVersion or ao.env.Process.Tags["Agent-Version"]or"1.0.1"Handlers.add("Info","Info",function(msg)msg.reply({Action="Info-Response",["Start-Date"]=tostring(StartDate),["End-Date"]=tostring(EndDate),Dex=Dex,["Token-Out"]=TokenOut,Slippage=tostring(Slippage),Status=Status,["Run-Indefinitely"]=tostring(RunIndefinitely),["Conversion-Percentage"]=tostring(ConversionPercentage),["Total-Transactions"]=tostring(TotalTransactions),["Total-AO-Sold"]=tostring(TotalAOSold),["Total-Wander-Fee"]=tostring(TotalWanderFee),["Total-Bought"]=json.encode(TotalBought),["Swap-In-Progress"]=tostring(SwapInProgress),["Processed-Up-To-Date"]=tostring(ProcessedUpToDate),["Swapped-Up-To-Date"]=tostring(SwappedUpToDate),["Agent-Version"]=AgentVersion})end)Handlers.add("Update-Agent","Update-Agent",function(msg)assertions.checkWalletForPermission(msg)assertions.isAgentActive()if(utils.isValidDex(msg.Tags.Dex))then Dex=msg.Tags.Dex end;if(utils.isValidSlippage(tonumber(msg.Tags.Slippage)))then Slippage=tonumber(msg.Tags.Slippage)end;if(utils.isValidRunningTime(tonumber(msg.Tags["Start-Date"]),tonumber(msg.Tags["End-Date"])))then StartDate=tonumber(msg.Tags["Start-Date"])EndDate=tonumber(msg.Tags["End-Date"])end;if(utils.isAddress(msg.Tags["Token-Out"]))then TokenOut=msg.Tags["Token-Out"]end;if(utils.isValidBoolean(msg.Tags["Run-Indefinitely"]))then RunIndefinitely=msg.Tags["Run-Indefinitely"]=="true"end;if(utils.isPercentage(tonumber(msg.Tags["Conversion-Percentage"])))then ConversionPercentage=tonumber(msg.Tags["Conversion-Percentage"])end;if(utils.isValidStatus(msg.Tags.Status))then Status=msg.Tags.Status;if(Status==enums.AgentStatus.COMPLETED or Status==enums.AgentStatus.CANCELLED)then ao.send({Target=ao.id,Action="Finalize-Agent"})end end;if(utils.isValidAgentVersion(msg.Tags["Agent-Version"]))then AgentVersion=msg.Tags["Agent-Version"]end end)Handlers.add("Swap-Permaswap","Swap-Permaswap",function(msg)assertions.checkWalletForPermission(msg,"Wallet does not have permission to swap.")SwapInProgress=true;swap.swapAOTokenWithPermaswap(msg,nil,nil,msg.Id)end)Handlers.add("Swap-Botega","Swap-Botega",function(msg)assertions.checkWalletForPermission(msg,"Wallet does not have permission to swap.")SwapInProgress=true;swap.swapAOTokenWithBotega(msg,nil,nil,msg.Id)end)Handlers.add("Withdraw","Withdraw",function(msg)assertions.checkWalletForPermission(msg,"Wallet does not have permission to withdraw.")local tokenId=msg.Tags["Token-Id"]local quantity=msg.Tags["Quantity"]assertions.isAddress("Token-Id",tokenId)assertions.isTokenQuantity("Quantity",quantity)token.transferToSelf(tokenId,quantity)end)Handlers.add("Credit-Notice","Credit-Notice",function(msg)local tokenId=msg.From or msg.Tags["From-Process"]local quantity=msg.Tags.Quantity;local pushedFor=msg.Tags["Pushed-For"]if tokenId==constants.AO_PROCESS_ID then SwapInProgress=true;ProcessedUpToDate=tonumber(msg.Tags["X-Swap-Date-To"])or os.time()swap.swapAOToken(msg,pushedFor)elseif tokenId==constants.WAR_PROCESS_ID or tokenId==constants.WUSDC_PROCESS_ID then token.transferToSelf(tokenId,quantity)end end)Handlers.add("Finalize-Agent","Finalize-Agent",function(msg)assertions.checkWalletForPermission(msg,"Wallet does not have permission to finalize the agent.")SwapInProgress=true;local aoBalance=token.getAOBalance()if(not utils.isZero(aoBalance))then swap.swapAOToken(msg,msg.Id)end;token.transferRemainingBalanceToSelf()end)