Bot Engine - Strooth Version [FEBE Mod]

stable
By Strooth in Trading Bots Published June 2021 👁 1,815 views 💬 4 comments

Description

A modified version of Pshai's FEBE 1. Install all of these (they have their own requirements as well ) Required - https://www.haasscripts.com/t/cmd-weighted-slot-spread-price-and-amount/ Required - https://www.haasscripts.com/t/bot-engine-settings-strooth-version-febe-mod/ Required - https://www.haasscripts.com/t/cmd-totext/ Required - https://www.haasscripts.com/t/cmd-backtestsettings-strooth-mod Required - https://www.haasscripts.com/t/cmdsetperc/ Required - https://www.haasscripts.com/t/cmd-vpm-haasscript-version/ 2. Install this bot engine itself 3. load the up ve template and play around with some ideas or VE Template - https://www.haasscripts.com/t/bot-engine-template-ve-strooth-version-febe-mod/ 4. Create a new script in se and as in the example below An Example of how to use the bot engine in Haas Script without the VE Template provided is in the first 4 lines of the bot engine but here it is anyway
local defaults = CC_BotEngine_Settings({}, true, 'S', 10, MinimumTradeAmount(), 0.1, 0.1, 0.1, false, false, LimitOrderType, 600, false, false, 1440, 14, 1, true, LimitOrderType, 600, false, false, 1440, 14, 1, true, 1, LimitOrderType, true, 1, LimitOrderType)
local default = CC_BotEngine_Settings(defaults, true, 'L', 10, MinimumTradeAmount(), 0.1, 0.1, 0.1, false, true, LimitOrderType, 600, false, false, 1440, 14, 1, false, LimitOrderType, 600, false, false, 1440, 14, 1, true, 1, LimitOrderType, true, 1, LimitOrderType)

CC_BotEngine(default , true, false)
HaasScript
DefineCommand('BotEngine', 'Execute Bot Engine logic with parameters')
EnableHighSpeedUpdates(true)
local defaults = CC_BotEngine_Settings({}, true, 'S', 10, MinimumTradeAmount(), 0.1, 0.1, 0.1, false, false, LimitOrderType, 600, false, false, 1440, 14, 1, true, LimitOrderType, 600, false, false, 1440, 14, 1, true, 1, LimitOrderType, true, 1, LimitOrderType)
local default = CC_BotEngine_Settings(defaults, true, 'L', 10, MinimumTradeAmount(), 0.1, 0.1, 0.1, false, true, LimitOrderType, 600, false, false, 1440, 14, 1, false, LimitOrderType, 600, false, false, 1440, 14, 1, true, 1, LimitOrderType, true, 1, LimitOrderType)
local ps = DefineParameter(ListDynamicType, 'params', 'Parameters for the core logic', false, default)
local backtest = DefineParameter(BooleanType, 'backtest', 'Enable backtest settings', false, true)

--=================================================================================================================================================
--- Logger Functions
--=================================================================================================================================================
local LoggerLevels = {
    ErrorsOnly = 'Errors Only',
    ErrorsAndWarnings = 'Erorrs & Warnings',
    All = 'All'
}
local Logger = {
    _level = InputOptions('DEBUG Level',
            LoggerLevels.All,
            LoggerLevels,
            {group = '     DEBUG'}),
    _in = 'Main',
    _prevIn = {},
    _log = Log,
    _warn = LogWarning,
    _error = LogError
}
local verbose = DefineParameter(BooleanType, 'log', 'show logs', false, Input('DEBUG Enable', false, {group = '     DEBUG'}))
function Logger:level()
    if Logger._level == LoggerLevels.ErrorsOnly then
        return 0
    elseif Logger._level == LoggerLevels.ErrorsAndWarnings then
        return 1
    elseif Logger._level == LoggerLevels.All then
        return 2
    end

    LogError('Logger level undefined: "' .. Logger._level .. '"')
end
function Logger:where()
    local ret = ''
    local prevs = self._prevIn
    if #prevs > 0 then
        for i = 1, #prevs do
            if prevs[i] != '' and #prevs[i] > 0 then
                ret = ret .. prevs[i] .. '::'
            end
        end
    end
    return ret .. self._in
end
function Logger:enter(to, enable)
    if enable then 
    self._prevIn = ArrayAdd(self._prevIn, self._in)
    self._in = to
    end 
end
function Logger:exit(enable)
    if enable then 
    self._in = ArrayLast(self._prevIn)
    self._prevIn = ArrayPop(self._prevIn)
    end 
end
function Logger:log(msg, enable)
    if enable then 
    if self:level() >= 2 then
        local _in = Logger:where()
        self._log('['.._in..'] '..msg)
    end
    end 
end
function Logger:warn(msg, enable)
    if enable then 
    if self:level() >= 1 then
        local _in = Logger:where()
        self._warn('['.._in..'] '..msg)
    end
    end 
end
function Logger:error(msg, enable)
  if enable then 
    local _in = Logger:where()
    self._error('['.._in..'] '..msg)
  end 
end
---=============================================================================================================================
Logger:log('start bot engine <3', verbose)
---=============================================================================================================================
Logger:log('define function to parse order type', verbose)
local ParseOrderType = function(type)
    local ret
    local arr = {
    LimitOrderType,
    MarketOrderType,
    MakerOrCancelOrderType,
    NoTimeOutOrderType,
    StopLimitOrderType,
    StopMarketOrderType,
    TakeProfitLimitOrderType,
    TakeProfitMarketOrderType
    }
    for i=1, #arr do
        if type == i then
            ret = arr[i]
            break
        elseif type == arr[i] then
            ret = i
            break
        end
    end
    return ret 
end 
Logger:log('start positionid loop', verbose)
for i=1, Count(ps) do 
    Logger:enter('positionid loop = '..i, verbose)
    local pid,p = ps[i].pid, ps[i].params
    pid = IfNull(pid, i)
    Logger:log('Id = '..pid, verbose)

    Logger:log('position information', verbose)
    local pos = {guid = Load(pid..'guid', NewGuid())}
    pos.filled_l = Load(pos.guid..'filled_l', 1)
    pos.filled_s = Load(pos.guid..'filled_s', 1)
    pos.dir = PositionToBool(GetPositionDirection(pos.guid))
    pos.aep = GetPositionEnterPrice(pos.guid, false)
    pos.amt = GetPositionAmount(pos.guid)
    if pos.amt == 0 and IsPositionClosed(pos.guid) then
        if IsAnyOrderOpen(pos.guid) then
            CancelAllOrders(pos.guid)
        end 
        if IsAnyOrderFinished(pos.guid) and IsPositionClosed(pos.guid) and not IsAnyOrderOpen(pos.guid) then 
            if Count(GetAllOpenPositions()) >= Count(ps) then break 
            else 
                pos.guid = NewGuid()
                pos.filled_l = 1
                pos.filled_s = 1
                pos.dir = PositionToBool(GetPositionDirection(pos.guid))
                pos.aep = GetPositionEnterPrice(pos.guid, false)
                pos.amt = GetPositionAmount(pos.guid)
            end 
        end 
    end 
    
    Logger:log(' setup trading commands', verbose)
    local cmd_exitPosition = PlaceExitPositionOrder
    Logger:log(' price information', verbose)
    local cp = CurrentPrice()

    Logger:log(' supported modules array', verbose)
    local supported_modules = {
        's_orders',
        's_tp',
        's_sl',
        's_buy',
        's_sell',
    }
    local active_modules = {}
    for i = 1, #supported_modules do
        active_modules[ supported_modules[i] ] = false
    end

    local updateOrderBundle = function(isLong, id, settings)
        Logger:enter(' update order bundle (buy/sell entries)', verbose)
        local weights, pricelist, start
        local active = settings.active
        Logger:log(' get price and amount spread', verbose)
        if settings.order_refill == true then start = 1 else start = isLong and pos.filled_l or pos.filled_s end 
        if active then 
            if settings.order_bestprice then 
            pricelist = isLong and Min(ArrayFilter({GetPositionEnterPrice(pos.guid, false), cp.low, cp.bid, LastLongPrice()}, 0, ArrayFilterGreaterThanType)) or Max(ArrayFilter({GetPositionEnterPrice(pos.guid, false), cp.high, cp.ask, LastShortPrice()}, 0, ArrayFilterGreaterThanType))
            else pricelist = isLong and cp.bid or cp.ask end 
            weights = CC_WeightedSpread(isLong, settings.order_size, settings.order_count, pricelist, settings.order_distribution, settings.order_spread, settings.order_atr, settings.order_atrint, settings.order_atrper) 
        end 
        for i = Parse(start, NumberType), settings.order_count do
            local name = id .. i
            local oid = Load(pos.guid .. name .. 'oid', '')
            local place_price = Load(pos.guid .. name .. 'pp', 0)
            local filled = Load(pos.guid .. name .. 'f', false)
            if settings.order_refill == false and filled == true then return end 
            if oid != '' then
                    local order = OrderContainer(oid)
                    local delta = -1
                    local max_dist = active and settings.order_cancel_dist or 0
                    Logger:log(' only calculate delta if cancel distance is used', verbose)
                    if max_dist > 0 then
                        delta = isLong
                            and Delta(cp.bid, place_price)
                            or Delta(place_price, cp.ask)
                    end
                    if order.isOpen then
                        if not active then
                            CancelOrder(oid)
                            Logger:log('Deactivated '..name, verbose)
                        elseif delta >= settings.order_cancel_dist then
                            CancelOrder(oid)
                            Logger:log('Delta cancelled '..name..' (delta: '..Round(delta, 4)..' %)', verbose)
                        end
                        if IsOrderOpen(oid) then 
                          Plot(0, name, order.price, {c=Yellow(70), id=oid, w=1.5})
                        end
                    elseif order.isCancelled and active and not( delta >= settings.order_cancel_dist) then
                       oid = PlaceCancelledOrder(oid, order.price)
                    elseif order.isFilled then 
                        if isLong then 
                            pos.filled_l = pos.filled_l+1
                        else 
                            pos.filled_s = pos.filled_s+1
                        end 
                        oid = ''
                        filled = true
                    else 
                        oid = ''
                    end
            elseif active then
                    if filled == false then
                        local delta = -1
                        local max_dist = settings.order_cancel_dist or 0
                        Logger:log(' order price with spread', verbose)
                        local price = ParseTradePrice(PriceMarket(), weights.price[i])
                        if max_dist > 0 then
                            delta = isLong
                                and Delta(cp.ask, price)
                                or Delta(price, cp.bid)
                        end
                        if delta >= (settings.order_cancel_dist*(i+1)) then
                              return
                        else 
                          Logger:log(' select trading command', verbose)
                          local cmd = isLong and PlaceGoLongOrder or PlaceGoShortOrder 
                          Logger:log(' order settings', verbose)
                          local order_settings = {
                              type = ParseOrderType(settings.order_type),
                              note = pid..' '..name,
                              timeout = settings.order_timeout,
                              positionId = pos.guid
                          }
                          Logger:log(' order size', verbose)
                          local orderSize = ParseTradeAmount(PriceMarket(), price, Max(weights.amount[i], MinimumTradeAmount()))
                          Logger:log(' place order', verbose)
                          oid = cmd(price, orderSize, order_settings)
                          Logger:log(' save price for cancel threshold calcs', verbose)
                          place_price = cp.close
                          filled = false 
                        end
                    end
            end
            if filled and Or(pos.dir.isNone, pos.amt == 0, pos.aep == 0) then 
                Logger:log(' reset', verbose)
                filled = false
                place_price = 0
            end
            Save(pos.guid .. name .. 'oid', oid)
            Save(pos.guid .. name .. 'pp', place_price)
            Save(pos.guid .. name .. 'f', filled)
        end
        Logger:exit(verbose)
    end
    
    local updateExitOrder = function(id, note, price, type, active, tprice)
        Logger:log(' update exit order', verbose)
        local oid = Load(pos.guid .. id .. 'oid', '')

        if oid == '' then
            if active then
                local settings = {
                    type = ParseOrderType(type),
                    note = pid..' '..note,
                    timeout = 9999999,
                    positionId = pos.guid,
                    triggerPrice = tprice
                }
    
                local isLong = pos.dir.isLong
                local cmd = isLong and PlaceExitLongOrder or PlaceExitShortOrder 
    
                oid = cmd(price, pos.amt, settings)
            end
        else
            local order = OrderContainer(oid)
    
            if order.isOpen then
                if not active then
                    CancelOrder(oid)
                    Logger:log('Deactivated '..guid ..' '.. note, verbose)

                elseif order.executedAmount != pos.amt then
                    CancelOrder(oid)
                    Logger:log('Refreshing order size - '..note, verbose)
    
                elseif order.price != price then
                    CancelOrder(oid)
                    Logger:log('Refreshing order price - '..note, verbose)
                end
            elseif order.isFilled then 
                if pos.dir.isLong then 
                    pos.filled_l = 1
                else 
                    pos.filled_s = 1
                end
                oid = ''
            end
        end
    
        Save(pos.guid .. id .. 'oid', oid)
        Logger:exit(verbose)
    end
    
    
    Logger:log(' pre-process parameters', verbose)
    local params = {}
    local plen
    if IsNotNull(p) then 
         if #p > 0 then plen = #p 
         else return end 
    else return end 
    local key = ''
    local value
    for i = 1, plen do
        key = p[i][1]
        value = p[i][2]
    
        params[ key ] = {}
    
        Logger:log(' build section parameters', verbose)
        if value != nil then
            local vlen = #value
            for j = 1, vlen do
                params[ key ][ value[j][1] ] = value[j][2] 
            end
        end
    
        active_modules[ key ] = true
    
        Logger:log( params[key] , verbose)
    end
    
    ----------------------------  MODULES  ------------------------------
    --    Module functionality should be placed below these lines!     --
    ---------------------------------------------------------------------
    
    Logger:log(' pre-define required variables', verbose)
    local orders = {}
    local module = {}
    module.name = supported_modules[1]
    module.max_open = 'max_open'
    module.size = 'size'
    module.spread = 'spread'
    module.cancel_dist = 'cancel_dist'
    module.trigger = 'trigger'
    module.bestprice = 'bestprice'
    
    if active_modules[ module.name ] == true then
        Logger:enter('Found order settings ', verbose)
    
        local module_params = params[ module.name ]
    
        Logger:log(' grab order settings', verbose)
        orders.max_open     = module_params[ module.max_open ]
        orders.size         = module_params[ module.size ]
        orders.spread       = module_params[ module.spread ]
        orders.cancel_dist  = module_params[ module.cancel_dist ]
        orders.trigger      = module_params[ module.trigger ]
        orders.bestprice    = module_params[ module.bestprice ]
        Logger:exit(verbose)
    else
        Logger:enter(' setup 1 order and use main TradeAmount()', verbose)
        orders.max_open = 1
        orders.size = MinimumTradeAmount()
        orders.spread = 1
        orders.cancel_dist = 1
        orders.trigger = 1
        orders.bestprice = true
        Logger:exit(verbose)
    end
    ---=============================================================================================================================
    Logger:log(' setup take-profit', verbose)
    module = {}
    module.name = supported_modules[2]
    module.percent = 'percent'
    module.order_type = 'order_type'
    
    if active_modules[ module.name ] == true then
        Logger:enter('Found take-profit settings ', verbose)
    
        local module_params = params[ module.name ]
    
        Logger:log(' grab settings', verbose)
        local tp = {}
        tp.percent          = module_params[ module.percent ]
        tp.tpercent         = orders.trigger
        tp.order_type       = module_params[ module.order_type ]
        tp.active           = Load('tpactivated', false)
        tp.price            = 0
        tp.trigger          = 0
        tp.safety           = IfElseIf(pos.dir.isLong, pos.dir.isShort, Delta(pos.aep, cp), Delta(cp, pos.aep), 0)
        if Load(pos.guid..'tpsafety', false) == false then 
            if tp.safety != 0 and IsSmallerThan(tp.safety, 0) then
                if tp.safety < Mul(tp.percent, -1) then 
                    Save(pos.guid..'tpsafety', true)
                end 
            end 
        end 
        Logger:log(' if using market order, wait for trigger', verbose)
        if tp.order_type == 2 then
            if IfElseIf(pos.dir.isLong, pos.dir.isShort, Delta(pos.aep, cp.bid) > tp.percent, Delta(cp.ask, pos.aep) > tp.percent, false) then
                    tp.active = true
                    tp.price = cp.close Logger:log(' price isnt important for market orders', verbose)
            end
    
        Logger:log(' if using other than stop orders, we can place it immediately', verbose)
        elseif tp.order_type <= 4 or tp.order_type >= 7 then
            Logger:log(' place TP beforehand', verbose)
            tp.active = true

            Logger:log(' calculate trigger price', verbose)
            if pos.dir.isLong then
                tp.price = AddPerc( pos.aep, tp.percent )
                if tp.tpercent != 0 then 
                    tp.trigger = AddPerc( tp.price, tp.tpercent )
                end 
            elseif pos.dir.isShort then
                tp.price = SubPerc( pos.aep, tp.percent )
                if tp.tpercent != 0 then 
                tp.trigger = SubPerc( tp.price, tp.tpercent )
                end 
            end
        else
            Logger:error('Native Stop order types not supported for Take-Profit ')
            tp.active = false
        end
        tp.active = tp.active and pos.dir.isNone == false

        if Load(pos.guid..'tpsafety', false) then 
            if GetPositionProfit(pos.guid) > 1 then 
                Save(pos.guid..'tpsafetytrail', true)
            end 
        end 
        if Load(pos.guid..'tpsafetytrail', false) then 
            if CC_ProfitTrailer(tp.percent, tp.percent/3, 'shrink', 0, pos.guid) then 
                tp.active = false
                tp.price = 0
                tp.trigger = 0
                if pos.dir.isLong then 
                    pos.filled_l = 1
                elseif pos.dir.isShort then 
                    pos.filled_s = 1
                end
                if IsAnyOrderOpen(pos.guid) then 
                    CancelAllOrders(pos.guid)
                end 
                if IsAnyOrderFinished(pos.guid) or not IsAnyOrderOpen(pos.guid) then 
                PlaceExitPositionOrder(pos.guid, cp, MarketOrderType, 'Bot Safety Exit')
                Save(pos.guid..'tpsafety', false)
                Save(pos.guid..'tpsafetytrail', false)
                end 
            end 
        end 
        if tp.active then 
          Save('tpactivated', true)
          if pos.aep > 0 then 
          Plot(0, 'TP-Trailing Activated', AddPerc(pos.aep, tp.percent), {c=Green(50), w=2, id=pos.guid})
          end 
          if CC_ProfitTrailer(tp.percent, tp.percent/2, 'default', 2, pos.guid) then 
            Save('tptrigger', true)
          end 
        end 
        if Load('tptrigger', false) then 
          Logger:log(' if we got a price, parse it properly', verbose)
          if tp.price > 0 then
              tp.price = ParseTradePrice(PriceMarket(), tp.price)
          end
          if tp.trigger > 0 then 
              tp.trigger = ParseTradePrice(PriceMarket(), tp.trigger)
              Logger:log(' run', verbose)
              updateExitOrder('tp', 'Take-Profit', tp.price, tp.order_type, tp.active, tp.trigger)
              Save('tpactivated', false)
              Save('tptrigger', false)
          else 
              Logger:log(' run', verbose)
              updateExitOrder('tp', 'Take-Profit', tp.price, tp.order_type, tp.active)
              Save('tpactivated', false)
              Save('tptrigger', false)
          end 
        end 
        Logger:exit(verbose)
    end
    
    ---=============================================================================================================================
    Logger:log(' setup stop-loss', verbose)
    module.name = supported_modules[3]
    
    if active_modules[ module.name ] == true then
        Logger:enter('Found stop-loss settings ', verbose)
    
        local module_params = params[ module.name ]
    
        Logger:log(' grab settings', verbose)
        local sl = {}
        sl.percent          = module_params[ module.percent ]
        sl.tpercent         = orders.trigger
        sl.order_type       = module_params[ module.order_type ]
        sl.active           = false
        sl.price            = 0
        sl.trigger          = 0
        Logger:log(' regular order types', verbose)
        if sl.order_type <= 4 then
            Logger:log(' wait until percent price change and place order', verbose)
            --if StopLoss(sl.percent, pos.guid, GetPositionDirection(pos.guid)) then
            if IfElseIf(pos.dir.isLong, pos.dir.isShort, Delta(cp.bid, pos.aep) > sl.percent, Delta(pos.aep, cp.ask) > sl.percent, false) then
                sl.active = true

                if pos.dir.isLong then
                    sl.price = cp.ask
                elseif pos.dir.isShort then
                    sl.price = cp.bid
                end
            end
    
        Logger:log(' native stop types', verbose)
        elseif sl.order_type > 4 and sl.order_type < 7 then
            Logger:log(' place SL beforehand when using native stops', verbose)
            sl.active = true
    
            Logger:log(' calculate trigger price', verbose)
            if pos.dir.isLong then
                sl.price = SubPerc( pos.aep, sl.percent )
                if sl.tpercent != 0 then 
                    sl.trigger = SubPerc( sl.price, sl.tpercent )
                end 
            elseif pos.dir.isShort then
                sl.price = AddPerc( pos.aep, sl.percent )
                if sl.tpercent != 0 then 
                    sl.trigger = AddPerc( sl.price, sl.tpercent )
                end 
            end
        else
            Logger:error('Native Take-Profit order types not supported for Stop-Loss ')
        end

        sl.active = sl.active and pos.dir.isNone == false
    
        Logger:log(' if we got a price, parse it properly', verbose)
        if sl.price > 0 then
            sl.price = ParseTradePrice(PriceMarket(), sl.price)
        end
        if sl.trigger > 0 then 
            sl.trigger = ParseTradePrice(PriceMarket(), sl.trigger)
            Logger:log(' run', verbose)
            updateExitOrder('sl', 'Stop-Loss', sl.price, sl.order_type, sl.active, sl.trigger)
        else
            Logger:log(' run', verbose)
            updateExitOrder('sl', 'Stop-Loss', sl.price, sl.order_type, sl.active)
        end 
        Logger:exit(verbose)
    end
    
    ---=============================================================================================================================
    Logger:log(' setup and run buying', verbose)
    module = {}
    module.name = supported_modules[4]
    module.order_timeout = 'order_timeout'
    module.order_refill = 'order_refill'
    module.order_atr = 'order_atr'
    module.order_atrint = 'order_atrint'
    module.order_atrper = 'order_atrper'
    module.order_distribution = 'order_distribution'
    module.order_type = 'order_type'
    
    if active_modules[ module.name ] == true then
        Logger:enter('Found buy settings ', verbose)
    
        local module_params = params[ module.name ]
    
        Logger:log(' grab settings', verbose)
        local buy = {}
        buy.active = true
        buy.order_timeout       = module_params[ module.order_timeout ]
        buy.order_refill        = module_params[ module.order_refill ]
        buy.order_type          = module_params[ module.order_type ]
        buy.order_distribution  = module_params[ module.order_distribution ]
        buy.order_atr           = module_params[ module.order_atr ]
        buy.order_atrint        = module_params[ module.order_atrint ]
        buy.order_atrper        = module_params[ module.order_atrper ]
        buy.order_count         = orders.max_open
        buy.order_size          = orders.size
        buy.order_spread        = orders.spread
        buy.order_cancel_dist   = orders.cancel_dist
        buy.order_bestprice     = orders.bestprice

        Logger:log(' update orders with buy settings', verbose)
        updateOrderBundle( true, 'buy', buy )
        Logger:exit(verbose)
    else
        Logger:enter(' grab settings', verbose)
        local buy = {}
        buy.active = false
        buy.order_count         = orders.max_open
    
        Logger:log(' cancel all open orders and reset', verbose)
        updateOrderBundle( true, 'buy', buy )
        Logger:exit(verbose)
    end
    
    ---=============================================================================================================================
    Logger:log(' setup and run selling', verbose)
    module.name = supported_modules[5]
    
    if active_modules[ module.name ] == true then
        Logger:enter('Found sell settings ', verbose)
    
        local module_params = params[ module.name ]

        Logger:log(' grab settings', verbose)
        local sell = {}
        sell.active = true
        sell.order_timeout       = module_params[ module.order_timeout ]
        sell.order_refill        = module_params[ module.order_refill ]
        sell.order_type          = module_params[ module.order_type ]
        sell.order_distribution  = module_params[ module.order_distribution ]
        sell.order_atr           = module_params[ module.order_atr ]
        sell.order_atrint        = module_params[ module.order_atrint ]
        sell.order_atrper        = module_params[ module.order_atrper ]
        sell.order_count         = orders.max_open
        sell.order_size          = orders.size
        sell.order_spread        = orders.spread
        sell.order_cancel_dist   = orders.cancel_dist
        sell.order_bestprice     = orders.bestprice

        Logger:log(' update orders with sell settings', verbose)
        updateOrderBundle( false, 'sell', sell )
        Logger:exit(verbose)
    else
        Logger:enter(' grab settings', verbose)
        local sell = {}
        sell.active = false
        sell.order_count         = orders.max_open
    
        Logger:log(' cancel all open orders and reset', verbose)
        updateOrderBundle( false, 'sell', sell )
        Logger:exit(verbose)
    end
    
    if pos.amt == 0 or pos.aep == 0 then Save(pos.guid..'guid', NewGuid()) end 
    ---=============================================================================================================================
    if pos.dir.isNone == false then
        Logger:enter(' plot position information on the chart', verbose)
        local pc = PositionContainer(pos.guid, false)
        local isLong = pos.dir.isLong
        Logger:log(' position average entry price', verbose)
        if pc.amount ~= 0 or pc.enterPrice ~= 0 then 
        Plot(0, pid..' EnterPrice', pc.enterPrice, LineOptions({color = isLong and Teal or Fuchsia, w=2, id = pos.guid}))
        end 
        Logger:exit(verbose)
    end
    Save(pid..'guid', pos.guid)
    Save(pos.guid..'filled_l', pos.filled_l)
    Save(pos.guid..'filled_s', pos.filled_s)
    Logger:log('End of for loop of pids', verbose)
    Logger:exit(verbose)
end 
if backtest then 
    Logger:enter('Load Backtest Settings', verbose)
    CC_BacktestSettings()
    Logger:log('Finished Backtest Settings', verbose)
    Logger:exit(verbose)
end
    ---=============================================================================================================================
DefineOutput(VoidType)

4 Comments

Sign in to leave a comment.

T
TooT almost 5 years ago

7. 20 Jun 2021 14:57:13 ERROR: DefineOutput() is not allowed in bot scripts.
6. 20 Jun 2021 14:57:13 ERROR: DefineParameter() is not allowed in bot scripts.
5. 20 Jun 2021 14:57:13 ERROR: DefineParameter() is not allowed in bot scripts.
4. 20 Jun 2021 14:57:13 ERROR: DefineParameter() is not allowed in bot scripts.
3. 20 Jun 2021 14:57:13 ERROR: DefineCommand() is not allowed in bot scripts

What shall i do?

S
Strooth almost 5 years ago

Save it as the correct type might help.

Its a command not a bot script. Select command in the dropdown when you open a new script.

T
TooT almost 5 years ago

6. 20 Jun 2021 21:19:45 ERROR: Command script is invalid and can not be used
5. 20 Jun 2021 21:19:45 ERROR: DefineParameter(): Attempting to call with 'null' value for defaultValue.
4. 20 Jun 2021 21:19:45 ERROR: CC_BotEngine_Settings(): Invalid input count of 31 (only takes 30).
3. 20 Jun 2021 21:19:45 ERROR: CC_BotEngine_Settings(): Invalid input count of 31 (only takes 30).
2. 20 Jun 2021 21:19:45 High speed updates enabled.
1. 20 Jun 2021 21:19:45 Doing compile test..

S
Strooth almost 5 years ago

Updated the instructions and example