New Case Study:See how Anthropic automated 95% of dependency reviews with Socket.Learn More
Socket
Sign inDemoInstall
Socket

kraken-api

Package Overview
Dependencies
Maintainers
1
Versions
20
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

kraken-api - npm Package Compare versions

Comparing version 0.1.7 to 1.0.0

244

kraken.js

@@ -1,22 +0,77 @@

var request = require('request');
var crypto = require('crypto');
var querystring = require('querystring');
const got = require('got');
const crypto = require('crypto');
const qs = require('qs');
// Public/Private method names
const methods = {
public : [ 'Time', 'Assets', 'AssetPairs', 'Ticker', 'Depth', 'Trades', 'Spread', 'OHLC' ],
private : [ 'Balance', 'TradeBalance', 'OpenOrders', 'ClosedOrders', 'QueryOrders', 'TradesHistory', 'QueryTrades', 'OpenPositions', 'Ledgers', 'QueryLedgers', 'TradeVolume', 'AddOrder', 'CancelOrder', 'DepositMethods', 'DepositAddresses', 'DepositStatus', 'WithdrawInfo', 'Withdraw', 'WithdrawStatus', 'WithdrawCancel' ],
};
// Default options
const defaults = {
url : 'https://api.kraken.com',
version : 0,
timeout : 5000,
};
// Create a signature for a request
const getMessageSignature = (path, request, secret, nonce) => {
const message = qs.stringify(request);
const secret_buffer = new Buffer(secret, 'base64');
const hash = new crypto.createHash('sha256');
const hmac = new crypto.createHmac('sha512', secret_buffer);
const hash_digest = hash.update(nonce + message).digest('binary');
const hmac_digest = hmac.update(path + hash_digest, 'binary').digest('base64');
return hmac_digest;
};
// Send an API request
const rawRequest = async (url, headers, data, timeout) => {
// Set custom User-Agent string
headers['User-Agent'] = 'Kraken Javascript API Client';
const options = { headers, timeout };
Object.assign(options, {
method : 'POST',
body : qs.stringify(data),
});
const { body } = await got(url, options);
const response = JSON.parse(body);
if(response.error && response.error.length) {
const error = response.error
.filter((e) => e.startsWith('E'))
.map((e) => e.substr(1));
if(!error.length) {
throw new Error("Kraken API returned an unknown error");
}
throw new Error(error.join(', '));
}
return response;
};
/**
* KrakenClient connects to the Kraken.com API
* @param {String} key API Key
* @param {String} secret API Secret
* @param {String} [otp] Two-factor password (optional) (also, doesn't work)
* @param {String} key API Key
* @param {String} secret API Secret
* @param {String|Object} [options={}] Additional options. If a string is passed, will default to just setting `options.otp`.
* @param {String} [options.otp] Two-factor password (optional) (also, doesn't work)
* @param {Number} [options.timeout] Maximum timeout (in milliseconds) for all API-calls (passed to `request`)
*/
function KrakenClient(key, secret, otp) {
var self = this;
class KrakenClient {
constructor(key, secret, options) {
// Allow passing the OTP as the third argument for backwards compatibility
if(typeof options === 'string') {
options = { otp : options };
}
var config = {
url: 'https://api.kraken.com',
version: '0',
key: key,
secret: secret,
otp: otp,
timeoutMS: 5000
};
this.config = Object.assign({ key, secret }, defaults, options);
}

@@ -30,13 +85,15 @@ /**

*/
function api(method, params, callback) {
var methods = {
public: ['Time', 'Assets', 'AssetPairs', 'Ticker', 'Depth', 'Trades', 'Spread', 'OHLC'],
private: ['Balance', 'TradeBalance', 'OpenOrders', 'ClosedOrders', 'QueryOrders', 'TradesHistory', 'QueryTrades', 'OpenPositions', 'Ledgers', 'QueryLedgers', 'TradeVolume', 'AddOrder', 'CancelOrder', 'DepositMethods', 'DepositAddresses', 'DepositStatus', 'WithdrawInfo', 'Withdraw', 'WithdrawStatus', 'WithdrawCancel']
};
if(methods.public.indexOf(method) !== -1) {
return publicMethod(method, params, callback);
api(method, params, callback) {
// Default params to empty object
if(typeof params === 'function') {
callback = params;
params = {};
}
else if(methods.private.indexOf(method) !== -1) {
return privateMethod(method, params, callback);
if(methods.public.includes(method)) {
return this.publicMethod(method, params, callback);
}
else if(methods.private.includes(method)) {
return this.privateMethod(method, params, callback);
}
else {

@@ -54,9 +111,22 @@ throw new Error(method + ' is not a valid API method.');

*/
function publicMethod(method, params, callback) {
publicMethod(method, params, callback) {
params = params || {};
var path = '/' + config.version + '/public/' + method;
var url = config.url + path;
// Default params to empty object
if(typeof params === 'function') {
callback = params;
params = {};
}
return rawRequest(url, {}, params, callback);
const path = '/' + this.config.version + '/public/' + method;
const url = this.config.url + path;
const response = rawRequest(url, {}, params, this.config.timeout);
if(typeof callback === 'function') {
response
.then((result) => callback(null, result))
.catch((error) => callback(error, null));
}
return response;
}

@@ -71,104 +141,46 @@

*/
function privateMethod(method, params, callback) {
privateMethod(method, params, callback) {
params = params || {};
var path = '/' + config.version + '/private/' + method;
var url = config.url + path;
// Default params to empty object
if(typeof params === 'function') {
callback = params;
params = {};
}
params.nonce = new Date() * 1000; // spoof microsecond
const path = '/' + this.config.version + '/private/' + method;
const url = this.config.url + path;
if(config.otp !== undefined) {
params.otp = config.otp;
if(!params.nonce) {
params.nonce = new Date() * 1000; // spoof microsecond
}
var signature = getMessageSignature(path, params, params.nonce);
if(this.config.otp !== undefined) {
params.otp = this.config.otp;
}
var headers = {
'API-Key': config.key,
'API-Sign': signature
};
const signature = getMessageSignature(
path,
params,
this.config.secret,
params.nonce
);
return rawRequest(url, headers, params, callback);
}
/**
* This method returns a signature for a request as a Base64-encoded string
* @param {String} path The relative URL path for the request
* @param {Object} request The POST body
* @param {Integer} nonce A unique, incrementing integer
* @return {String} The request signature
*/
function getMessageSignature(path, request, nonce) {
var message = querystring.stringify(request);
var secret = new Buffer(config.secret, 'base64');
var hash = new crypto.createHash('sha256');
var hmac = new crypto.createHmac('sha512', secret);
var hash_digest = hash.update(nonce + message).digest('binary');
var hmac_digest = hmac.update(path + hash_digest, 'binary').digest('base64');
return hmac_digest;
}
/**
* This method sends the actual HTTP request
* @param {String} url The URL to make the request
* @param {Object} headers Request headers
* @param {Object} params POST body
* @param {Function} callback A callback function to call when the request is complete
* @return {Object} The request object
*/
function rawRequest(url, headers, params, callback) {
// Set custom User-Agent string
headers['User-Agent'] = 'Kraken Javascript API Client';
var options = {
url: url,
method: 'POST',
headers: headers,
form: params,
timeout: config.timeoutMS
const headers = {
'API-Key' : this.config.key,
'API-Sign' : signature,
};
var req = request.post(options, function(error, response, body) {
if(typeof callback === 'function') {
var data;
const response = rawRequest(url, headers, params, this.config.timeout);
if(error) {
return callback.call(self, new Error('Error in server response: ' + JSON.stringify(error)), null);
}
if(typeof callback === 'function') {
response
.then((result) => callback(null, result))
.catch((error) => callback(error, null));
}
try {
data = JSON.parse(body);
}
catch(e) {
return callback.call(self, new Error('Could not understand response from server: ' + body), null);
}
//If any errors occured, Kraken will give back an array with error strings under
//the key "error". We should then propagate back the error message as a proper error.
if(data.error && data.error.length) {
var krakenError = null;
data.error.forEach(function(element) {
if (element.charAt(0) === "E") {
krakenError = element.substr(1);
return false;
}
});
if (krakenError) {
return callback.call(self, new Error('Kraken API returned error: ' + krakenError), null);
}
}
else {
return callback.call(self, null, data);
}
}
});
return req;
return response;
}
self.api = api;
self.publicMethod = publicMethod;
self.privateMethod = privateMethod;
}
module.exports = KrakenClient;
{
"name": "kraken-api",
"version": "0.1.7",
"version": "1.0.0",
"description": "kraken.com API client library for NodeJS",

@@ -12,8 +12,7 @@ "keywords": [

"author": "Robert Myers (https://github.com/nothingisdead)",
"contributors": [
],
"contributors": [],
"license": "MIT",
"dependencies": {
"querystring": ">=0.2.0",
"request": ">=2.27.0"
"got": "^7.1.0",
"qs": ">=6.4.0"
},

@@ -20,0 +19,0 @@ "repository": {

@@ -6,40 +6,33 @@ Node Kraken

This is an asynchronous node js client for the kraken.com API.
This is an asynchronous node js client for the kraken.com API. It exposes all the API methods found here: https://www.kraken.com/help/api through the ```api``` method:
It exposes all the API methods found here: https://www.kraken.com/help/api through the 'api' method:
Example Usage:
```javascript
var KrakenClient = require('kraken-api');
var kraken = new KrakenClient('api_key', 'api_secret');
const key = '...'; // API Key
const secret = '...'; // API Private Key
const KrakenClient = require('kraken-api');
const kraken = new KrakenClient(key, secret);
// Display user's balance
kraken.api('Balance', null, function(error, data) {
if(error) {
console.log(error);
}
else {
console.log(data.result);
}
});
(async () => {
// Display user's balance
console.log(await kraken.api('Balance'));
// Get Ticker Info
kraken.api('Ticker', {"pair": 'XBTCXLTC'}, function(error, data) {
if(error) {
console.log(error);
}
else {
console.log(data.result);
}
});
// Get Ticker Info
console.log(await kraken.api('Ticker', { pair : 'XXBTZUSD' }));
})();
```
**Update:**
**Updates:**
As of version 0.1.0, the callback passed to the *api* function conforms to the Node.js standard of
As of version 1.0.0:
- All methods return a promise.
- The second argument (parameters) can be omitted.
- The third argument to the constructor can be an object (configuration) or a string (OTP), for backwards compatibility.
As of version 0.1.0, the callback passed to the ```api``` function conforms to the Node.js standard of
```javascript
function(error, data) {
// ...
// ...
}

@@ -52,7 +45,4 @@ ```

I used the example php implementation at https://github.com/payward/kraken-api-client and the python implementation at https://github.com/veox/krakenex as references.
I used the example php implementation at https://github.com/payward/kraken-api-client and the python implementation at https://github.com/veox/python3-krakenex as references.
Feeling generous? Send me a fraction of a bitcoin!
12X8GyUpfYxEP7sh1QaU4ngWYpzXJByQn5
BTC donation address: 12X8GyUpfYxEP7sh1QaU4ngWYpzXJByQn5
SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc