Skip to content

Commit

Permalink
Merge pull request #42 from Adamant-im/dev
Browse files Browse the repository at this point in the history
v5.7.0
  • Loading branch information
just-software-dev authored Nov 8, 2023
2 parents f10fd28 + da2a4ea commit 0cf28af
Show file tree
Hide file tree
Showing 34 changed files with 2,751 additions and 2,062 deletions.
2 changes: 2 additions & 0 deletions .eslintignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
/trade/settings
/trade/tests
24 changes: 14 additions & 10 deletions .eslintrc.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,33 +5,37 @@ module.exports = {
node: true,
},
extends: [
'eslint:recommended',
'google',
],
parser: '@babel/eslint-parser',
parserOptions: {
ecmaVersion: 12,
},
rules: {
quotes: ['error', 'single'],
'prefer-arrow-callback': ['error'],
'object-shorthand': ['error', 'always'],
'quote-props': ['error', 'as-needed'],
'object-curly-spacing': ['error', 'always'],
'max-len': ['error',
{ 'code': 131,
'ignoreTrailingComments': true,
'ignoreComments': true,
'ignoreUrls': true,
'ignoreStrings': true,
'ignoreTemplateLiterals': true,
'ignoreRegExpLiterals': true,
{ code: 133,
ignoreTrailingComments: true,
ignoreComments: true,
ignoreUrls: true,
ignoreStrings: true,
ignoreTemplateLiterals: true,
ignoreRegExpLiterals: true,
}],
'require-jsdoc': ['off'],
'valid-jsdoc': ['off'],
'no-array-constructor': ['off'],
'no-caller': ['off'],
'prefer-promise-reject-errors': ['off'],
'guard-for-in': ['off'],
'no-unused-vars': ['off'],
'padded-blocks': ['off'],
'new-cap': ['off'],
'camelcase': ['off'],
'eqeqeq': ['error', 'always'],
camelcase: ['off'],
eqeqeq: ['error', 'always'],
},
};
20 changes: 14 additions & 6 deletions app.js
Original file line number Diff line number Diff line change
@@ -1,14 +1,16 @@
const notify = require('./helpers/notify');
const db = require('./modules/DB');
const checker = require('./modules/checkerTransactions');
const doClearDB = process.argv.includes('clear_db');
const config = require('./modules/configReader');
const txParser = require('./modules/incomingTxsParser');
const { initApi } = require('./routes/init');

// Socket connection
const api = require('./modules/api');
api.socket.initSocket({ socket: config.socket, wsType: config.ws_type, onNewMessage: txParser, admAddress: config.address });
if (config.passPhrase) {
const api = require('./modules/api');
const txParser = require('./modules/incomingTxsParser');

api.socket.initSocket({ socket: config.socket, wsType: config.ws_type, onNewMessage: txParser, admAddress: config.address });
}

setTimeout(init, 5000);

Expand All @@ -24,13 +26,19 @@ function init() {
db.ordersDb.db.drop();
notify(`*${config.notifyName}: database cleared*. Manually stop the Bot now.`, 'info');
} else {
checker();
if (config.passPhrase) {
const checker = require('./modules/checkerTransactions');
checker();
}

require('./trade/mm_trader').run();
require('./trade/mm_orderbook_builder').run();
require('./trade/mm_liquidity_provider').run();
require('./trade/mm_price_watcher').run();
// require('./trade/mm_orderbook_builder').test();
notify(`*${config.notifyName} started* for address _${config.address}_ (ver. ${config.version}).`, 'info');

const addressInfo = config.address ? ` for address _${config.address}_` : ' in CLI mode';
notify(`${config.notifyName} *started*${addressInfo} (ver. ${config.version}).`, 'info');
}
} catch (e) {
notify(`${config.notifyName} is not started. Error: ${e}`, 'error');
Expand Down
13 changes: 13 additions & 0 deletions helpers/const.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,12 +9,25 @@ module.exports = {
UPDATE_CRYPTO_RATES_INTERVAL: 60 * 1000, // Update crypto rates every minute
PRECISION_DECIMALS: 8, // Accuracy for converting cryptos, 9.12345678 ETH
PRINT_DECIMALS: 8, // For pretty print, 9.12345678 ETH
DEFAULT_WITHDRAWAL_PRECISION: 8, // If exchange's currency info doesn't provide coin decimals
MAX_ADM_MESSAGE_LENGTH: 10000,
MAX_TELEGRAM_MESSAGE_LENGTH: 4095,
EXECUTE_IN_ORDER_BOOK_MAX_PRICE_CHANGE_PERCENT: 0.15, // In-orderbook trading: don't change price by mm-order more, than 0.15%
EXECUTE_IN_ORDER_BOOK_MAX_SPREAD_PERCENT: 0.15 / 1.25, // In-orderbook trading: Maintain spread percent
LIQUIDITY_SS_MAX_SPREAD_PERCENT: 0.2, // Liquidity spread support orders: Maintain spread percent
DEFAULT_ORDERBOOK_ORDERS_COUNT: 15,
DEFAULT_PW_DEVIATION_PERCENT_FOR_DEPTH_PM: 1,
SOCKET_DATA_VALIDITY_MS: 2000,
SOCKET_DATA_MAX_HEARTBEAT_INTERVAL_MS: 25000,
MM_POLICIES: ['optimal', 'spread', 'orderbook', 'depth', 'wash'],
MM_POLICIES_VOLUME: ['optimal', 'spread', 'orderbook', 'wash'],
MM_POLICIES_REGULAR: ['optimal', 'spread', 'orderbook', 'depth'],
MM_POLICIES_REGULAR_VOLUME: ['optimal', 'spread', 'orderbook'],
MM_POLICIES_IN_SPREAD_TRADING: ['optimal', 'spread', 'wash'],
MM_POLICIES_IN_ORDERBOOK_TRADING: ['optimal', 'orderbook', 'depth'],
LADDER_STATES: ['Not placed', 'Open', 'Filled', 'Partly filled', 'Cancelled', 'Missed', 'To be removed', 'Removed'],
LADDER_OPENED_STATES: ['Open', 'Partly filled'],
LADDER_PREVIOUS_FILLED_ORDER_STATES: [undefined, 'Not placed', 'Filled', 'Cancelled', 'To be removed', 'Removed'],
REGEXP_WHOLE_NUMBER: /^[0-9]+$/,
REGEXP_UUID: /^[a-f\d]{4}(?:[a-f\d]{4}-){4}[a-f\d]{12}$/,
};
8 changes: 5 additions & 3 deletions helpers/cryptos/adm_utils.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,11 @@ module.exports = class admCoin extends baseCoin {
this.account.passPhrase = config.passPhrase;
this.account.keyPair = config.keyPair;
this.account.address = config.address;
this.getBalance().then((balance) => {
log.log(`Initial ${this.token} balance: ${balance ? balance.toFixed(constants.PRINT_DECIMALS) : 'unable to receive'}`);
});
if (this.account.passPhrase) {
this.getBalance().then((balance) => {
log.log(`Initial ${this.token} balance: ${balance ? balance.toFixed(constants.PRINT_DECIMALS) : 'unable to receive'}`);
});
}
}

get FEE() {
Expand Down
6 changes: 3 additions & 3 deletions helpers/cryptos/exchanger.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,10 @@ module.exports = {
async updateCryptoRates() {
const url = config.infoservice + '/get';
const rates = await axios.get(url, {})
.then(function(response) {
.then((response) => {
return response.data ? response.data.result : undefined;
})
.catch(function(error) {
.catch((error) => {
log.warn(`Unable to fetch crypto rates in updateCryptoRates() of ${utils.getModuleName(module.id)} module. Request to ${url} failed with ${error.response ? error.response.status : undefined} status code, ${error.toString()}${error.response && error.response.data ? '. Message: ' + error.response.data.toString().trim() : ''}.`);
});

Expand Down Expand Up @@ -86,7 +86,7 @@ module.exports = {
if (this.isERC20(to)) {
networkFee = this.convertCryptos('ETH', to, networkFee).outAmount;
}
};
}
const value = rate * +amount - networkFee;
return {
outAmount: +value.toFixed(constants.PRECISION_DECIMALS),
Expand Down
38 changes: 38 additions & 0 deletions helpers/dateTime.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
function time() {
return formatDate(Date.now()).hh_mm_ss;
}

function date() {
return formatDate(Date.now()).YYYY_MM_DD;
}

function fullTime() {
return date() + ' ' + time();
}

/**
* Formats unix timestamp to string
* @param {number} timestamp Timestamp to format
* @return {object} Contains different formatted strings
*/
function formatDate(timestamp) {
if (!timestamp) return false;
const formattedDate = {};
const dateObject = new Date(timestamp);
formattedDate.year = dateObject.getFullYear();
formattedDate.month = ('0' + (dateObject.getMonth() + 1)).slice(-2);
formattedDate.date = ('0' + dateObject.getDate()).slice(-2);
formattedDate.hours = ('0' + dateObject.getHours()).slice(-2);
formattedDate.minutes = ('0' + dateObject.getMinutes()).slice(-2);
formattedDate.seconds = ('0' + dateObject.getSeconds()).slice(-2);
formattedDate.YYYY_MM_DD = formattedDate.year + '-' + formattedDate.month + '-' + formattedDate.date;
formattedDate.YYYY_MM_DD_hh_mm = formattedDate.year + '-' + formattedDate.month + '-' + formattedDate.date + ' ' + formattedDate.hours + ':' + formattedDate.minutes;
formattedDate.hh_mm_ss = formattedDate.hours + ':' + formattedDate.minutes + ':' + formattedDate.seconds;
return formattedDate;
}

module.exports = {
time,
date,
fullTime,
};
2 changes: 1 addition & 1 deletion helpers/dbModel.js
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,7 @@ module.exports = (db) => {
return this._id;
}
}
};
}

return Model;
};
62 changes: 19 additions & 43 deletions helpers/log.js
Original file line number Diff line number Diff line change
@@ -1,72 +1,48 @@
const config = require('../modules/configReader');
const dateTime = require('./dateTime');

const fs = require('fs');
if (!fs.existsSync('./logs')) {
fs.mkdirSync('./logs');
}

const infoStr = fs.createWriteStream('./logs/' + date() + '.log', {
const infoStr = fs.createWriteStream('./logs/' + dateTime.date() + '.log', {
flags: 'a',
});

infoStr.write(`\n\n[The bot started] _________________${fullTime()}_________________\n`);
infoStr.write(`\n\n[The bot started] _________________${dateTime.fullTime()}_________________\n`);

module.exports = {
error(str) {
if (['error', 'warn', 'info', 'log'].includes(config.log_level)) {
infoStr.write(`\n ` + 'error|' + fullTime() + '|' + str);
console.log('\x1b[31m', 'error|' + fullTime(), '\x1b[0m', str);
if (!process.env.CLI_MODE_ENABLED) {
console.log('\x1b[31m', 'error|' + dateTime.fullTime(), '\x1b[0m', str);
}
infoStr.write('\n ' + 'error|' + dateTime.fullTime() + '|' + str);
}
},
warn(str) {
if (['warn', 'info', 'log'].includes(config.log_level)) {
console.log('\x1b[33m', 'warn|' + fullTime(), '\x1b[0m', str);
infoStr.write(`\n ` + 'warn|' + fullTime() + '|' + str);
if (!process.env.CLI_MODE_ENABLED) {
console.log('\x1b[33m', 'warn|' + dateTime.fullTime(), '\x1b[0m', str);
}
infoStr.write('\n ' + 'warn|' + dateTime.fullTime() + '|' + str);
}
},
info(str) {
if (['info', 'log'].includes(config.log_level)) {
console.log('\x1b[32m', 'info|' + fullTime(), '\x1b[0m', str);
infoStr.write(`\n ` + 'info|' + fullTime() + '|' + str);
if (!process.env.CLI_MODE_ENABLED) {
console.log('\x1b[32m', 'info|' + dateTime.fullTime(), '\x1b[0m', str);
}
infoStr.write('\n ' + 'info|' + dateTime.fullTime() + '|' + str);
}
},
log(str) {
if (['log'].includes(config.log_level)) {
console.log('\x1b[34m', 'log|' + fullTime(), '\x1b[0m', str);
infoStr.write(`\n ` + 'log|[' + fullTime() + '|' + str);
if (!process.env.CLI_MODE_ENABLED) {
console.log('\x1b[34m', 'log|' + dateTime.fullTime(), '\x1b[0m', str);
}
infoStr.write('\n ' + 'log|[' + dateTime.fullTime() + '|' + str);
}
},
};

function time() {
return formatDate(Date.now()).hh_mm_ss;
}

function date() {
return formatDate(Date.now()).YYYY_MM_DD;
}

function fullTime() {
return date() + ' ' + time();
}

/**
* Formats unix timestamp to string
* @param {number} timestamp Timestamp to format
* @return {object} Contains different formatted strings
*/
function formatDate(timestamp) {
if (!timestamp) return false;
const formattedDate = {};
const dateObject = new Date(timestamp);
formattedDate.year = dateObject.getFullYear();
formattedDate.month = ('0' + (dateObject.getMonth() + 1)).slice(-2);
formattedDate.date = ('0' + dateObject.getDate()).slice(-2);
formattedDate.hours = ('0' + dateObject.getHours()).slice(-2);
formattedDate.minutes = ('0' + dateObject.getMinutes()).slice(-2);
formattedDate.seconds = ('0' + dateObject.getSeconds()).slice(-2);
formattedDate.YYYY_MM_DD = formattedDate.year + '-' + formattedDate.month + '-' + formattedDate.date;
formattedDate.YYYY_MM_DD_hh_mm = formattedDate.year + '-' + formattedDate.month + '-' + formattedDate.date + ' ' + formattedDate.hours + ':' + formattedDate.minutes;
formattedDate.hh_mm_ss = formattedDate.hours + ':' + formattedDate.minutes + ':' + formattedDate.seconds;
return formattedDate;
}
42 changes: 25 additions & 17 deletions helpers/notify.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,20 +13,29 @@ const {
} = config;

const slackColors = {
'error': '#FF0000',
'warn': '#FFFF00',
'info': '#00FF00',
'log': '#FFFFFF',
error: '#FF0000',
warn: '#FFFF00',
info: '#00FF00',
log: '#FFFFFF',
};

const discordColors = {
'error': '16711680',
'warn': '16776960',
'info': '65280',
'log': '16777215',
error: '16711680',
warn: '16776960',
info: '65280',
log: '16777215',
};

/**
* Notify to channels, which set in config
* @param {String} messageText Notification message, may include markdown
* @param {String} type error < warn < info < log
* @param {Boolean} silent_mode If true, only priority notification will be sent. only logging
* @param {Boolean} isPriority Priority notifications have special channels
*/
module.exports = (messageText, type, silent_mode = false, isPriority = false) => {
const paramString = `messageText: '${messageText}', type: ${type}, silent_mode: ${String(silent_mode)}, isPriority: ${String(isPriority)}`;

try {
const prefix = isPriority ? '[Attention] ' : '';
const message = `${prefix}${messageText}`;
Expand All @@ -40,19 +49,19 @@ module.exports = (messageText, type, silent_mode = false, isPriority = false) =>

if (slackKeys.length) {
const params = {
'attachments': [{
'fallback': message,
'color': slackColors[type],
'text': makeBoldForSlack(message),
'mrkdwn_in': ['text'],
attachments: [{
fallback: message,
color: slackColors[type],
text: makeBoldForSlack(message),
mrkdwn_in: ['text'],
}],
};

slackKeys.forEach((slackApp) => {
if (typeof slackApp === 'string' && slackApp.length > 34) {
axios.post(slackApp, params)
.catch((error) => {
log.log(`Request to Slack with message ${message} failed. ${error}.`);
log.warn(`Notifier: Request to Slack with message ${message} failed. ${error}.`);
});
}
});
Expand All @@ -68,7 +77,7 @@ module.exports = (messageText, type, silent_mode = false, isPriority = false) =>
const mdMessage = makeBoldForMarkdown(message);
api.sendMessage(config.passPhrase, admAddress, `${type}| ${mdMessage}`).then((response) => {
if (!response.success) {
log.warn(`Failed to send notification message '${mdMessage}' to ${admAddress}. ${response.errorMessage}.`);
log.warn(`Notifier: Failed to send notification message '${mdMessage}' to ${admAddress}. ${response.errorMessage}.`);
}
});
}
Expand Down Expand Up @@ -97,12 +106,11 @@ module.exports = (messageText, type, silent_mode = false, isPriority = false) =>
}
});
}

} else {
log[type](`/No notification, Silent mode, Logging only/ ${removeMarkdown(message)}`);
}
} catch (e) {
log.error('Notifier error: ' + e);
log.error(`Notifier: Error while processing a notification with params ${paramString}. ${e}`);
}
};

Expand Down
Loading

0 comments on commit 0cf28af

Please sign in to comment.