oanda-trading-environment 0.2.0
OANDA REST-API based environment serving as a base for futher development of trading tools. Main part is the OANDAd daemon processing the streaming quotes
License: MIT
Keywords: Python OANDA oandapy REST API trading modules

OANDA Trading Environment
=========================

`|PyPI version| <http://badge.fury.io/py/oanda-trading-environment>`_

The OANDA Trading Environment is built using the OANDA REST-API by making use of the `https://github.com/oanda/oandapy <https://github.com/oanda/oandapy>`_ API-wrapper.

Streaming Candles
-----------------

Main part is the **OANDAd** daemon that parses the streaming quotes in configurable timeframes, by 1 minute, 5 minutes, 15 minutes etc. This makes it produce streaming candles.

Candle data:

::

      {"data": {"instrument": "EUR_JPY",
                "granularity" : "M1",
                "start": "2015-09-02 15:36:00"
                "end": "2015-09-02 15:37:00",
                "data": {"high": 134.967, 
                         "open": 134.962,
                         "last": 134.9565,
                          "low": 134.9475,
                       "volume": 19
                 },
               }
       }

The larger timeframes can be requested using the API.

Actions
-------

When a timeframe is completed it can be handled by one or more plugins. Plugins have a configfile based on the name of the plugin-file, but in lowercase. The plugins can be found under *etc/OANDA/plugins* and the plugin configs under *etc/OANDA/config/plugins*.

Plugins need to be enabled in the config file, see the 'plugins:' section in *etc/OANDA/config/OANDAd.cfg*.

The environment comes with a few plugins:

Publish/Subscribe - plugin
~~~~~~~~~~~~~~~~~~~~~~~~~~

This plugin can be configured to 'publish' the candle using a publisher/subscriber mechanism. This is achieved by using the `0MQ <http://zeromq.org>`_ library and the python binding for it: pyzmq

Other trading applications can easily subscribe to receive the candle data. See `here <#zmq_example>`_ for a ZMQ subscription example.

This plugin is enabled by default.

Plainfile - plugin
~~~~~~~~~~~~~~~~~~

This plugin can be configured to write candle records to a flatfile in a directory structure.

Example:

::

     /tmp/oandadb
     |-- BCO_USD
     |   |-- M1
     |   |   `-- cache
     |   |-- M15
     |   |   `-- cache
     |   `-- M5
     |       `-- cache
     |-- DE30_EUR
     |   |-- M1
     |   |   `-- cache
     |   |-- M15
     |   |   `-- cache
     |   `-- M5
     |       `-- cache
     |-- EUR_CHF
     |   |-- M1
     |   |   `-- cache
     |   |-- M15
     |   |   `-- cache
     |   `-- M5
     |       `-- cache
     |-- EUR_GBP
     |   |-- M1
     |   |   `-- cache
     |   |-- M15
     |   |   `-- cache
     |   `-- M5
     |       `-- cache
     |-- EUR_JPY
     |   |-- M1
     |   |   `-- cache
     |   |-- M15
     |   |   `-- cache
     |   `-- M5
     |       `-- cache
     |-- EUR_USD
         |-- M1
         |   `-- cache
         |-- M15
         |   `-- cache
         `-- M5
             `-- cache

MySQL - plugin
~~~~~~~~~~~~~~

The MySQL plugin can be configured to insert records into a database. This plugin is provided as an example, since it needs details that depend on your databasemodel.

Specs and Prerequisites
-----------------------

To access the OANDA services you will need a token, see `https://developer.oanda.com <https://developer.oanda.com>`_ for details.

Install
-------

Git
~~~

Install by using a virtual environment and git:

::

      $ cd <somewhere>
      $ mkdir OANDA
      $ cd OANDA
      $ virtualenv venv

Optionally use *--system-site-packages* to use the standard available packages for the python modules available on your system: *pyyaml*, *pyzmq*. Check for the packages on the distribution you use.

::

      $ . ./venv/bin/activate
      $ git clone https://github.com/hootnot/oanda-trading-environment.git
      $ cd oanda-trading-environment
      $ python setup.py install

OANDA has not made the oandapy module pip installable. A hack to get oandapy installed as a standalone module:

::

      $ pip install git+https://github.com/hootnot/oandapy

This will install the latest oandapy using the setup.py from the oandapy fork.

::

      $ pip list | grep oanda
      oanda-trading-environment (0.0.1)
      oandapy (0.1)

pip
~~~

Install from pypi:

using a virtual environment:

::

      $ cd <somewhere>
      $ mkdir OANDA
      $ cd OANDA
      $ virtualenv [--system-site-packages] venv
      $ . ./venv/bin/activate
      $ pip install oanda-trading-environment
      $ pip install git+https://github.com/hootnot/oandapy

using a system install:

::

      $ sudo pip install oanda-trading-environment
      $ sudo pip install git+https://github.com/hootnot/oandapy

Configure the OANDAd.cfg config file and start the daemon.

Quick start
~~~~~~~~~~~

After installing you **need** to configure the environment by editing the config file *etc/OANDA/config/OANDAd.cfg*. This is a YAML based configfile.

Configure the **environment** and the **token**. Alter the list of instruments you want to follow.

The pubsub plugin publishes by default at localhost, port 5550. These can be altered in the 'pubsub' config: *etc/OANDA/config/plugins/pubsub.cfg*.

Controlling OANDAd
^^^^^^^^^^^^^^^^^^

OANDAd is built using `daemoncle <https://github.com/jnrbsn/daemonocle>`_. The 'start', 'status' and 'stop' commands are implemented. The daemon forks itself and the child will process the stream. When there are issues, TIME-OUT for instance, the child will exit and a new child will be spawned.

::

      $ OANDAd start 
      Starting OANDAd ... OK

      $ OANDAd status
      OANDAd -- pid: 51931, status: sleeping, uptime: 0m, %cpu: 0.0, %mem: 1.8

      $ OANDAd stop
      Stopping OANDAd ... OK

The daemon will process streaming quotes now and process the timeframes as configured. Timeframes are currently based on the midprice of bid/ask.

Logging
~~~~~~~

The ticks received from the stream are written to a logfile:

::

     streamdata.<date>

The daemon itself logs to OANDAd.log

Loglevel and the streamdata logfile extension is configurable. Check the *OANDAd.cfg* file for details.

ZMQ - client
~~~~~~~~~~~~

This simple piece of code acts as a subscriber to the daemon. All completed timeframes are written to stdout. Using ZMQ make it easy to program different strategies completely independent from each other. By using 'topics' it is possible to subscribe for a certain time granularity like M1, M5 etc. Check the ZMQ for details.

::

     import zmq

     context = zmq.Context()
     socket = context.socket( zmq.SUB)
     socket.connect("tcp://127.0.0.1:5550")
     socket.setsockopt(zmq.SUBSCRIBE, "")

     socket.setsockopt( zmq.RCVBUF, 1000)
     while True:
       msg = socket.recv()
       print "GOT: ", msg

This will show candle data like below, every time a timeframe is completed.

::

     GOT:  {"data": {
                     "instrument": "EUR_GBP",
                     "granularity": "M1",
                     "start": "2015-09-04 17:45:00",
                     "end": "2015-09-04 17:46:00",
                     "data": {
                              "high": 0.734445,
                              "open": 0.734399,
                              "last": 0.73437,
                              "low": 0.734345,
                              "volume": 16
                             }
                    }
           }

     GOT:  {"data": {
                     "instrument": "EUR_JPY",
                     "granularity": "M1",
                     "start": "2015-09-04 17:45:00",
                     "end": "2015-09-04 17:46:00",
                     "data": {
                              "high": 132.629,
                              "open": 132.619,
                              "last": 132.6185,
                              "low": 132.608,
                              "volume": 15
                             }
                    }
            }

     GOT:  {"data": {
                     "instrument": "SPX500_USD",
                     "granularity": "M1",
                     "start": "2015-09-04 17:45:00",
                     "end": "2015-09-04 17:46:00",
                     "data": {
                              "high": 1915.35,
                              "open": 1914.75,
                              "last": 1915.25,
                              "low": 1914.75,
                              "volume": 33
                             }
                    }
            }

.. |PyPI version| image:: https://badge.fury.io/py/oanda-trading-environment.svg