Giter VIP home page Giter VIP logo

btoandav20's People

Contributors

angonyfox avatar dave-vallance avatar erikjanhofstede avatar ftomassetti avatar happydasch avatar josipbudzaki avatar nk avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

btoandav20's Issues

Starting Algorithm With Pending Order

Hi,

again this could be related to Backtrader... :-)

Before I start the script oandav20test.py, I create a Buy Stop order via the OANDA Web Trading Platform that will not be executed, because it's weekend.

Afterwards I start oandav20test.py.

How is it possible to recognize this existing (pending) order within the code?

Insufficient authorization to perform request

import pytz
import btoandav20
import v20

with open('token', 'r') as tokenFile:
    token = tokenFile.read().replace('\n', '')
oandastore = btoandav20.stores.OandaV20Store(token=token, account='001-004-3121847-001', practice=True)
print(oandastore.getbroker())

It is not possible to authenticate via OandaV20Store object. The output is:
GET https://api-fxpractice.oanda.com:443/v3/accounts/001-004-3121847-001/summary expected status 200, got 401 (Unauthorized) Insufficient authorization to perform request.

The debug log of this snippet is here.

The authentication to Oanda API is possible (according to this page) thus the token is correct.

btoandav20 is installed together with pyyaml 5.1.2, v20 3.0.25.0, backtrader 1.9.74.123

Where should I look for the problem?

Filling positions with external orders

Currently it is not possible, to close a trade from outside backtrader. The reason is, there is no order in backtrader, that requested this action. It is now possible to identify external orders and to simulate them in backtrader, so the trades get closed correctly. Needs to be implemented.

V20 Timeout

Received this error running tests against the Oanda practise env. The error was encountered after several hours of running successfully.

File "/Applications/anaconda/lib/python3.6/site-packages/btoandav20/feeds/oandav20feed.py", line 286, in _load
if 'code' in msg:
TypeError: argument of type 'V20Timeout' is not iterable

cannot connect

Facing issue with connecting after upgrading to the new btoandav20.

Copy the messages here, I do get the 1st 500 backfill data, but there after is an issue:
on clicking the link provided by store, the message is:
{"errorMessage":"Insufficient authorization to perform request."}
As u can see below, candle 501 is still coming in.

...
Day, 500,2020-06-19 11:20:00,1.11932,1.11934,1.11912,1.11922,29
***** DATA NOTIFY: LIVE
***** STORE NOTIFY: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/XXX-XXX-XXXXXXXX-XXX/transactions/stream has timed out (stream)
***** STORE NOTIFY: Trying to reconnect streaming events (1 of -1)
***** STORE NOTIFY: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/XXX-XXX-XXXXXXXX-XXX/transactions/stream has timed out (read)
***** STORE NOTIFY: Trying to reconnect streaming events (2 of -1)
***** STORE NOTIFY: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/1XXX-XXX-XXXXXXXX-XXX/transactions/stream has timed out (read)
***** STORE NOTIFY: Trying to reconnect streaming events (3 of -1)
***** STORE NOTIFY: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/XXX-XXX-XXXXXXXX-XXX/transactions/stream has timed out (read)
***** DATA NOTIFY: CONNBROKEN
***** STORE NOTIFY: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/XXX-XXX-XXXXXXXX-XXX/pricing/stream?instruments=EUR_USD has timed out (stream)
***** DATA NOTIFY: LIVE
***** STORE NOTIFY: Trying to reconnect streaming events (4 of -1)
***** STORE NOTIFY: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/XXX-XXX-XXXXXXXX-XXX/transactions/stream has timed out (stream)
***** STORE NOTIFY: Trying to reconnect streaming events (1 of -1)
***** STORE NOTIFY: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/XXX-XXX-XXXXXXXX-XXX/transactions/stream has timed out (stream)
***** STORE NOTIFY: Trying to reconnect streaming events (1 of -1)
***** STORE NOTIFY: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/XXX-XXX-XXXXXXXX-XXX/transactions/stream has timed out (read)
Day, 501,2020-06-19 11:21:00,1.11925,1.11972,1.11917,1.11964,0
***** STORE NOTIFY: Trying to reconnect streaming events (2 of -1)
***** STORE NOTIFY: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/XXX-XXX-XXXXXXXX-XXX/transactions/stream has timed out (stream)
***** STORE NOTIFY: Trying to reconnect streaming events (1 of -1)
***** STORE NOTIFY: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/XXX-XXX-XXXXXXXX-XXX/transactions/stream has timed out (read)
***** STORE NOTIFY: Trying to reconnect streaming events (2 of -1)
...

I regenerated my Api key but its the same messages. Also to note, I am not trying this when market is closed.

Cannot seem to adjust trailing stop

Hi if I have code like this:

self.long_order = self.buy_bracket(exectype=bt.Order.Stop, stopexec=bt.Order.StopTrail, size=qty, valid=self.valid,
            limitprice=TP2_price,
            
            price=entry_price,
            
            stopprice=stoploss_price,
            # trailpercent=0.05,
        )

I see that its taking effect because I am getting trailing stop order notifications, and they are getting hit somehow as long as I specify stopexec=bt.Order.StopTrail.

Buy Stops            - 68
Sell Stops           - 120
Trailing Stop Losses - 179
Take Profits         - 9

However when I try to change the trailing stop, for example have it trail by 5%:

self.long_order = self.buy_bracket(exectype=bt.Order.Stop, stopexec=bt.Order.StopTrail, size=qty, valid=self.valid,
            limitprice=TP2_price,
            
            price=entry_price,
            
            stopprice=stoploss_price,
            trailpercent=0.05,
        )

I get the same result, the value is not being adjusted.

Buy Stops            - 68
Sell Stops           - 120
Trailing Stop Losses - 179
Take Profits         - 9

EDIT: The backtrader documentation kinda makes it look like it should go on the root level but it should be nested in stopargs. My mistake.

Minimize threads for price streams

Currently for every instrument a new thread with a open connection will be created. If possible, all price stream events should be running in one thread with a single open connection.
When new data feeds are added, the connection should be closed and a new connection with all instruments should be opened, instead of creating a new thread.

Get History with long period - Error 400 from API with Exceed max count

Hi there,

Great job with the Oanda wrapper.
I wanted to backtest a strategy and was selecting a long period for the backtesting and the script just hanged with nothing happening.

After a bit of research and debug, i found out that the call to get the history of the candles was asking for too many candles at once hence a 400 response with the following message:
{ "errorMessage": "Maximum value for 'count' exceeded" }

I worked through the code and realised that removing the "toTime" from the query was solving this issue though i'm not sure of the impact on other scenario.

So I modified the file 'oandav20store.py' => function '_t_candles' to remove "toTime" from "dtkwargs" in the while loop with the following (though just not adding it to the dtkwargs might be a better solution but I was afraid of any unseen impact):

    def _t_candles(self, dataname, dtbegin, dtend, timeframe, compression,
                   candleFormat, includeFirst, onlyComplete, q):
        '''Callback method for candles request'''
        granularity = self.get_granularity(timeframe, compression)
        if granularity is None:
            q.put(None)
            return

        dtkwargs = {}
        if dtbegin is not None:
            dtkwargs['fromTime'] = dtbegin.strftime("%Y-%m-%dT%H:%M:%S.000000000Z")
            dtkwargs['includeFirst'] = includeFirst

        if dtend is not None:
            dtkwargs['toTime'] = dtend.strftime("%Y-%m-%dT%H:%M:%S.000000000Z")

        count = 0
        while True:
            count += 1
            if count > 1: dtkwargs['includeFirst'] = False
            try:
                if 'toTime' in dtkwargs:
                    del dtkwargs['toTime']
                response = self.oapi.instrument.candles(dataname,
                                                 granularity=granularity,
                                                 price=candleFormat,
                                                 **dtkwargs)
                candles = response.get('candles', 200)
            except Exception as e:
                self.put_notification(e)
                return

            dtobj = None
            for candle in candles:
                if not onlyComplete or candle.complete:
                    q.put(candle.dict())
                    dtobj = datetime.utcfromtimestamp(float(candle.time))

            if dtobj is not None:
                dtkwargs['fromTime'] = dtobj.strftime("%Y-%m-%dT%H:%M:%S.000000000Z")
            elif dtobj is None:
                break
            if len(candles) == 0:
                break

        q.put({})  # end of transmission'''

To reproduce this issue, you just need to use a store with the following values:

    DataFactory = store.getdata
    # from_date
    dtformat = '%Y-%m-%dT%H:%M:%S'
    fromdate = datetime.datetime.strptime("2017-10-01T00:00:00", dtformat)
    todate = datetime.datetime.strptime("2018-06-04T01:00:00", dtformat)

    datakwargs = dict(
        timeframe=bt.TimeFrame.Minutes,
        compression=15,
        qcheck=0.5,
        historical=True,
        fromdate=fromdate,
        todate=todate,
        bidask=True,

    )
    data0 = DataFactory(dataname="EUR_USD", **datakwargs)

Let me know what you think of the fix and I can do a PR if you wish. Just let me know how to proceed and what to test first. If I did anything wrong in the config to use the wrapper and there is no need for a fix , please let me know ! ;)

Short Interruption of Internet Connection Stops Price Retrieval

Hi,

whenever after 24 hours my internet provider makes a forced separation of my line, afterwards no price data is retrieved anymore.

I thought that the last statement in #10 meant, that with

stream_timeout=None,
poll_timeout=none,

a short interruption of my internet connection will not harm the processing anymore.

Did I understand it wrong?

Thanks in advance!

Resample Candles Have Gaps?

Hi,

I use the original script oandav20text.py from this project with these parameters:

--token <TOKEN> --account <ACCOUNT> --data0 EUR_USD --timeframe Seconds --compression 5 --trade --broker --resample --fromdate 2018-05-18T20:00:00

I observe sometimes gaps in the old data.
Example:
Between:

2018-05-18T20:01:15.000000

and

2018-05-18T20:01:25.000000

the second 20 is missing.

I suppose this is related to OANDA itself. Does somebody know whether this was always the case with OANDA?

Or do I have to supply a different parameter so that these gaps do not appear?

Thanks in advance!

Data0, 0002, 736832.833449, 2018-05-18T20:00:10.000000, 1.176740, 1.176740, 1.176740, 1.176740,      1, 0, nan
Data0, 0003, 736832.833565, 2018-05-18T20:00:20.000000, 1.176760, 1.176760, 1.176750, 1.176750,      3, 0, nan
Data0, 0004, 736832.833681, 2018-05-18T20:00:30.000000, 1.176770, 1.176800, 1.176750, 1.176800,      5, 0, nan
Data0, 0005, 736832.833738, 2018-05-18T20:00:35.000000, 1.176800, 1.176800, 1.176800, 1.176800,      2, 0, 1.176776
Data0, 0006, 736832.833796, 2018-05-18T20:00:40.000000, 1.176800, 1.176800, 1.176800, 1.176800,      2, 0, 1.176778
Data0, 0007, 736832.833854, 2018-05-18T20:00:45.000000, 1.176800, 1.176800, 1.176790, 1.176790,      2, 0, 1.176788
Data0, 0008, 736832.833912, 2018-05-18T20:00:50.000000, 1.176810, 1.176810, 1.176800, 1.176800,      2, 0, 1.176798
Data0, 0009, 736832.833970, 2018-05-18T20:00:55.000000, 1.176770, 1.176770, 1.176730, 1.176730,      2, 0, 1.176784
Data0, 0010, 736832.834028, 2018-05-18T20:01:00.000000, 1.176720, 1.176760, 1.176720, 1.176760,      5, 0, 1.176776
Data0, 0011, 736832.834086, 2018-05-18T20:01:05.000000, 1.176760, 1.176760, 1.176760, 1.176760,      6, 0, 1.176768
Data0, 0012, 736832.834144, 2018-05-18T20:01:10.000000, 1.176760, 1.176770, 1.176760, 1.176770,      4, 0, 1.176764
Data0, 0013, 736832.834201, 2018-05-18T20:01:15.000000, 1.176760, 1.176770, 1.176760, 1.176770,      2, 0, 1.176758
Data0, 0014, 736832.834317, 2018-05-18T20:01:25.000000, 1.176800, 1.176860, 1.176800, 1.176860,      3, 0, 1.176784
Data0, 0015, 736832.834606, 2018-05-18T20:01:50.000000, 1.176900, 1.176900, 1.176880, 1.176880,      9, 0, 1.176808
Data0, 0016, 736832.834664, 2018-05-18T20:01:55.000000, 1.176870, 1.176870, 1.176820, 1.176820,      4, 0, 1.176820
Data0, 0017, 736832.834722, 2018-05-18T20:02:00.000000, 1.176830, 1.176880, 1.176820, 1.176880,      5, 0, 1.176842

Get Cancel Notification if Market is Closed?

Hi,

I create a market order outside of trading hours.
I can see that the order is created in backtrader-oandav20, and gets received by OANDA.
I can see in the OANDA web trading platform, that the order gets immediately cancelled by OANDA:

Ticket	Type	Market	Units	Price	Half Spread Cost	Profit (EUR)	Commission	Balance	Date / Time
384	Order Cancelled		-	-	-	-	-	-	3/31/2018, 5:13:16 AM
383	Market Order	EUR/USD	10	-	-	-	-	-	3/31/2018, 5:13:16 AM

But I do not receive a notification in backtrader-oandav20. I would expect that somehow I get notified about that in notify_order(), but this is not the case.

Is this related to backtrader-oandav20 or is this the way how backtrader works in general (as we do not get new data outside of trading hours)?

Market Order With Price Supplied

Hi,

perhaps this is a standard Backtrader behaviour, but anyhow:

In the example, I can see the order statement:

                self.order = self.buy(size=self.p.stake,
                                      exectype=self.p.exectype,
                                      price=price,
                                      valid=self.p.valid)

It gets executed with a market order in the plain vanilla case:

                print("set up buy order, exectype:", self.p.exectype)
                from backtrader import order; print("OrderBase.ExecTypes:", order.OrderBase.ExecTypes)


set up buy order, exectype: 0
OrderBase.ExecTypes: ['Market', 'Close', 'Limit', 'Stop', 'StopLimit', 'StopTrail', 'StopTrailLimit', 'Historical']

For me it seems a little bit contradicting that I as a user am allowed to create an order with market conditions and that I can also supply a price.

I would expect that I can either supply a price or give a market order - but not both.

Slow Internet Connection

Hi,

with a (very) slow internet connection, I can realize an exception here:

                self._reconns -= 1
                self._st_start(instart=False, tmout=self.p.reconntimeout)
                continue
            print("msg:",msg)
            if 'code' in msg:                      # <<<=============== exception
                self.put_notification(self.CONNBROKEN)
                code = msg['code']
                if code not in [599, 598, 596]:
                    self.put_notification(self.DISCONNECTED)
                    self._state = self._ST_OVER
                    return False  # failed

which leads to:

    ***** STORE NOTIF: v20 REST request to https://api-fxpractice.oanda.com:443/v3/accounts/***-***-*******-***/summary has timed out (read)
    msg: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/***-***-*******-***/pricing/stream?instruments=EUR_USD has timed out (stream)
    Traceback (most recent call last):
      File "/home/user/4me/Technologie/0010-install/pycharm/2017-12-12-ultimate-edition/pycharm-2017.3/helpers/pydev/pydevd.py", line 1668, in <module>
        main()
      File "/home/user/4me/Technologie/0010-install/pycharm/2017-12-12-ultimate-edition/pycharm-2017.3/helpers/pydev/pydevd.py", line 1662, in main
        globals = debugger.run(setup['file'], None, None, is_module)
      File "/home/user/4me/Technologie/0010-install/pycharm/2017-12-12-ultimate-edition/pycharm-2017.3/helpers/pydev/pydevd.py", line 1072, in run
        pydev_imports.execfile(file, globals, locals)  # execute the script
      File "/home/user/4me/Technologie/0010-install/pycharm/2017-12-12-ultimate-edition/pycharm-2017.3/helpers/pydev/_pydev_imps/_pydev_execfile.py", line 18, in execfile
        exec(compile(contents+"\n", file, 'exec'), glob, loc)
      File "/home/user/PycharmProjects/0363-backtrader-oandav20-in-between/examples/oandav20test/oandav20test.py", line 547, in <module>
        runstrategy()
      File "/home/user/PycharmProjects/0363-backtrader-oandav20-in-between/examples/oandav20test/oandav20test.py", line 339, in runstrategy
        cerebro.run(exactbars=args.exactbars)
      File "/home/user/anaconda3/lib/python3.6/site-packages/backtrader/cerebro.py", line 1127, in run
        runstrat = self.runstrategies(iterstrat)
      File "/home/user/anaconda3/lib/python3.6/site-packages/backtrader/cerebro.py", line 1295, in runstrategies
        self._runnext(runstrats)
      File "/home/user/anaconda3/lib/python3.6/site-packages/backtrader/cerebro.py", line 1538, in _runnext
        drets.append(d.next(ticks=False))
      File "/home/user/anaconda3/lib/python3.6/site-packages/backtrader/feed.py", line 404, in next
        ret = self.load()
      File "/home/user/anaconda3/lib/python3.6/site-packages/backtrader/feed.py", line 476, in load
        _loadret = self._load()
      File "/home/user/PycharmProjects/0363-backtrader-oandav20-in-between/btoandav20/feeds/oandav20feed.py", line 286, in _load
        if 'code' in msg:
    TypeError: argument of type 'V20Timeout' is not iterable

    Process finished with exit code 1

Question: Importing from subdirectory

Hello - This is a probably a dumb import question but... I would like to import the module from a subdirectory and get the following error:

AttributeError: module 'extensions.stores.btoandav20.feeds' has no attribute 'OandaV20Data'

My folder structure is like this:

extensions/
stores/
btoandav20/
_init.py
brokers/
feeds/
sizers/
stores/

I am trying to import with the following line:

from extensions.stores import btoandav20

The issue is raised specifically from the following lines in the example script

StoreCls = btoandav20.stores.OandaV20Store DataCls = btoandav20.feeds.OandaV20Data

Now if I place my test script directly in the stores folder an simply import btoandav20 everything works fine.

Any ideas?

Apologies, this is more of a general python question but I am a bit stumped :)

Extra info... if I open up python and do dir() on btoandav20 after importing it, I can see that 'OandaV20Data' is not present. Conversely, it is if imported directly from my stores folder.

Could it be something to do with the importing of the store within the broker and data feed scripts? i.e the line:

from btoandav20.stores import oandav20store

My import knowledge is not the greatest so I am sure it is something wrong with the way I am setting up rather than the code.

No stream data return

Hi๏ผŒ
I use a following command to get a living data stream but no data returns. (Accound Id and token is omitted)
python btTest.py --data0 EUR_USD --resample --timeframe Seconds --compression 1.

The output is:
-- Contract Details:
{'name': 'EUR_USD', 'type': 'CURRENCY', 'displayName': 'EUR/USD', 'pipLocation': -4, 'displayPrecision': 5, 'tradeUnitsPrecision': 0, 'minimumTradeSize': '1.0', 'maximumTrailingStopDistance': '1.0', 'minimumTrailingStopDistance': '0.0005', 'maximumPositionSize': '0.0', 'maximumOrderUnits': '100000000.0', 'marginRate': '0.01'}
Datetime, Open, High, Low, Close, Volume, OpenInterest, SMA
Could you please tell me where is the possible error?
Thanks
zihoa

Backfill data after a reconnect

Feeds need to be notified about a broken connection and should fill missing data (from last received tick until first new tick) with candles. Check for backfill param.

Data feed should set it state to connection broken while there is no connection / stream available. After restoring connection it should backfill and when done it should set it state back to live.

Missing order notifications when running live

When running my algorithm on a live account with real money, the furthest order notification I seem to get is Submitted -> Accepted.

I have logic that executes after a first take profit target (limit order) is hit, so it cannot activate because I never get the Completed notification for that take profit.

Everything seems to work as expected while backtesting and I get all of the notifications including Completed, but they appear to be missing live.

Single Stop Trail Order

Hi!
As discussed, am having an error putting in a single stoptrail order without brackets.

Code is as below.

import backtrader as bt
import btoandav20
import backtrader.version as btvers

print(btvers.__version__)


class BaseStrategy(bt.Strategy):  # Strategy is a lines object
    params = dict(sizer=None, ticker='EURUSD')
    long_parent_order, long_stoploss, long_partial, long_trailstop = None, None, None, None  

    short_parent_order, short_stoploss, short_partial, short_trailstop = None, None, None, None


    def __init__(self):

        self.order_list = [self.long_parent_order, self.long_stoploss,
                           self.short_parent_order, self.short_stoploss,
                           self.long_trailstop, self.short_trailstop]
        self.action = 'nothing'
        self.one_test_trade = True
        self.move_to_position_px = False
        self.trail_stop_started = False


        self.data0 = self.datas[0]
        # self.data1 = self.datas[1]
        # self.lendata1 = 0

        self.ATR_at_exe = -1
        self.atr = bt.indicators.ATR(self.data0, period=14, plot=False)


    def notify_data(self, data, status, *args, **kwargs):
        print('*' * 5, 'DATA NOTIFY:', data._getstatusname(status), *args)
        if status == data.LIVE:
            self.data_live = True

    def notify_store(self, msg, *args, **kwargs):
        print('*' * 5, 'STORE NOTIFY:', msg)

    def notify_order(self, order):  # called when a buy or sell is requested

        if order.status in [order.Canceled]:
            print('Canceled: {}->{}'.format(order.ref, order.info['name']))
            pass

        if order.status in [order.Submitted]:  # status 1
            # Buy/Sell order submitted/accepted to/by broker - Nothing to do
            print('Order Submitted...', order.ref)
            return

        if order.status in [order.Accepted]:  # status 2
            # Buy/Sell order submitted/accepted to/by broker - Nothing to do
            print('-' * 65, 'ACCEPTED ORDER', '-' * 65)
            print('{} ACC-D, REF {}, AT {}: {:.2f} shares of {}, Created Price: {:.5f}'.format(
                order.info['name'], order.ref, bt.num2date(order.created.dt), order.created.size, self.p.ticker,
                order.created.price))
            print('-' * 146)
            return

        if order.status in [order.Margin, order.Rejected]:
            print('Order Margin/Rejected', order.ref)
            return

        if order.status in [order.Completed]:  # status 4

            print('-' * 65, 'EXECUTED ORDER', '-' * 65)
            print('{} EXE-D, REF {}: {:.2f} shares {}, Exe Px: {:.5f}, ATR: {:.5f}, Val: {:.2f}, Comm: {:.2f}, PNL: {:.5f}'.format(
                order.info['name'], order.ref, order.executed.size, self.p.ticker,
                order.executed.price, self.ATR_at_exe, order.executed.value, order.executed.comm, order.executed.pnl))
            print('-' * 146)  # bt.num2date(order.executed.dt)


            print('self.position: ', self.position)
            if not self.position:
                print('came in here')
                self.long_parent_order, self.long_stoploss, self.long_partial, self.long_trailstop = None, None, None, None
                self.short_parent_order, self.short_stoploss, self.short_partial, self.short_trailstop = None, None, None, None
                for each_order in self.order_list:
                    self.cancel(each_order) if each_order else None
                if 'TrailStop' in order.info['name']:
                    self.move_to_position_px, self.trail_stop_started = False, False


    def start(self): 
        if self.data0.contractdetails is not None:
            print('-- Contract Details:')
            print(self.data0.contractdetails)
        print('Started')
        acc_cash = self.broker.getcash()
        acc_val = self.broker.getvalue()
        print('Account Cash = {}'.format(acc_cash))
        print('Account Value = {}'.format(acc_val))

    data_live = False

    def next(self):
        logdata('1Min', self.data0)

        # if len(self.data1) > self.lendata1:
        #     self.logdata('3Min', self.data1)
        #     self.lendata1 = len(self.data1)

        if not self.data_live:
            return


        if not self.position:
            if self.one_test_trade:
                self.action = 'long'
                price = self.data0.close[0]
                sl_px = round(price - self.atr[0] * 2, 5)
                sl_pips = round(abs(sl_px - price) / 0.0001, 2)
                self.ATR_at_exe = self.atr[0]
                self.sizer = btoandav20.sizers.OandaV20Risk(risk_percents=2, stoploss=sl_pips)
                exe_size = self.sizer.getsizing(data=self.data0, isbuy=True)

            if self.action == 'long':
                print('sl_pips, ATR: ', sl_pips, self.atr[0])
                print('final exe size: ', exe_size)
                print('prices: ', sl_px, price)

                self.long_parent_order, self.long_stoploss, _ = self.buy_bracket(exectype=bt.Order.Market, size=exe_size, stopprice=sl_px, limitprice=None)
                self.long_parent_order.addinfo(name='Parent Long Bracket Main')
                self.long_stoploss.addinfo(name='Parent Long Bracket Stoploss, sl_px {:.5f}'.format(sl_px))

                self.action = 'nothing'
                self.one_test_trade = False

        elif self.position:
            if self.position.size > 0:  # todo this is long
                # Have not partial closed and price hit 1 x ATR -> partial close 1/2 the size and move stop to position price
                if not self.move_to_position_px and self.data.close[0] >= self.position.price + self.ATR_at_exe * 1:

                    half_size = int(self.position.size/2)
                    size_left = abs(self.position.size - half_size)
                    stop_px = round(self.position.price, 5)
                    self.long_partial = self.sell(exectype=bt.Order.Market, size=half_size)
                    self.long_partial.addinfo(name='Parent Long Partial Close, size left {}'.format(half_size))

                    self.cancel(self.long_stoploss) if self.long_stoploss else None
                    self.long_stoploss = self.sell(price=stop_px, exectype=bt.Order.Stop, size=size_left)
                    self.long_stoploss.addinfo(name='Parent Long Move Stop to Position Price {}, size left {}, next limit {}'.format(stop_px, size_left, self.position.price + self.ATR_at_exe * 1.15)) 
                    self.move_to_position_px = True

                # already partial closed and price hit 2 x ATR -> change to trailing stop
                elif not self.trail_stop_started and self.move_to_position_px and self.data.close[0] >= self.position.price + self.ATR_at_exe * 1.15:
                    stop_size = abs(self.long_stoploss.size)
                    trail_stop_px = self.data0.close[0]
                    self.cancel(self.long_stoploss) if self.long_stoploss else None

                    # THIS ARE THE LINES WHERE I IMPLEMENT TRAILING STOP
                    self.long_trailstop = self.sell(price=trail_stop_px, exectype=bt.Order.StopTrail, size=stop_size, trailamount=self.ATR_at_exe * 1.5) 
                    # self.long_trailstop = self.sell(price=trail_stop_px, exectype=bt.Order.StopTrail, size=stop_size, id='888', trailamount=self.ATR_at_exe * 1.5)  # I tried with an id here. 
                    self.long_trailstop.addinfo(name='Parent Long TrailStop {}, id:{}'.format(trail_stop_px, '888'))
                    self.trail_stop_started = True


def logdata(name, which_data):
    txt = list()
    txt.append(name)
    txt.append('{:4d}'.format(len(which_data)))
    dtfmt = '%Y-%m-%d %H:%M:%S'
    txt.append('{}'.format(which_data.datetime.datetime(0).strftime(dtfmt)))
    txt.append('{:.5f}'.format(which_data.open[0]))
    txt.append('{:.5f}'.format(which_data.high[0]))
    txt.append('{:.5f}'.format(which_data.low[0]))
    txt.append('{:.5f}'.format(which_data.close[0]))
    # txt.append('{:.4f}'.format(which_data.volume[0]))
    print(','.join(txt))


StoreCls = btoandav20.stores.OandaV20Store
BrokerCls = btoandav20.brokers.OandaV20Broker
DataCls = btoandav20.feeds.OandaV20Data

cerebro = bt.Cerebro()

storekwargs = dict(token='', account='101- - -', practice=True)
store = StoreCls(**storekwargs)

broker = BrokerCls(**storekwargs)
cerebro.setbroker(broker)

dataX = store.getdata(dataname='EUR_USD', timeframe=bt.TimeFrame.Minutes, compression=1, qcheck=0.5, backfill_start=True, backfill=False,
                      reconnect=True, reconntimeout=10, bidask=True, bar2edge=True, adjbartime=True, rightedge=True, takelate=True)
cerebro.resampledata(dataX, timeframe=bt.TimeFrame.Minutes, compression=1, name='1M')
# cerebro.resampledata(dataX, timeframe=bt.TimeFrame.Minutes, compression=3, name='3M')

cerebro.addstrategy(BaseStrategy)
strat = cerebro.run(maxcpus=2, exactbars=-1, runonce=False)

error:
Traceback (most recent call last): File "C:/Users/bob/Trade/Algo/oanda.py", line 195, in <module> strat = cerebro.run(maxcpus=2, exactbars=-1, runonce=False) File "C:\Users\bob\AppData\Local\Programs\Python\Python38\lib\site-packages\backtrader\cerebro.py", line 1127, in run runstrat = self.runstrategies(iterstrat) File "C:\Users\bob\AppData\Local\Programs\Python\Python38\lib\site-packages\backtrader\cerebro.py", line 1298, in runstrategies self._runnext(runstrats) File "C:\Users\bob\AppData\Local\Programs\Python\Python38\lib\site-packages\backtrader\cerebro.py", line 1630, in _runnext strat._next() File "C:\Users\bob\AppData\Local\Programs\Python\Python38\lib\site-packages\backtrader\strategy.py", line 347, in _next super(Strategy, self)._next() File "C:\Users\bob\AppData\Local\Programs\Python\Python38\lib\site-packages\backtrader\lineiterator.py", line 271, in _next self.next() File "C:/Users/bob/Dropbox/Trade/Algo/oanda.py", line 157, in next self.long_trailstop = self.sell(price=trail_stop_px, exectype=bt.Order.StopTrail, size=stop_size, trailamount=self.ATR_at_exe * 1.5) File "C:\Users\bob\AppData\Local\Programs\Python\Python38\lib\site-packages\backtrader\strategy.py", line 963, in sell return self.broker.sell( File "C:\Users\bob\AppData\Local\Programs\Python\Python38\lib\site-packages\btoandav20\brokers\oandav20broker.py", line 315, in sell return self._transmit(order) File "C:\Users\bob\AppData\Local\Programs\Python\Python38\lib\site-packages\btoandav20\brokers\oandav20broker.py", line 277, in _transmit return self.o.order_create(order) File "C:\Users\bob\AppData\Local\Programs\Python\Python38\lib\site-packages\btoandav20\stores\oandav20store.py", line 360, in order_create okwargs['type'] = self._ORDEREXECS[order.exectype] KeyError: 5

Other actions taken:

Quick change to oandav20store.py

# Order type matching with oanda 
_ORDEREXECS = {
        bt.Order.Market: 'MARKET',
        bt.Order.Limit: 'LIMIT',
        bt.Order.Stop: 'STOP',
        bt.Order.StopLimit: 'STOP',
        bt.Order.StopTrail: 'TRAILING_STOP_LOSS',  # added this line
    }

But bunch of errors. Program continues running. I think there is not enough code to link single
trail orders to oanda api.

Pls help us to have a look. Thanks!!

Which Features are Missing?

Hi,

may I ask you

  1. which features are missing presently?
  2. how long it may take to add them?
  3. where beginners could help?

Thanks!

Connection to server fail

when i try to run the oandav20test program i get the following error

python3 oandav20test.py --account '' --token --data0 "GBP_USD"

++++++++++++++++++++++++++++++++++++++++

Strategy Created

Datetime, Open, High, Low, Close, Volume, OpenInterest, SMA
***** STORE NOTIF: Connection to v20 REST server at https://api-fxpractice.oanda.com:443/v3/accounts//instruments failed
***** DATA NOTIF: NOTSUBSCRIBED
++++++++++++++++++++++++++++++++++++++++

but when i run this command

curl --cipher 'DEFAULT:!DH' -H "Authorization: Bearer " https://api-fxpractice.oanda.com/v3/accounts//instruments

i get this responce

+++++++++++++++++++++++++++++++++++++
{"instruments":[{"name":"CHF_JPY","type":"CURRENCY","displayName":"CHF/JPY","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"0","shortRate":"0","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_HKD","type":"CURRENCY","displayName":"EUR/HKD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.1","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0277","shortRate":"-0.0082","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"AUD_NZD","type":"CURRENCY","displayName":"AUD/NZD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0138","shortRate":"-0.0097","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_DKK","type":"CURRENCY","displayName":"USD/DKK","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.018","shortRate":"-0.0703","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_HKD","type":"CURRENCY","displayName":"USD/HKD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.1","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0182","shortRate":"-0.0114","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_NOK","type":"CURRENCY","displayName":"USD/NOK","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.07","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0091","shortRate":"-0.0127","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"CAD_SGD","type":"CURRENCY","displayName":"CAD/SGD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0365","shortRate":"-0.0452","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"AUD_JPY","type":"CURRENCY","displayName":"AUD/JPY","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"0","shortRate":"0","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_CAD","type":"CURRENCY","displayName":"USD/CAD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.011","shortRate":"-0.0103","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"ZAR_JPY","type":"CURRENCY","displayName":"ZAR/JPY","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.005","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.07","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"0","shortRate":"0","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"GBP_HKD","type":"CURRENCY","displayName":"GBP/HKD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.1","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0782","shortRate":"-0.0429","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_CZK","type":"CURRENCY","displayName":"USD/CZK","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.1745","shortRate":"-0.1196","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"GBP_NZD","type":"CURRENCY","displayName":"GBP/NZD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0521","shortRate":"-0.0379","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_DKK","type":"CURRENCY","displayName":"EUR/DKK","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.1","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0443","shortRate":"-0.0451","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"AUD_CAD","type":"CURRENCY","displayName":"AUD/CAD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0128","shortRate":"-0.0096","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"CHF_ZAR","type":"CURRENCY","displayName":"CHF/ZAR","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.07","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0894","shortRate":"0.0285","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"NZD_USD","type":"CURRENCY","displayName":"NZD/USD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0106","shortRate":"-0.0118","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_HUF","type":"CURRENCY","displayName":"USD/HUF","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.052","shortRate":"-0.0384","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_CZK","type":"CURRENCY","displayName":"EUR/CZK","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.1848","shortRate":"-0.0783","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_HUF","type":"CURRENCY","displayName":"EUR/HUF","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0522","shortRate":"-0.0263","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"CAD_HKD","type":"CURRENCY","displayName":"CAD/HKD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.1","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.021","shortRate":"-0.0148","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_ZAR","type":"CURRENCY","displayName":"USD/ZAR","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.07","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.08","shortRate":"0.0201","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"AUD_USD","type":"CURRENCY","displayName":"AUD/USD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0128","shortRate":"-0.0094","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"NZD_CAD","type":"CURRENCY","displayName":"NZD/CAD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0113","shortRate":"-0.0113","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_PLN","type":"CURRENCY","displayName":"EUR/PLN","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0256","shortRate":"-0.0028","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_CAD","type":"CURRENCY","displayName":"EUR/CAD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0176","shortRate":"-0.0043","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_USD","type":"CURRENCY","displayName":"EUR/USD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.017","shortRate":"-0.0046","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_JPY","type":"CURRENCY","displayName":"EUR/JPY","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"0","shortRate":"0","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"CAD_CHF","type":"CURRENCY","displayName":"CAD/CHF","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0015","shortRate":"-0.0206","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"GBP_USD","type":"CURRENCY","displayName":"GBP/USD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"50000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0447","shortRate":"-0.0388","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_MXN","type":"CURRENCY","displayName":"USD/MXN","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.10","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0824","shortRate":"0.0447","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"CHF_HKD","type":"CURRENCY","displayName":"CHF/HKD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.1","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0302","shortRate":"-0.0054","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"GBP_JPY","type":"CURRENCY","displayName":"GBP/JPY","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.050","maximumPositionSize":"0","maximumOrderUnits":"50000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"0","shortRate":"0","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_TRY","type":"CURRENCY","displayName":"USD/TRY","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"10000000","marginRate":"0.12","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.3005","shortRate":"-0.0585","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"NZD_JPY","type":"CURRENCY","displayName":"NZD/JPY","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"0","shortRate":"0","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"AUD_CHF","type":"CURRENCY","displayName":"AUD/CHF","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.003","shortRate":"-0.0194","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"AUD_HKD","type":"CURRENCY","displayName":"AUD/HKD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.1","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0229","shortRate":"-0.0134","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_CHF","type":"CURRENCY","displayName":"EUR/CHF","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0086","shortRate":"-0.0138","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"AUD_SGD","type":"CURRENCY","displayName":"AUD/SGD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0408","shortRate":"-0.0408","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_CHF","type":"CURRENCY","displayName":"USD/CHF","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0017","shortRate":"-0.0194","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_NOK","type":"CURRENCY","displayName":"EUR/NOK","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.07","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0157","shortRate":"-0.0068","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_SGD","type":"CURRENCY","displayName":"EUR/SGD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0996","shortRate":"-0.0662","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"TRY_JPY","type":"CURRENCY","displayName":"TRY/JPY","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.12","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"0","shortRate":"0","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_THB","type":"CURRENCY","displayName":"USD/THB","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"0","shortRate":"0","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"GBP_CHF","type":"CURRENCY","displayName":"GBP/CHF","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0097","shortRate":"-0.0764","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_PLN","type":"CURRENCY","displayName":"USD/PLN","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0202","shortRate":"-0.0098","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"GBP_AUD","type":"CURRENCY","displayName":"GBP/AUD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0423","shortRate":"-0.0445","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"SGD_HKD","type":"CURRENCY","displayName":"SGD/HKD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.1","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0632","shortRate":"-0.0366","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"NZD_SGD","type":"CURRENCY","displayName":"NZD/SGD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0364","shortRate":"-0.0491","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"GBP_PLN","type":"CURRENCY","displayName":"GBP/PLN","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0781","shortRate":"-0.0321","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_SGD","type":"CURRENCY","displayName":"USD/SGD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0323","shortRate":"-0.0385","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_SEK","type":"CURRENCY","displayName":"EUR/SEK","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0142","shortRate":"-0.0076","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"HKD_JPY","type":"CURRENCY","displayName":"HKD/JPY","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.1","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"0","shortRate":"0","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"CAD_JPY","type":"CURRENCY","displayName":"CAD/JPY","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"0","shortRate":"0","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"GBP_ZAR","type":"CURRENCY","displayName":"GBP/ZAR","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.07","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.3067","shortRate":"0.0905","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"NZD_HKD","type":"CURRENCY","displayName":"NZD/HKD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.1","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0217","shortRate":"-0.0158","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_AUD","type":"CURRENCY","displayName":"EUR/AUD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0163","shortRate":"-0.0059","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_CNH","type":"CURRENCY","displayName":"USD/CNH","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0233","shortRate":"-0.008","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"SGD_JPY","type":"CURRENCY","displayName":"SGD/JPY","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0385","shortRate":"-0.0323","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_JPY","type":"CURRENCY","displayName":"USD/JPY","pipLocation":-2,"displayPrecision":3,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"100.000","minimumTrailingStopDistance":"0.050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"0","shortRate":"0","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_TRY","type":"CURRENCY","displayName":"EUR/TRY","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"10000000","marginRate":"0.12","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.3215","shortRate":"-0.0198","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_ZAR","type":"CURRENCY","displayName":"EUR/ZAR","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.07","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0868","shortRate":"0.0257","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"NZD_CHF","type":"CURRENCY","displayName":"NZD/CHF","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0019","shortRate":"-0.0212","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"GBP_CAD","type":"CURRENCY","displayName":"GBP/CAD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0475","shortRate":"-0.0392","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_SAR","type":"CURRENCY","displayName":"USD/SAR","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.1363","shortRate":"-0.113","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_NZD","type":"CURRENCY","displayName":"EUR/NZD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0183","shortRate":"-0.0049","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"EUR_GBP","type":"CURRENCY","displayName":"EUR/GBP","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.065","shortRate":"-0.02","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"USD_SEK","type":"CURRENCY","displayName":"USD/SEK","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.008","shortRate":"-0.0138","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"GBP_SGD","type":"CURRENCY","displayName":"GBP/SGD","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"0","shortRate":"0","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}},{"name":"SGD_CHF","type":"CURRENCY","displayName":"SGD/CHF","pipLocation":-4,"displayPrecision":5,"tradeUnitsPrecision":0,"minimumTradeSize":"1","maximumTrailingStopDistance":"1.00000","minimumTrailingStopDistance":"0.00050","maximumPositionSize":"0","maximumOrderUnits":"100000000","marginRate":"0.05","guaranteedStopLossOrderMode":"DISABLED","tags":[{"type":"ASSET_CLASS","name":"CURRENCY"}],"financing":{"longRate":"-0.0136","shortRate":"-0.0607","financingDaysOfWeek":[{"dayOfWeek":"MONDAY","daysCharged":1},{"dayOfWeek":"TUESDAY","daysCharged":1},{"dayOfWeek":"WEDNESDAY","daysCharged":1},{"dayOfWeek":"THURSDAY","daysCharged":1},{"dayOfWeek":"FRIDAY","daysCharged":1},{"dayOfWeek":"SATURDAY","daysCharged":0},{"dayOfWeek":"SUNDAY","daysCharged":0}]}}],"lastTransactionID":"9306"}
++++++++++++++++++++++++++++++++++++

It looks like i'm pulling from the same "/v3/accounts//instruments" on th same server in both cases. The only differences i see are the 443 port number and the "--cipher 'DEFAULT:!DH'" i had to use with curl.

Does anyone know if ether of these could cause the connection failure with oandav20test.py
or did i miss something else?

Simple backtest example

Can you guys please provide some simple documentation explaining how to execute a simple backtest on a particular strategy? The code as is for oandav20test will run, but no backtest is performed (no trades are simulated). I don't understand the line if status == data.Live. This is the case even when specific historical dates are provided, when the --trade flag is set to True, etc. Also, I am unclear about the distinction between the Store and the Broker class. Are both needed? Why or why not? Also I've noticed that the code does not handle exceptions for live streaming data in an intuitive way. The code will halt when live bars are encountered, haven't figured out why as of yet. Any guidance would be helpful. Thanks for your work so far.

Get open orders?

Hi,
I would like to know if there is some way to get open orders on start-up?

My example is this:

  • My strategy opens a bracket order.
  • Mainside is executed and the stop side and limit side are accepted and working.
  • I stop the script (my strategy runs on a daily timeframe, hence, only wanting to run it at a certain time once a day)
  • Upon the next resumption of the script, I can get the position data/info of the executed mainside, but nothing about the other two orders that are open and working in the market still.

I would like to be able to re-populate my order book with the currently open orders per data every time I run the script. Is this possible, any help?

Thanks in advance.

Installation and importing issues

Hey everyone, I've been having lots of trouble setting this up. I'm running it on Windows 7 and using the Anaconda Python distribution (python version 3.6.3). I installed backtrader via the Anaconda prompt using pip install:
pip install backtrader v20

I gathered that I need this backtrader v20 version from a conversation on the backtrader community forum. Problem is, when I run this, I get an error that says "Failed building wheel for ujson" - I can provide the whole error if necessary, but I'm not sure if this is the main issue. However, pip install backtrader (without the v20) works fine and produces no errors.

Now to the main issue. If I download the btoandav20 folder from github and put it into the same folder as my script (just using the example script you provided), the import doesn't really work. I can do

import btoandav20

and that runs with no errors. As soon as I run the next few lines:

StoreCls = btoandav20.stores.OandaV20Store DataCls = btoandav20.feeds.OandaV20Data

I get an error that says

image

Now, if I try doing this instead, as recommended on the backtrader community forum

from .btoandav20 import OandaV20Store

I get an error that says

image

I'm really at a loss here and have no clue how to make this whole thing work. IT is NOT my strongpoint, I've asked some friends who are a bit more savvy for help and they can't figure it out either. And help would be appreciated.

How to get Tick Data?

Hi,

I want to use backtrader-oandav20 for the following scenario:

  1. work on a relatively long timeframe (e.g.: 4 hour candlestick)
  2. once all the criteria are met, I want to create an order only when with the beginning of the next candlestick some price related criteria are met - and I do not want to wait another four hours to get that data.

So it seems that using these parameters (especially --replay) will decouple the events in next() from the 4 hour timeframe and somehow follow a tick based scheme.

        "--data0", "EUR_USD",
        "--timeframe", "Hours",
        "--compression", "4",
        "--trade",
        "--broker",
        "--replay",

My questions would be:

  1. Is this the best way to satisfy the conditions I have?

  2. Is it ok to take the close values in next() as tick data for that very moment in time?

Thanks in advance!

Additional info: for 30 seconds candlesticks I get the following ohlc data in next() during live trading:

Data0, 0526, 736797.605425, 2018-04-13T14:31:48.755079, 1.232620, 1.232880, 1.232620, 1.232880,      0, 0
Data0, 0526, 736797.605430, 2018-04-13T14:31:49.173544, 1.232620, 1.232930, 1.232620, 1.232930,      0, 0
Data0, 0526, 736797.605432, 2018-04-13T14:31:49.286881, 1.232620, 1.232940, 1.232620, 1.232940,      0, 0
Data0, 0526, 736797.605439, 2018-04-13T14:31:49.966881, 1.232620, 1.232950, 1.232620, 1.232950,      0, 0
Data0, 0526, 736797.605444, 2018-04-13T14:31:50.383364, 1.232620, 1.232950, 1.232620, 1.232940,      0, 0
Data0, 0526, 736797.605450, 2018-04-13T14:31:50.845130, 1.232620, 1.232950, 1.232620, 1.232920,      0, 0
Data0, 0526, 736797.605462, 2018-04-13T14:31:51.932038, 1.232620, 1.232950, 1.232620, 1.232890,      0, 0
Data0, 0526, 736797.605505, 2018-04-13T14:31:55.595839, 1.232620, 1.232950, 1.232620, 1.232870,      0, 0
Data0, 0526, 736797.605518, 2018-04-13T14:31:56.712167, 1.232620, 1.232950, 1.232620, 1.232870,      0, 0
Data0, 0526, 736797.605519, 2018-04-13T14:31:56.812509, 1.232620, 1.232950, 1.232620, 1.232880,      0, 0
Data0, 0526, 736797.605552, 2018-04-13T14:31:59.716355, 1.232620, 1.232950, 1.232620, 1.232920,      0, 0
Data0, 0526, 736797.605555, 2018-04-13T14:31:59.919824, 1.232620, 1.232950, 1.232620, 1.232950,      0, 0
Data0, 0526, 736797.605556, 2018-04-13T14:32:00.000000, 1.232620, 1.232950, 1.232620, 1.232950,      0, 0
Data0, 0527, 736797.605583, 2018-04-13T14:32:02.377908, 1.232960, 1.232960, 1.232960, 1.232960,      0, 0
Data0, 0527, 736797.605585, 2018-04-13T14:32:02.513011, 1.232960, 1.232960, 1.232960, 1.232960,      0, 0
Data0, 0527, 736797.605591, 2018-04-13T14:32:03.097025, 1.232960, 1.232960, 1.232960, 1.232960,      0, 0
Data0, 0527, 736797.605658, 2018-04-13T14:32:08.892387, 1.232960, 1.232960, 1.232910, 1.232910,      0, 0
Data0, 0527, 736797.605712, 2018-04-13T14:32:13.510517, 1.232960, 1.232960, 1.232910, 1.232960,      0, 0
Data0, 0527, 736797.605723, 2018-04-13T14:32:14.505975, 1.232960, 1.232960, 1.232910, 1.232940,      0, 0
Data0, 0527, 736797.605819, 2018-04-13T14:32:22.753668, 1.232960, 1.232960, 1.232880, 1.232880,      0, 0
Data0, 0527, 736797.605821, 2018-04-13T14:32:22.910506, 1.232960, 1.232960, 1.232870, 1.232870,      0, 0
Data0, 0527, 736797.605837, 2018-04-13T14:32:24.304192, 1.232960, 1.232960, 1.232840, 1.232840,      0, 0
Data0, 0527, 736797.605863, 2018-04-13T14:32:26.542472, 1.232960, 1.232960, 1.232800, 1.232800,      0, 0
Data0, 0527, 736797.605883, 2018-04-13T14:32:28.266955, 1.232960, 1.232960, 1.232800, 1.232800,      0, 0
Data0, 0527, 736797.605888, 2018-04-13T14:32:28.699783, 1.232960, 1.232960, 1.232800, 1.232800,      0, 0
Data0, 0527, 736797.605896, 2018-04-13T14:32:29.440938, 1.232960, 1.232960, 1.232800, 1.232810,      0, 0
Data0, 0527, 736797.605901, 2018-04-13T14:32:29.868938, 1.232960, 1.232960, 1.232800, 1.232830,      0, 0
Data0, 0527, 736797.605903, 2018-04-13T14:32:30.000000, 1.232960, 1.232960, 1.232800, 1.232830,      0, 0
Data0, 0528, 736797.605921, 2018-04-13T14:32:31.569371, 1.232880, 1.232880, 1.232880, 1.232880,      0, 0
Data0, 0528, 736797.605931, 2018-04-13T14:32:32.434444, 1.232880, 1.232880, 1.232860, 1.232860,      0, 0
Data0, 0528, 736797.605936, 2018-04-13T14:32:32.865210, 1.232880, 1.232880, 1.232810, 1.232810,      0, 0
Data0, 0528, 736797.605938, 2018-04-13T14:32:33.007967, 1.232880, 1.232880, 1.232790, 1.232790,      0, 0
Data0, 0528, 736797.606012, 2018-04-13T14:32:39.448498, 1.232880, 1.232880, 1.232760, 1.232760,      0, 0
Data0, 0528, 736797.606040, 2018-04-13T14:32:41.843023, 1.232880, 1.232880, 1.232760, 1.232810,      0, 0
Data0, 0528, 736797.606042, 2018-04-13T14:32:42.000164, 1.232880, 1.232880, 1.232760, 1.232860,      0, 0
Data0, 0528, 736797.606085, 2018-04-13T14:32:45.753161, 1.232880, 1.232880, 1.232760, 1.232820,      0, 0
Data0, 0528, 736797.606090, 2018-04-13T14:32:46.191843, 1.232880, 1.232880, 1.232760, 1.232820,      0, 0
Data0, 0528, 736797.606120, 2018-04-13T14:32:48.807781, 1.232880, 1.232880, 1.232760, 1.232850,      0, 0
Data0, 0528, 736797.606134, 2018-04-13T14:32:49.955592, 1.232880, 1.232880, 1.232760, 1.232800,      0, 0
Data0, 0528, 736797.606150, 2018-04-13T14:32:51.373026, 1.232880, 1.232880, 1.232760, 1.232820,      0, 0
Data0, 0528, 736797.606153, 2018-04-13T14:32:51.654869, 1.232880, 1.232880, 1.232760, 1.232850,      0, 0
Data0, 0528, 736797.606161, 2018-04-13T14:32:52.289567, 1.232880, 1.232880, 1.232760, 1.232870,      0, 0
Data0, 0528, 736797.606178, 2018-04-13T14:32:53.800100, 1.232880, 1.232880, 1.232760, 1.232820,      0, 0
Data0, 0528, 736797.606180, 2018-04-13T14:32:53.964864, 1.232880, 1.232880, 1.232760, 1.232820,      0, 0
Data0, 0528, 736797.606183, 2018-04-13T14:32:54.196084, 1.232880, 1.232880, 1.232760, 1.232840,      0, 0
Data0, 0528, 736797.606228, 2018-04-13T14:32:58.132886, 1.232880, 1.232880, 1.232760, 1.232810,      0, 0
Data0, 0528, 736797.606250, 2018-04-13T14:33:00.000000, 1.232880, 1.232880, 1.232760, 1.232810,      0, 0
Data0, 0529, 736797.606299, 2018-04-13T14:33:04.249912, 1.232830, 1.232830, 1.232830, 1.232830,      0, 0

Clean shutdown

With the new way streams are handled it is impossible to have a clean shutdown, since the threads run forever.

Stops working after a few hours

I have a simple test setup where I use DataFactory for just one pair 'EUR_USD' resample to 1 hour (minute time frame with 60 compression), and just print time and price everytime next() is called. This works for a few hours but then just stops. Here is an example of my stdout logs where it worked for 9 hours and stopped with no errors:

...
2019-10-22 15:00:00 EUR_USD 1.11372
2019-10-22 16:00:00 EUR_USD 1.114
2019-10-22 17:00:00 EUR_USD 1.11438
2019-10-22 18:00:00 EUR_USD 1.11231
2019-10-22 19:00:00 EUR_USD 1.1131
2019-10-22 20:00:00 EUR_USD 1.11244
***** DATA NOTIF: LIVE
2019-10-22 22:00:00 EUR_USD 1.11234
2019-10-22 23:00:00 EUR_USD 1.11298
2019-10-23 01:00:00 EUR_USD 1.11254
2019-10-23 02:00:00 EUR_USD 1.11207
2019-10-23 03:00:00 EUR_USD 1.11194
2019-10-23 04:00:00 EUR_USD 1.11169
2019-10-23 05:00:00 EUR_USD 1.11201
2019-10-23 06:00:00 EUR_USD 1.11244
2019-10-23 07:00:00 EUR_USD 1.11247
kr@qa:~$ date -u
Wed Oct 23 12:24:32 UTC 2019

Is this a known issue?

OANDA v20 repetitive disconnection

Hi Federico,

Thank you for your work, really useful API.

I have updated to this latest version this week and I seem to have a repetitive disconnection with OANDA Live and Demo.
This could be due to OANDA environments but I haven't seen any issue reported on their side so, I am posting here to check if others have the same issue too.


--- DATA NOTIF: LIVE
STORE NOTIF: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/101-006-13XX881-005/transactions/stream has timed out (read)

  STORE NOTIF: Trying to reconnect streaming events (1 of -1)

--- DATA NOTIF: DELAYED
STORE NOTIF: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/101-006-13XX881-005/transactions/stream has timed out (stream)

  STORE NOTIF: Trying to reconnect streaming events (1 of -1)

--- DATA NOTIF: CONNBROKEN

  STORE NOTIF: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/101-006-13XX881-005/transactions/stream has timed out (read)

  STORE NOTIF: Trying to reconnect streaming events (2 of -1)
  STORE NOTIF: v20 REST request to https://stream-fxpractice.oanda.com:443/v3/accounts/101-006-13XX881-005/transactions/stream has timed out (stream)

Thanks
Rob

OHLC off by 1

#Not sure if I am misssing a setting but the input data is off by one candle. The data shown below API is from the backtrader-oandav20 test code for AUD/CAD on Mar 28 with H1 compression and the data shown under Web Oanda is what is displayed in the Oanda test web account. Please note that I am in the EST timezone and have DST. Assuming Oanda is also in NY, it should be in EST and timezone should not be a factor.

API
Data0, 0504, 736781.666667, 2018-03-28T16:00:00.000000, 0.988090, 0.989560, 0.987650, 0.989500
Data0, 0505, 736781.708333, 2018-M3-28T17:00:00.000000, 0.989500, 0.989840, 0.988050, 0.988460
Data0, 0506, 736781.750000, 2018-03-28T18:00:00.000000, 0.988420, 0.989680, 0.988390, 0.989460
Data0, 0507, 736781.791667, 2018-03-28T19:00:00.000000, 0.989480, 0.989580, 0.988810, 0.989350
Data0, 0508, 736781.833333, 2018-03-28T20:00:00.000000, 0.989320, 0.990210, 0.989300, 0.989960

Web Oanda

16:00 0.98950, 0.98984, 0.98805, 0.98846
17:00 0.98946, 0.98968, 0.98838, 0.98946
18:00 0.98946, 0.98958, 0.98880, 0.98934
19:00 0.98934, 0.99021, 0.98930, 0.98996
20:00 0.98996, 0.99043, 0.98972, 0.98984

How do I install it in backtrader

Hello I was wondering where and How I should install your package ?

when I try to run it with my account and token I get the following error

python3 oandav20test.py --account --token --data0 GBP_USD --resample --timeframe Minutes --compression 1 --no-backfill_start --stake 1000 --trade

Traceback (most recent call last):
File "oandav20test.py", line 30, in
import btoandav20
ImportError: No module named 'btoandav20'

Nothing happening

Hi guys,
First of all I would like to thank you for the hard work you've put into this project, it's simply amazing looking to all that it can do...

Unfortunatelly I'm not yet able to use it properly, after a few days spent to create the environment for it and formatting my ubuntu dozens of times :( yes I'm a rookie in python, ubuntu everything but not on trading... I think I'm very close to make it work but can't figure out what's wrong.

First when I launch the test I do it this way:
python oandav20test.py --account '100-000-00000000-000' --token 'e8f4f3daabffa01528964db356252481-cefd9e110c1242d3f*************' --data0 EUR_GBP --resample --timeframe Minutes --compression 1 --no-backfill_start --stake 100 --trade

I'm not sure if I do it right, I just followed your forum.
Now, it seems that's working but it's not working properly:

So I get all these results:

--------------------------------------------------
Strategy Created
--------------------------------------------------
-- Contract Details:
{'minimumTradeSize': '1.0', 'displayName': u'EUR/GBP', 'name': u'EUR_GBP', 'displayPrecision': 5, 'maximumTrailingStopDistance': '1.0', 'minimumTrailingStopDistance': '0.0005', 'marginRate': '0.0333', 'tradeUnitsPrecision': 0, 'pipLocation': -4, 'maximumOrderUnits': '100000000.0', 'maximumPositionSize': '0.0', 'type': u'CURRENCY'}
Datetime, Open, High, Low, Close, Volume, OpenInterest, SMA
***** DATA NOTIF: LIVE
Data0, 0001, 737406.893056, 2019-12-13T21:26:00.000000, 0.833520, 0.833590, 0.833520, 0.833590,      0, 0, nan
-------------------------------------------------- ORDER BEGIN 2019-12-13 23:27:00.120499
Ref: 1
OrdType: 0
OrdType: Buy
Status: 1
Status: Submitted
Size: 100
Price: 0.82859
Price Limit: None
TrailAmount: None
TrailPercent: None
ExecType: 0
ExecType: Market
CommInfo: None
End of Session: 737407.0
Info: AutoOrderedDict()
Broker: None
Alive: True
-------------------------------------------------- ORDER END
-------------------------------------------------- ORDER BEGIN 2019-12-13 23:27:00.121684
Ref: 1
OrdType: 0
OrdType: Buy
Status: 2
Status: Accepted
Size: 100
Price: 0.82859
Price Limit: None
TrailAmount: None
TrailPercent: None
ExecType: 0
ExecType: Market
CommInfo: None
End of Session: 737407.0
Info: AutoOrderedDict()
Broker: None
Alive: True
-------------------------------------------------- ORDER END
-------------------------------------------------- ORDER BEGIN 2019-12-13 23:27:00.122730
Ref: 1
OrdType: 0
OrdType: Buy
Status: 4
Status: Completed
Size: 100
Price: 0.82859
Price Limit: None
TrailAmount: None
TrailPercent: None
ExecType: 0
ExecType: Market
CommInfo: <backtrader.comminfo.CommInfoBase object at 0x7fb102d24a90>
End of Session: 737407.0
Info: AutoOrderedDict()
Broker: None
Alive: False
-------------------------------------------------- ORDER END
-------------------------------------------------- TRADE BEGIN 2019-12-13 23:27:00.123758
ref:1
data:<btoandav20.feeds.oandav20feed.OandaV20Data object at 0x7fb100e74e50>
tradeid:0
size:100
price:0.83357
value:83.357
commission:0.0
pnl:0.0
pnlcomm:0.0
justopened:True
isopen:True
isclosed:False
baropen:2
dtopen:737406.89375
barclose:0
dtclose:0.0
barlen:0
historyon:False
history:[]
status:1
-------------------------------------------------- TRADE END
Data0, 0002, 737406.893750, 2019-12-13T21:27:00.000000, 0.833570, 0.833570, 0.833570, 0.833570,      0, 0, nan
-------------------------------------------------- ORDER BEGIN 2019-12-13 23:28:00.124779
Ref: 2
OrdType: 1
OrdType: Sell
Status: 1
Status: Submitted
Size: -50
Price: 0.83357
Price Limit: None
TrailAmount: None
TrailPercent: None
ExecType: 0
ExecType: Market
CommInfo: None
End of Session: 737407.0
Info: AutoOrderedDict()
Broker: None
Alive: True
-------------------------------------------------- ORDER END
-------------------------------------------------- ORDER BEGIN 2019-12-13 23:28:00.125943
Ref: 2
OrdType: 1
OrdType: Sell
Status: 2
Status: Accepted
Size: -50
Price: 0.83357
Price Limit: None
TrailAmount: None
TrailPercent: None
ExecType: 0
ExecType: Market
CommInfo: None
End of Session: 737407.0
Info: AutoOrderedDict()
Broker: None
Alive: True
-------------------------------------------------- ORDER END
-------------------------------------------------- ORDER BEGIN 2019-12-13 23:28:00.127005
Ref: 2
OrdType: 1
OrdType: Sell
Status: 4
Status: Completed
Size: -50
Price: 0.83357
Price Limit: None
TrailAmount: None
TrailPercent: None
ExecType: 0
ExecType: Market
CommInfo: <backtrader.comminfo.CommInfoBase object at 0x7fb102d24a90>
End of Session: 737407.0
Info: AutoOrderedDict()
Broker: None
Alive: False
-------------------------------------------------- ORDER END
Data0, 0003, 737406.894444, 2019-12-13T21:28:00.000000, 0.833540, 0.833750, 0.833540, 0.833750,      0, 0, nan
-------------------------------------------------- ORDER BEGIN 2019-12-13 23:29:00.321794
Ref: 3
OrdType: 1
OrdType: Sell
Status: 1
Status: Submitted
Size: -50
Price: 0.83375
Price Limit: None
TrailAmount: None
TrailPercent: None
ExecType: 0
ExecType: Market
CommInfo: None
End of Session: 737407.0
Info: AutoOrderedDict()
Broker: None
Alive: True
-------------------------------------------------- ORDER END
-------------------------------------------------- ORDER BEGIN 2019-12-13 23:29:00.326125
Ref: 3
OrdType: 1
OrdType: Sell
Status: 2
Status: Accepted
Size: -50
Price: 0.83375
Price Limit: None
TrailAmount: None
TrailPercent: None
ExecType: 0
ExecType: Market
CommInfo: None
End of Session: 737407.0
Info: AutoOrderedDict()
Broker: None
Alive: True
-------------------------------------------------- ORDER END
-------------------------------------------------- ORDER BEGIN 2019-12-13 23:29:00.327720
Ref: 3
OrdType: 1
OrdType: Sell
Status: 4
Status: Completed
Size: -50
Price: 0.83375
Price Limit: None
TrailAmount: None
TrailPercent: None
ExecType: 0
ExecType: Market
CommInfo: <backtrader.comminfo.CommInfoBase object at 0x7fb102d24a90>
End of Session: 737407.0
Info: AutoOrderedDict()
Broker: None
Alive: False
-------------------------------------------------- ORDER END
-------------------------------------------------- TRADE BEGIN 2019-12-13 23:29:00.328797
ref:1
data:<btoandav20.feeds.oandav20feed.OandaV20Data object at 0x7fb100e74e50>
tradeid:0
size:0
price:0.83357
value:0.0
commission:0.0
pnl:0.007
pnlcomm:0.007
justopened:False
isopen:False
isclosed:True
baropen:2
dtopen:737406.89375
barclose:4
dtclose:737406.895139
barlen:2
historyon:False
history:[]
status:2
-------------------------------------------------- TRADE END
Data0, 0004, 737406.895139, 2019-12-13T21:29:00.000000, 0.833740, 0.833740, 0.833730, 0.833730,      0, 0, nan
Data0, 0005, 737406.895833, 2019-12-13T21:30:00.000000, 0.833650, 0.833650, 0.833550, 0.833550,      0, 0, 0.833638
Data0, 0006, 737406.896528, 2019-12-13T21:31:00.000000, 0.833600, 0.833630, 0.833540, 0.833550,      0, 0, 0.833630
Data0, 0007, 737406.897222, 2019-12-13T21:32:00.000000, 0.833590, 0.833620, 0.833560, 0.833620,      0, 0, 0.833640
Data0, 0008, 737406.897917, 2019-12-13T21:33:00.000000, 0.833590, 0.833590, 0.833590, 0.833590,      0, 0, 0.833608
Data0, 0009, 737406.898611, 2019-12-13T21:34:00.000000, 0.833620, 0.833620, 0.833440, 0.833440,      0, 0, 0.833550
Data0, 0010, 737406.900000, 2019-12-13T21:36:00.000000, 0.833430, 0.833430, 0.833370, 0.833390,      0, 0, 0.833518
Data0, 0011, 737406.900694, 2019-12-13T21:37:00.000000, 0.833500, 0.833540, 0.833500, 0.833540,      0, 0, 0.833516
Data0, 0012, 737406.901389, 2019-12-13T21:38:00.000000, 0.833520, 0.833520, 0.833520, 0.833520,      0, 0, 0.833496

But nothing shows either in MT4, either in the dashboard of Oanda... I'm using a demo account, it has some demo funds in it I think it should be ok?
I was looking into the files and I'm not sure if here practice should be True or False... for the demo account...

params = (
        ('token', 'e8f4xxxxx'),
        ('account', '10xxxxxxxxxxxx'),
        **('practice', False),**
        ('account_poll_freq', 10.0),  # account balance refresh timeout
        ('stream_timeout', 10),
        ('poll_timeout', 2),

I'm not sure so if somebody can tell me please what I'm doing wrong to finally get this up and running will be great!

Thank you again for all your work, very good looking system and finally something decent which anyone can use, almost.

Type Errors in bbroker.py

Hi - This is probably for the main backtrader issue tracker but I got this error while running tests with this Oandav20 package. Has anyone encountered this error?

If I should post it in the backtrader respository, please let me know. Thanks.

File "/Applications/anaconda/lib/python3.6/site-packages/backtrader/cerebro.py", line 1127, in run
runstrat = self.runstrategies(iterstrat)
File "/Applications/anaconda/lib/python3.6/site-packages/backtrader/cerebro.py", line 1295, in runstrategies
self._runnext(runstrats)
File "/Applications/anaconda/lib/python3.6/site-packages/backtrader/cerebro.py", line 1619, in _runnext
self._brokernotify()
File "/Applications/anaconda/lib/python3.6/site-packages/backtrader/cerebro.py", line 1357, in _brokernotify
self._broker.next()
File "/Applications/anaconda/lib/python3.6/site-packages/backtrader/brokers/bbroker.py", line 1178, in next
self.check_submitted()
File "/Applications/anaconda/lib/python3.6/site-packages/backtrader/brokers/bbroker.py", line 581, in check_submitted
cash = self._execute(order, cash=cash, position=position)
File "/Applications/anaconda/lib/python3.6/site-packages/backtrader/brokers/bbroker.py", line 775, in _execute
opencash /= comminfo.get_leverage() # dec cash with level
TypeError: unsupported operand type(s) for /=: 'decimal.Decimal' and 'float'

Replay Feature is fetching higher timeframe instead of lower timeframe

Hi,

Thanks for the help on the previous issue. Works perfectly ;)
So going through my backtesting, I wanted to use the replay function to backtest a strategy based on 15Min candles using 1Min candles for the ticks.

Though when using the oandav20feed, the data retrieved is already the replay dataframe / compression. In my example, the data fetch was 15Min instead of 1Min. That means that the tick (calling next on strategy) are not using M1 data but M15 so the same as if i don't use replay.

I did a bit of debug and was able to find out that the replay filter will override self._timeframe and self._compression from the data feed. Though in my case a simple override of the replay function in the oandav20feed seems to have fixed the issue with the following code:

    def replay(self, **kwargs):
        # save original timeframe and compression to fetch data
        # they will be overriden when calling replay
        orig_timeframe = self._timeframe
        orig_compression = self._compression
        #setting up replay configuration
        super(DataBase, self).replay(**kwargs)
        #putting back original timeframe and compression to fetch correct data
        #the replay configuration will still use the correct dataframe and compression for strategy
        self._timeframe = orig_timeframe
        self._compression = orig_compression

You can reproduce the issue by using a modified replay sample files as below (fetch day data to use on a strategy for weeks):

#!/usr/bin/env python
# -*- coding: utf-8; py-indent-offset:4 -*-
###############################################################################
#
# Copyright (C) 2015, 2016 Daniel Rodriguez
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program.  If not, see <http://www.gnu.org/licenses/>.
#
###############################################################################
from __future__ import (absolute_import, division, print_function,
                        unicode_literals)

import argparse

import backtrader as bt
import backtrader.feeds as btfeeds
import backtrader.indicators as btind
import btoandav20
import datetime

class SMAStrategy(bt.Strategy):
    params = (
        ('period', 10),
        ('onlydaily', False),
    )

    def __init__(self):
        self.sma = btind.SMA(self.data, period=self.p.period)

    def start(self):
        self.counter = 0

    def prenext(self):
        self.counter += 1
        print('prenext len %d - counter %d' % (len(self), self.counter))

    def next(self):
        self.counter += 1
        print('---next len %d - counter %d' % (len(self), self.counter))


def runstrat():

    # Create a cerebro entity
    cerebro = bt.Cerebro(stdstats=False)
    StoreCls = btoandav20.stores.OandaV20Store

    cerebro.addstrategy(SMAStrategy)

    # Load the Data
    storekwargs = dict(
        token="xxxxxxxxxxx",
        account="yyyyyyyyyyy",
        practice=True
    )

    store = StoreCls(**storekwargs)
    DataFactory = store.getdata
    dtformat = '%Y-%m-%dT%H:%M:%S'

    fromdate = datetime.datetime.strptime("2010-01-01T00:00:00", dtformat)
    todate = datetime.datetime.strptime("2010-01-31T00:00:00", dtformat)
    datakwargs = dict(
        timeframe=bt.TimeFrame.Days,
        compression=1,
        qcheck=0.5,
        historical=True,
        fromdate=fromdate,
        todate=todate,
        bidask=True,

    )
    data = DataFactory(dataname="EUR_USD", **datakwargs)
    # Prepare the data for replay at higher timeframe
    data.replay(
        timeframe=bt.TimeFrame.Weeks,
        compression=1)

    # First add the original data - smaller timeframe
    cerebro.adddata(data)

    # Run over everything
    cerebro.run(preload=False)

if __name__ == '__main__':
    runstrat()

Warning: With the fix proposed, on my system, the values don't correspond between oanda data and replaying the data. I believe it must be some timezone issues between the data coming back from Oanda and the timing of replayed data. But it could simply be another issue on replaying.

Fetch data in a random time interval

I have set the timeframe as bt.TimeFrame.Seconds, with compression as 5. However, when fetching bars from Onada, it gives data in a random time interval instead. Here goes my code

import backtrader as bt
import btoandav20
import os

class TestStra(bt.Strategy):
    def __init__(self):
        self.contracts = {}

    def next(self):
        dt = self.datas[0].datetime.datetime(0)
        print(dt)
        print('*'*20)

    def start(self):
        for d in self.datas:
            if d.contractdetails is not None:
                self.contracts[d._name] = d.contractdetails
                print('-- Contract Details:')
                print(d.contractdetails)
            else:
                print(d._name, ' Error!')

token = os.getenv('ACCESS_TOKEN')
accId = os.getenv('ACCOUNT_ID')

StoreCls = btoandav20.stores.OandaV20Store
DataCls = btoandav20.feeds.OandaV20Data
BrokerCls = btoandav20.brokers.OandaV20Broker

store = StoreCls(token=token, account=accId, practice=True)
broker = store.getbroker()

datakwargs = dict(
    timeframe=bt.TimeFrame.Seconds, 
    compression=5,
    qcheck=0.5, # Timeout for periodic 'notification/resampling/replaying check'
    historical=False, # do only historical download
    bidask=False, # Use bidask ... if False use midpoint
    useask=False,
    backfill_start=False, # Backfilling at the start
    backfill=False # Backfilling after a disconnection
)

cerebro = bt.Cerebro()
cerebro.setbroker(broker)
data = DataCls(dataname='EUR_USD', **datakwargs)
cerebro.adddata(data, name='EUR_USD')
cerebro.addstrategy(TestStra)
cerebro.run()

And the out put is:

-- Contract Details:
{'name': 'EUR_USD', 'type': 'CURRENCY', 'displayName': 'EUR/USD', 'pipLocation': -4, 'displayPrecision': 5, 'tradeUnitsPrecision': 0, 'minimumTradeSize': '1.0', 'maximumTrailingStopDistance': '1.0', 'minimumTrailingStopDistance': '0.0005', 'maximumPositionSize': '0.0', 'maximumOrderUnits': '100000000.0', 'marginRate': '0.02'}
2018-04-30 05:14:09.203323
********************
2018-04-30 05:14:36.952126
********************
2018-04-30 05:15:01.749879
********************
2018-04-30 05:15:06.593084
********************
2018-04-30 05:15:19.020546
********************
2018-04-30 05:15:19.066050
********************
2018-04-30 05:15:19.659851
********************
2018-04-30 05:15:54.686889
********************
2018-04-30 05:15:58.245570

as you can see, its not fetching in every 5 seconds, but a random fashion. How should solve this problem? Many thanks in advance!

Stop Trail

Hi the readme states stoptrail only works in bracket orders. Will a normal stoptrail be implemented?

Also hoping if a close can implemented.

Exception during Trading

calling with:
--data0 EUR_USD --timeframe Minutes --compression 1 --trade --broker

leads to:

Exception in thread Thread-18:
Traceback (most recent call last):
  File "/home/user/anaconda3/lib/python3.6/threading.py", line 916, in _bootstrap_inner
    self.run()
  File "/home/user/anaconda3/lib/python3.6/threading.py", line 864, in run
    self._target(*self._args, **self._kwargs)
  File "/home/user/PycharmProjects/0362-backtrader-oandav20-in-between/btoandav20/stores/oandav20store.py", line 533, in _t_order_create
    if self._transactions.has_key(oid):
AttributeError: 'collections.defaultdict' object has no attribute 'has_key'

code fragment:

        # use the id of the transaction which created
        # the order, this will be the order id
        oid = o.id
        self._orders[oid] = oref

        # process transactions after id mapping was added
        if self._transactions.has_key(oid):                     #<<-----------------exception
            tpending = self._transactions.pop(oid)
            for trans in tpending:
                self._process_transaction(oid, trans)

backfill_from AttributeError '_env'

Im trying to do a backfill_from with bt.feeds.PandasData but gives me an error which I cant figure out the problem to:

AttributeError: 'Lines_LineSeries_DataSeries_OHLC_OHLCDateTime_Abst' object has no attribute '_env'

dataBackfill = bt.feeds.PandasData(dataname=dataframe)  

data = btoandav20.feeds.OandaV20Data(dataname=pair,reconnections=-1,reconntimeout=1,reconnect=True,qcheck= 0.05, backfill_from=dataBackfill,tz=pytz.timezone('Europe/London'), timeframe=bt.TimeFrame.Minutes, compression=1)

Any ideas what the issue would be?

Just so that you know the same file PandasData read in for the backfill_from works fine using ibstore.getdata().

Orders/Trades do not Appear in Oanda Transaction History

Hi,

I supply the test example with:
--token [token] --account [account] --data0 EUR_USD --timeframe Minutes --compression 1 --trade

I would expect that a trade would be executed at the OANDA backend accordingly.

Unfortunately, in the OANDA transaction history, I cannot find the order/trade (see attached log).

output.txt

S/L T/P T/S not working

Hi,
I'm back again I've been strugling for 2 days to get this working but I think I'm too stupid for this so I'll ask for a bit of help, I've downloaded the last fork uploaded yesterday, reinstalled everything from scratch. I don't know what I'm doing wrong but I need to setup the trailing stop and stop loss.

I've tried by adding here this method:

if self.datastatus and not self.position and len(self.orderid) < 1:
            if not self.p.usebracket:
                if not self.p.sell:
                    # price = round(self.data0.close[0] * 0.90, 2)
                    price = self.data0.close[0] - 0.005
                    self.order = self.buy(size=self.p.stake,
                                          exectype=self.p.exectype,
                                          price=price,
                                          valid=self.p.valid)
                else:
                    # price = round(self.data0.close[0] * 1.10, 4)
                    price = self.data0.close[0] - 0.05
                    self.order = self.sell(size=self.p.stake,
                                           exectype=self.p.exectype,
                                           price=price,
                                           valid=self.p.valid)

            else:
                print('USING BRACKET')
                price = self.data0.close[0] - 0.05
                self.order, _, _ = self.buy_bracket(size=self.p.stake,
                                                    exectype=bt.Order.Market,
                                                    price=price,
                                                    **stopprice = price - price * 0.001**,
						    **limitprice = price + price * 0.002**,
                                                    valid=self.p.valid)

also for trailing stop I've tried this method which again didn't do anything, in the fxTrade platform there's nothing in S/L T/P T/S columns, and also within the print of the order inside the terminal there's nothing:


            else:
                print('USING BRACKET')
                price = self.data0.close[0] - 0.05
                self.order, _, _ = self.buy_bracket(size=self.p.stake,
                                                    exectype=bt.Order.StopTrail, 
						    trailpercent=0.02,
                                                    valid=self.p.valid)

terminal print


-------------------------------------------------- ORDER BEGIN 2019-12-18 19:45:00.358522
Ref: 3
OrdType: 1
OrdType: Sell
Status: 4
Status: Completed
Size: -125
Price: 143.355
Price Limit: None
TrailAmount: None
TrailPercent: None
ExecType: 0
ExecType: Market
CommInfo: <backtrader.comminfo.CommInfoBase object at 0x7f4be29b4310>
End of Session: 737411.9999999999
Info: AutoOrderedDict()
Broker: None
Alive: False
-------------------------------------------------- ORDER END
-------------------------------------------------- TRADE BEGIN 2019-12-18 19:45:00.358930
ref:1
data:<btoandav20.feeds.oandav20feed.OandaV20Data object at 0x7f4be10c9fd0>
tradeid:0
size:0.0
price:143.337
value:0.0
commission:0.0
pnl:2.125000000003041
pnlcomm:2.125000000003041
justopened:False
isopen:False
isclosed:True
baropen:1
dtopen:737411.7375
barclose:3
dtclose:737411.7388888889
barlen:2
historyon:False
history:[]
status:2

I'm not sure if this is the only place where I need to declare the trailing stop and I don't understand how to add the stop loss for first step.
So let's suppose I trade long GBP/JPY, currently the price is 143.337, if it goes up to let's say 143.90 then the trailing stop should go after him and stop at a percentage or a number of pips, preferably the number of pips, in case I'm right then this trailing stop goes with it, change the stop loss right?, if I'm wrong, there's a stop loss in place (which I guess I should declare too through stopprice = price - price * 0.001....

I don't understand what I'm doing wrong and how to declare a stop price and a trailing stop in the same time, so if the strategy is right will get a profit at a certain level when the price goes up and then drops, if the strategy is wrong then it won't loose more than whichever price - price * 0.001.

Thank you very much again for your support.

candle prices

I need to open this issue again. I have added the timezone argument, but that has not resolved it for me.
I wanted to clarify - the time shown with each candle is correct. That is not the issue. The issue is that the ohlcv made available in the most recent candle is for the prior candle in oanda. For instance, at the 1:00 PM most recent data0 , it is getting the ohlcv that was displayed by Oanda on their web at 12:00. It is lagging the candle by 1 in the 1 hour size.

Trailing Stop by percent gives error

Using trailamount seems to be ok, but trailpercent gives error.

self.long_order2 = self.buy_bracket(exectype=bt.Order.Stop, stopexec=bt.Order.StopTrail, size=qty,
            limitprice=TP2_price,
            
            price=entry_price,
            
            # stopprice=stoploss_price,
            stopargs={
                # 'trailamount': stop_dist,
                'trailpercent': 0.01,
            },
        )
  File "brokers/backtrader/algo.py, line 574, in buy_risk
    'trailpercent': 0.01,
  File "/usr/local/lib/python3.7/site-packages/backtrader/strategy.py", line 1169, in buy_bracket
    olimit = self.sell(**kargs)
  File "/usr/local/lib/python3.7/site-packages/backtrader/strategy.py", line 969, in sell
    **kwargs)
  File "/usr/local/lib/python3.7/site-packages/btoandav20/brokers/oandav20broker.py", line 315, in sell
    return self._transmit(order)
  File "/usr/local/lib/python3.7/site-packages/btoandav20/brokers/oandav20broker.py", line 272, in _transmit
    self.o.order_create(parent, stopside, takeside)
  File "/usr/local/lib/python3.7/site-packages/btoandav20/stores/oandav20store.py", line 385, in order_create
    '.%df' % order.data.contractdetails['displayPrecision']),
TypeError: unsupported format string passed to NoneType.__format__

At a glance, it looks like there might not be support for trailing stop by percent? https://github.com/ftomassetti/backtrader-oandav20/blob/master/btoandav20/stores/oandav20store.py#L384
If so, could it be added?

Thank you for the library! ๐Ÿ‘

backfill_from does not backfill DELAYED or switch to LIVE data

As per output below you get a status notification that the data is DELAYED but no backfill or live data comes in.

Ive included below the output using ibstore(). You can see it notifies DELAYED, backfills and then switches to LIVE.

Ive included all outputs, code and the test file:

--------- Print btoandav20 of next(),notify_store(), notify_data()

EUR_USD 2019-09-20 09:44:00 1.10533
EUR_USD 2019-09-20 09:45:00 1.10521
EUR_USD 2019-09-20 09:46:00 1.10521
EUR_USD 2019-09-20 09:47:00 1.10525
EUR_USD 2019-09-20 09:48:00 1.10521
EUR_USD 2019-09-20 09:49:35.331337 1.10506
 STATUS ************ DATA NOTIF: EUR_USD DELAYED

--------- CODE for btoandav20

class TestX(bt.Strategy):

    def __init__(self):
        pass
    
    def notify_data(self, data, status, *args, **kwargs):
        print(" STATUS ************ DATA NOTIF: "+data._name+" "+data._getstatusname(status))

    def notify_store(self, msg, *args, **kwargs):
        print(" STORE NOTIF ------------- : "+str(msg))
    
    def next(self):
        print(self.data._name,self.data.datetime.datetime(),self.data.close[0])

def runstrat(args=None):
    pair = "EUR_USD"
    cerebro = bt.Cerebro()
    btoandav20.stores.OandaV20Store(token=apikey, account=acc, practice=True)
    filein = os.path.join(dir_path,"Data","Backtrader",pair+"_Test.h5")
    dataframe = pd.read_hdf(filein,"x")
    dataBackfill = bt.feeds.PandasData(dataname=dataframe) 
    data = btoandav20.feeds.OandaV20Data(dataname=pair,backfill_from=dataBackfill,backfill=True,timeframe=bt.TimeFrame.Minutes, compression=1)
    cerebro.adddata(data)
    cerebro.addstrategy(TestX)
    cerebro.run()

--------- Print ibstore of next(),notify_store(), notify_data()

EUR.USD-CASH-IDEALPRO 2019-09-20 05:46:00 1.10521
EUR.USD-CASH-IDEALPRO 2019-09-20 05:47:00 1.10525
EUR.USD-CASH-IDEALPRO 2019-09-20 05:48:00 1.10521
EUR.USD-CASH-IDEALPRO 2019-09-20 05:49:35.331337 1.10506
 STATUS ************ DATA NOTIF: EUR.USD-CASH-IDEALPRO DELAYED
 STORE NOTIF ------------- : <error id=-1, errorCode=2119, errorMsg=Market data farm is connecting:cashfarm>
EUR.USD-CASH-IDEALPRO 2019-09-20 05:50:00 1.10515
 STORE NOTIF ------------- : <error id=-1, errorCode=2104, errorMsg=Market data farm connection is OK:cashfarm>
 STORE NOTIF ------------- : <error id=-1, errorCode=2106, errorMsg=HMDS data farm connection is OK:cashhmds>
EUR.USD-CASH-IDEALPRO 2019-09-20 05:51:00 1.10507
EUR.USD-CASH-IDEALPRO 2019-09-20 05:52:00 1.10502
EUR.USD-CASH-IDEALPRO 2019-09-20 05:53:00 1.10491
EUR.USD-CASH-IDEALPRO 2019-09-20 05:54:00 1.10492
EUR.USD-CASH-IDEALPRO 2019-09-20 05:54:53.250373 1.10492
EUR.USD-CASH-IDEALPRO 2019-09-20 05:54:54.349542 1.1049
EUR.USD-CASH-IDEALPRO 2019-09-20 05:54:54.350538 1.10489
 STATUS ************ DATA NOTIF: EUR.USD-CASH-IDEALPRO LIVE
EUR.USD-CASH-IDEALPRO 2019-09-20 05:54:54.350538 1.1049
EUR.USD-CASH-IDEALPRO 2019-09-20 05:54:54.794882 1.10491

--------- CODE for ibstore


class TestX(bt.Strategy):

    def __init__(self):
        pass
    
    def notify_data(self, data, status, *args, **kwargs):
        print(" STATUS ************ DATA NOTIF: "+data._name+" "+data._getstatusname(status))

    def notify_store(self, msg, *args, **kwargs):
        print(" STORE NOTIF ------------- : "+str(msg))
    
    def next(self):
        print(self.data._name,self.data.datetime.datetime(),self.data.close[0])

def runstrat(args=None):
    pair = "EUR_USD"
    cerebro = bt.Cerebro()
    ibstore = bt.stores.IBStore(host='127.0.0.1', port=4002, clientId=1,reconnect=-1,timeout = 600) 
    filein = os.path.join(dir_path,"Data","Backtrader",pair+"_Test.h5")
    dataframe = pd.read_hdf(filein,"x")
    dataBackfill = bt.feeds.PandasData(dataname=dataframe) 
    data = ibstore.getdata(dataname='EUR.USD-CASH-IDEALPRO',backfill_from=dataBackfill, backfill=True,timeframe=bt.TimeFrame.Minutes, compression=1)
    cerebro.adddata(data)
    cerebro.addstrategy(TestX)
    cerebro.run()

-------- Test file EUR_USD_Test.h5.zip

EUR_USD_Test.h5.zip

How to Work With oandav20test.py? - Parameter --timeframe

Hi,

I try to make first steps with "oandav20test.py", but get difficulties.

How do I have to supply the "--timeframe" parameter properly? Using this:

import sys
sys.argv[1:] = [
    "--token", "123",
    "--account", "456",
    "--data0", "111"
           "--timeframe", "Minutes"  # , "1"
]

leads to an error:

oandav20test.py: error: unrecognized arguments: Minutes

Thanks in advance!

Issue in oandav20store.py line 879 for Python3

Hi,

Please refer to line 879:
del self._trades[key]

you should not delete an item while looping a dict or orderedDict, it will throws this exception:

File "/media/jimfoo88/Media/linux_files/anaconda3/envs/jimtfgpu/lib/python3.8/site-packages/btoandav20/stores/oandav20store.py", line 894, in _process_trades
    for key, value in self._trades.items():
RuntimeError: OrderedDict mutated during iteration

Please make a shallow copy before iterating the items, like this: self._trades.copy().items()

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.