A Pine Script v5 or v6 strategy from TradingView runs here as it is, on every plan. The engine compiles it to its own strategy format, so it backtests, optimizes over its inputs, runs on the server and goes to the marketplace like any other strategy, and it runs on the native core when that is switched on.
The rule the compiler keeps: a script either computes exactly what TradingView computes, within the engine's own fills, or it is refused with the line and the column of the reason. It never runs something close.
Bringing a script in
Open Build, press the plus in the Strategies rail, choose Pine script and paste your script over the template it starts with. Or use the import button in the rail: it takes a .pine or .txt file, or the script pasted in, names it after its strategy() title, and compiles it before anything is saved, so what it refuses is listed by line first. The editor highlights Pine, and Validate compiles it again after you change it.
What runs
strategy()and its title. Capital, commission, slippage and margin are the run's own settings here, and the compiler says so.default_qty_valuewithdefault_qty_type(strategy.fixed,strategy.cashorstrategy.percent_of_equity) is the size of every entry without aqty.input.int,input.float,input.boolandinput(): each is a parameter, withminval,maxvalandstepas its range in the optimizer.input.sourceis fixed at its default price.- Declarations,
varwith:=and+=,if,else if,else, the ternary,and,or,not, history withx[n], and your own functions. - Prices,
bar_index,syminfo.mintick, and the bar's time:hour(time, "UTC")and its siblings are exact; barehourreads UTC here where TradingView reads the exchange's zone, and the compiler notes it. ta.sma,ema,rma,wma,rsi,atr,tr,stdev,cci,highest,lowest,change,mom,stoch,crossover,crossunder,cross,ta.macd,ta.bbandta.dmiinto three names,math.*andmath.sum,na,nz.strategy.entrylong and short,strategy.close_all,strategy.closewith one entry id orstrategy.position_entry_name, andstrategy.exitwithprofitandlossin ticks.qtyonstrategy.entry, in units of the instrument, as on TradingView.qtyorqty_percentonstrategy.close: part of the position, in units or as a percentage of it.strategy.entrywithlimit=orstop=: an order that waits at that price under its id until it fills orstrategy.cancel(id)orstrategy.cancel_all()takes it back. The same id again moves it.oca_namewithoca_type=strategy.oca.cancelcancels the rest of the group when one fills.strategy.exitwithtrail_pointsandtrail_offset: a trailing stop that starts once the position istrail_pointsticks in profit and follows the best pricetrail_offsetticks behind.switch, as a statement and as a value.input.string(withoptions),input.sessionandinput.timeframe, fixed at their defaults. Text compares with==and!=.input.colorand colours are for drawing and are left out.- A session filter:
not na(time(timeframe.period, "0800-1600", "UTC")). Without"UTC"the session is read in UTC here, where TradingView reads the exchange's zone, and the compiler notes it. request.security(syminfo.tickerid, timeframe.period, expr)on the chart's own symbol and timeframe.- Plots,
alertandalertconditionare left out of the run, with a note.
What is refused
Each by line and column: loops, libraries, methods and types, varip, request.* on another symbol or timeframe, drawings, arrays, strategy.order, limit and stop together, strategy.oca.reduce, trail_price and a trail with only one of its two settings, reads of the position (strategy.position_size and the rest), pyramiding, input.time and time as a value, an indicator inside an if body, and a declaration that reads a var set earlier on the same bar. TradingView skips bars in two more places, so they are refused too: an indicator in one side of ?: whose condition changes, and in version 6 an indicator on the right of and or or. Put it on a line of its own. The message says how to write each.
Where TradingView and this engine part
- Fills. An entry fills at the next bar's open, stops and targets inside the bar by the accuracy tier you choose, and the size is
qtyor the default size, else the run's lot size. TradingView's broker emulator makes its own assumptions inside a bar. - A percentage of equity is a percentage of the balance here, measured when the entry is placed, without the open position's profit.
- An entry at a price the way you already hold. TradingView ignores it; here it waits and can fill once the position is closed. Cancel it in the script where that matters.
- A position opened at a price has its stop and target checked from the next bar here. TradingView can stop it out in the bar it filled.
- Two orders on one bar. Two separate
ifblocks that both enter on the same bar are weighed as the engine weighs a bar's intents: from flat the first entry wins. TradingView places both, so the second reverses the first. Write the second aselse ifto be exact on both.
Taking it back out
Export to TradingView in the editor's toolbar prints the strategy back as Pine v6 in the subset that runs here, with its inputs at the values you tested. The same panel prints a MetaTrader 5 expert advisor and a cTrader cBot: both carry this engine's own indicators, checked against it value for value, and replay the history they have before their first order so the indicators start warm. Each file says in its header what differs on that platform. None of them installs itself: paste or compile it on the platform. A Python strategy that reads the order book exports to MetaTrader 5 and to cTrader, and is refused for TradingView, which has no order book to read.
A Python strategy exports to TradingView the same way when it keeps to what the engine can compile: parameters, state in self, ctx.sma and the other indicators, lists over ctx.bars(n) after if len(bars) < n: return, and ctx.signal. It is compiled, run beside the original on the same bars, and printed only when both traded alike; otherwise the panel names the line, or the trade where they parted.