forked from askmike/gekko
-
Notifications
You must be signed in to change notification settings - Fork 2
/
gekko.js
245 lines (188 loc) · 5.71 KB
/
gekko.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
/*
Gekko is a Bitcoin trading bot for popular Bitcoin exchanges written
in node, it features multiple trading methods using technical analysis.
Disclaimer:
USE AT YOUR OWN RISK!
The author of this project is NOT responsible for any damage or loss caused
by this software. There can be bugs and the bot may not perform as expected
or specified. Please consider testing it first with paper trading /
backtesting on historical data. Also look at the code to see what how
it's working.
*/
var gekkoDir = './';
var coreDir = gekkoDir + 'core/';
var pluginDir = gekkoDir + 'plugins/';
var _ = require('lodash');
var async = require('async');
var util = require(coreDir + 'util');
var log = require(coreDir + 'log');
// if the user just wants to see the current version
if(util.getArgument('v')) {
util.logVersion();
util.die();
}
// make sure the current node version is recent enough
if(!util.recentNode())
util.die([
'Your local version of nodejs is to old. ',
'You have ',
process.version,
' and you need atleast ',
util.getRequiredNodeVersion()
].join(''));
var config = util.getConfig();
// Temporary checks to make sure everything we need is
// up to date and present on the system.
// temp at Fri Jan 17 16:00:19 CET 2014
if(config.normal)
util.die('Please update your config! config.normal is now called config.watch');
if(config.EMA)
util.die('Please update your config! EMA is now called DEMA');
// temp at Wed Jan 22 12:18:08 CET 2014
if(!config.profitSimulator.slippage)
util.die('Please update your config! The profit simulator is missing slippage');
// temp at Sun Feb 9 17:13:45 CET 2014
if(!config.DEMA.thresholds)
util.die('Please update your config!');
if(
config.trader.enabled &&
!config['I understand that Gekko only automates MY OWN trading strategies']
)
util.die('Do you understand what Gekko will do with your money? Read this first:\n\nhttps://github.com/askmike/gekko/issues/201');
// START
log.info('Gekko v' + util.getVersion(), 'started');
log.info('I\'m gonna make you rich, Bud Fox.', '\n\n');
var gekkoMode = 'realtime';
// currently we only support a single
// market and a single advisor.
// make sure the monitoring exchange is configured correctly for monitoring
var exchangeChecker = require(coreDir + 'exchangeChecker');
var invalid = exchangeChecker.cantMonitor(config.watch);
if(invalid)
util.die(invalid);
var plugins = [];
var emitters = {};
var setupMarket = function(next) {
var Market = require(coreDir + 'marketManager');
emitters.market = new Market;
next();
}
// load each plugin
var loadPlugins = function(next) {
var pluginSettings = require(gekkoDir + 'plugins');
var iterator = function(plugin, next) {
// verify the actor settings in config
if(!(plugin.slug in config)) {
log.warn('unable to find', plugin.slug, 'in the config. Is your config up to date?')
return next();
}
var pluginConfig = config[plugin.slug];
// only load actors that are supported by
// Gekko's current mode
if(!_.contains(plugin.modes, gekkoMode))
return next();
// if the actor is disabled skip as well
if(!pluginConfig.enabled)
return next();
// verify plugin dependencies are installed
if('dependencies' in plugin)
_.each(plugin.dependencies, function(dep) {
try {
require(dep.module);
}
catch(e) {
var error = [
'The plugin',
plugin.slug,
'expects the module',
dep.module,
'to be installed.',
'However it is not, install',
'it by running: \n\n',
'\tnpm install',
dep.module + '@' + dep.version
].join(' ');
util.die(error);
}
});
var Plugin = require(pluginDir + plugin.slug);
if(!plugin.silent) {
log.info('Setting up:');
log.info('\t', plugin.name);
log.info('\t', plugin.description);
}
if(plugin.async) {
var instance = new Plugin(util.defer(next));
instance.meta = plugin;
plugins.push(instance);
} else {
var instance = new Plugin;
instance.meta = plugin;
plugins.push(instance);
_.defer(next);
}
if(!plugin.silent)
console.log();
}
async.eachSeries(
pluginSettings,
iterator,
next
);
};
// advisor is a special actor in that it spawns an
// advice feed which everyone can subscribe to.
var setupAdvisor = function(next) {
var settings;
var plugin = _.find(plugins, function(advisor) {
if(!advisor.meta.originates)
return false;
settings = _.find(
advisor.meta.originates,
function(o) {
return o.feed === 'advice feed'
}
);
return settings;
});
emitters.advisor = settings ? plugin[settings.object] : false;
next();
}
var attachPlugins = function(next) {
var subscriptions = require(gekkoDir + 'subscriptions');
_.each(plugins, function(plugin) {
_.each(subscriptions, function(sub) {
if(sub.handler in plugin) {
// if the actor wants to listen
// to something disabled
if(!emitters[sub.emitter])
return log.warn([
plugin.meta.name,
'wanted to listen to the',
sub.emitter + ',',
'however the',
sub.emitter,
'is disabled.'
].join(' '))
// attach handler
emitters[sub.emitter]
.on(sub.event, plugin[sub.handler]);
}
});
});
next();
}
log.info('Setting up Gekko in', gekkoMode, 'mode');
console.log();
async.series(
[
loadPlugins,
setupAdvisor,
setupMarket,
attachPlugins
],
function() {
// everything is setup!
emitters.market.start();
}
);