UNPKG

robinhood-yolo

Version:

NodeJS API wrapper for Robinhood Options trading and CLI to trade from your terminal

310 lines (297 loc) 9.36 kB
var TIMEOUT, a, assert, chalk, moment, p, presetList, presetObject, should, testOption; a = require('../utils/apiMaster')({ newLogin: true }); p = require('print-tools-js'); chalk = require('chalk'); moment = require('moment'); assert = require('chai').assert; should = require('chai').should(); TIMEOUT = 25000; // Test Option testOption = { ticker: 'SPY', date: '2023-12-15' }; //: List Preset presetList = function(func, key, arg1, arg2, arg3, arg4, arg5, arg6) { var data; data = null; before(async function() { this.timeout(TIMEOUT); return data = (await func.bind(a)(arg1, arg2, arg3, arg4, arg5, arg6)); }); it('Returns array', function() { return data.should.be.a('array'); }); return it('Key exists', function() { return assert.equal(data[0][key] != null, true); }); }; //: Object Preset presetObject = function(func, key, arg1, arg2, arg3, arg4, arg5, arg6) { var data; data = null; before(async function() { this.timeout(TIMEOUT); return data = (await func.bind(a)(arg1, arg2, arg3, arg4, arg5, arg6)); }); it('Returns object', function() { return data.should.be.a('object'); }); return it('Key exists', function() { return assert.equal(data[key] != null, true); }); }; if (a.configData != null) { //: Test Constructor describe('constructor()', function() { before(async function() { return (await a.login()); }); it('Is object', function() { return a.should.be.a('object'); }); it('Has username', function() { return a.username.should.be.a('string'); }); it('Has access token', function() { return a.accessToken.should.be.a('string'); }); it('Has refresh token', function() { return a.refreshToken.should.be.a('string'); }); it('Has auth token', function() { return assert.equal(a.authToken.indexOf('Bearer'), 0); }); return it('Has account URL', function() { return a.accountUrl.should.be.a('string'); }); }); //: Test Account describe('getAccount()', function() { return presetObject(a.getAccount, 'margin_balances'); }); //: Test Portfolio describe('getPortfolioInfo()', function() { return presetObject(a.getPortfolioInfo, 'equity'); }); //: Test Get Equity describe('getAccountEquity()', function() { return it('Returns number', async function() { var data; data = (await a.getAccountEquity()); return data.should.be.a('number'); }); }); //: Test Get Cash Balance describe('getCashBalance()', function() { return it('Returns number', async function() { var data; data = (await a.getCashBalance()); return data.should.be.a('number'); }); }); //: Test Market Hours describe('getMarketHours()', function() { return presetObject(a.getMarketHours, 'is_open', '2019-07-04'); }); //: Test Transfers describe('getTransfers()', function() { return presetList(a.getTransfers, 'scheduled'); }); //: Test Stock Orders describe('stockOrders()', function() { return presetList(a.stockOrders, 'instrument'); }); //: Test Get Watchlist describe('getWatchList()', function() { return presetList(a.getWatchList, 'quote_data', { instrumentData: true, quoteData: true }); }); //: Test Quotes for single instrument describe('quotes() - single', function() { return presetObject(a.quotes, 'chain_data', 'GE', { chainData: true }); }); //: Test Quotes for multiple instruments describe('quotes() - multiple', function() { return presetList(a.quotes, 'chain_data', ['GE', 'AAPL'], { chainData: true }); }); //: Test Historicals describe('historicals()', function() { presetList(a.historicals, 'close_price', 'GE', { interval: 'day', span: 'year', bounds: 'regular' }); return it('Test Multiple instruments', async function() { var data; data = (await a.historicals(['GE', 'AAPL'])); return data[0].should.be.a('array'); }); }); //: Test Options Historicals describe('optionsHistoricals()', function() { return presetList(a.findOptionHistoricals, 'begins_at', testOption.ticker, testOption.date); }); //: Test Get Options describe('getOptions()', function() { return presetList(a.getOptions, 'market_data', testOption.ticker, testOption.date, { optionType: 'call', marketData: true }); }); //: Test Find Options for single option describe('findOptions() - single', function() { return presetObject(a.findOptions, 'market_data', testOption.ticker, testOption.date, { optionType: 'call', strikeType: 'itm', strikeDepth: 0, marketData: true }); }); //: Test Find Options by strike price describe('findOptions() - strike', function() { return presetObject(a.findOptions, 'market_data', testOption.ticker, testOption.date, { optionType: 'call', strike: 11.00, marketData: true }); }); //: Test Find Options for multiple options describe('findOptions() - range', function() { return presetList(a.findOptions, 'strike_price', testOption.ticker, testOption.date, { optionType: 'call', range: 3 }); }); //: Test Options Positions for all describe('optionsPositions() - all', function() { return presetList(a.optionsPositions, 'chain_symbol', { marketData: false, orderData: false, openOnly: false }); }); //: Test Options Positions for open only describe('optionsPositions() - open only', function() { var data; data = null; before(async function() { this.timeout(TIMEOUT); return data = (await a.optionsPositions({ marketData: true, orderData: true })); }); it('Returns array', function() { return data.should.be.a('array'); }); return it('Key exists', function() { if ((data != null) && data.length !== 0) { p.success("Has open positions, testing."); return assert.equal(data[0]['market_data'] != null, true); } else { p.warning(chalk`No open positions, skipping {cyan optionsPositions() - open only} - {magenta Key exists}.`); return this.skip(); } }); }); //: Test Options Orders for all orders describe('optionsOrders() - all', function() { return presetList(a.optionsOrders, 'legs'); }); //: Test Options Orders for not filled describe('optionsOrders() - not filled', function() { var data; data = null; before(async function() { this.timeout(TIMEOUT); return data = (await a.optionsOrders({ notFilled: true })); }); it('Returns array', function() { return data.should.be.a('array'); }); return it('Key exists', function() { if ((data != null) && data.length > 0) { p.success("Has unfilled orders, testing."); return assert.equal(data[0]['legs'] != null, true); } else { p.warning(chalk`No unfilled orders, skipping {cyan optionsOrders() - not filled} - {magenta Key exists}.`); return this.skip(); } }); }); //: Test Options Orders for single order describe('optionsOrders() - single', function() { return presetObject(a.optionsOrders, 'legs', { id: 'af8d5deb-df2f-42a7-974e-7e16729937f7' }); }); //: Test get history describe('getHistory()', function() { return presetList(a.getHistory, 'amount', { consume: false }); }); //: Test Placing Options orders, replacing, and canceling describe('Placing Orders', function() { var buy, cancel, curTime, dateNum, replace; curTime = new Date(); buy = replace = cancel = null; dateNum = (curTime.getHours() * 10000) + (curTime.getMinutes() * 100) + curTime.getSeconds(); before(async function() { var accountData, data, doTest; this.timeout(TIMEOUT); doTest = true; accountData = (await a.getAccount()); if (Number(accountData.buying_power) <= 0) { p.warning("Account has no buying power, skipping"); doTest = false; } if (dateNum <= 160100) { p.warning(chalk`Markets are open (${dateNum}), skipping {cyan Placing Orders} - {magenta all}.`); doTest = false; } if (doTest) { p.success(`Markets are closed (${dateNum}), will test placing orders.`); data = (await a.findOptions(testOption.ticker, testOption.date, { strikeDepth: 7 })); buy = (await a.placeOptionOrder(data.url, 1, 0.01)); replace = (await a.replaceOptionOrder(1, 0.02, { orderId: buy.id })); return cancel = (await a.cancelOptionOrder(replace.cancel_url)); } else { return this.skip(); } }); it('Buy returns object', function() { return buy.should.be.a('object'); }); it('Buy key exists', function() { return assert.equal(buy.id != null, true); }); it('Replace returns object', function() { return replace.should.be.a('object'); }); it('Replace key exists', function() { return assert.equal(replace.id != null, true); }); return it('Cancel returns true', function() { return assert.equal(cancel, true); }); }); } else { p.error('No accounts in config file. Exiting.'); } //::: End Program :::