NAV
Example

Python Quick Start

1. Using The SDK

A lightweight code library that includes HTTP requests for all BitMart API interfaces and subscription to websocket public and private channels. Clone it and use it in your code. This SDK is specifically designed for Python developers.

Usage:

from bitmart.api_spot import APISpot

if __name__ == '__main__':

    api_key = "Your API KEY"
    secret_key = "Your Secret KEY"
    memo = "Your Memo"

    spotAPI = APISpot(api_key, secret_key, memo, timeout=(3, 10))

    ## Place Spot Order
    spotAPI.post_submit_limit_buy_order('BTC_USDT', size='0.01', price='8800')

2. Simple API Example

If you prefer not to use the SDK and want to implement the API requests yourself, you can refer to the example below:

Implementation of Spot Order API

The example includes the correct method for generating a signature, which is applicable to all BitMart APIs in this document.

Usage:

import json
import requests
import time
import hashlib
import hmac

API_KEY = 'your_api_key'
API_SECRET = 'your_api_secret'
API_MEMO = 'your_api_memo'

BASE_URL = 'https://api-cloud.bitmart.com'


# Get current timestamp
def get_timestamp():
    return str(int(time.time() * 1000))


# Generate signature
def generate_signature(timestamp, body):
    message = f'{str(timestamp)}#{API_MEMO}#{body}'
    return hmac.new(API_SECRET.encode(), message.encode(), hashlib.sha256).hexdigest()


# Set key and sign
def generate_header(body):
    timestamp = get_timestamp()
    return {
        'Content-Type': 'application/json',
        'X-BM-KEY': API_KEY,
        'X-BM-TIMESTAMP': timestamp,
        'X-BM-SIGN': generate_signature(timestamp, str(json.dumps(body)))
    }


# Place order
def place_order():
    path = '/spot/v2/submit_order'
    body = {
        'size': '100',
        'price': '500000',
        'side': 'sell',
        'symbol': 'BTC_USDT',
        'type': 'limit'
    }
    url = BASE_URL + path
    response = requests.post(url, headers=generate_header(body), json=body)
    if response.status_code == 200:
        print(response.json())
    else:
        print('Error: {}'.format(response.text))


if __name__ == '__main__':
    place_order()


3. Simple Websocket Example

Spot Public Channel Subscription

The example includes the correct method for decompressing data, which is applicable to all BitMart Spot Websockets in this document.

Usage:

import websocket
import zlib

class sample_socket_client(object):
    def __init__(self, url, params , on_message):
        self.ws = None
        self.url = url
        self.params = params
        self.on_message = on_message
        self.connection()

    def connection(self):
        self.ws = websocket.WebSocketApp(url=self.url, on_message=self.on_message,
                                         on_open=self.on_open, on_error=self.on_error, on_close=self.on_close)
        self.ws.run_forever(ping_interval=10, ping_timeout=1, ping_payload='ping')

    def on_error(self, ws, error):
        print("{}on_error:{}".format(ws, error))

    def on_close(self, ws, close_status_code, close_msg):
        self.connection()

    def on_open(self, ws):
        ws.send(self.params)


# decompress data
def inflate(data):
    decompress = zlib.decompressobj(
        -zlib.MAX_WBITS
    )
    inflated = decompress.decompress(data)
    inflated += decompress.flush()
    return inflated.decode('UTF-8')


# on message
def on_message(ws, message):
    if type(message) == bytes:
        response = inflate(message)
    else:
        response = message
    print("Received message: " + response)


if __name__ == '__main__':
    sample_socket_client("wss://ws-manager-compress.bitmart.com/api?protocol=1.1", '{"op": "subscribe", "args": ["spot/ticker:BTC_USDT"]}', on_message)

Spot Private Channel Subscription

The example includes the correct methods for decompressing data and logging in, which are applicable to all BitMart Spot Websockets in this document.

Usage:

import websocket
import time
import hashlib
import hmac
import json
import zlib

API_KEY = 'your_api_key'
API_SECRET = 'your_api_secret'
API_MEMO = 'your_api_memo'


class sample_socket_client(object):
    def __init__(self, url, login_message, params , on_message):
        self.ws = None
        self.url = url
        self.login_message = login_message
        self.params = params
        self.on_message = on_message
        self.connection()

    def connection(self):
        self.ws = websocket.WebSocketApp(url=self.url, on_message=self.on_message,
                                         on_open=self.on_open, on_error=self.on_error, on_close=self.on_close)
        self.ws.run_forever(ping_interval=10, ping_timeout=1, ping_payload='ping')

    def on_error(self, ws, error):
        print("{}on_error:{}".format(ws, error))

    def on_close(self, ws, close_status_code, close_msg):
        self.connection()

    def on_open(self, ws):
        if self.login_message:
            ws.send(self.login_message)

        time.sleep(3)
        ws.send(self.params)


# decompress data
def inflate(data):
    decompress = zlib.decompressobj(
        -zlib.MAX_WBITS
    )
    inflated = decompress.decompress(data)
    inflated += decompress.flush()
    return inflated.decode('UTF-8')


# on message
def on_message(ws, message):
    if type(message) == bytes:
        response = inflate(message)
    else:
        response = message
    print("Received message: " + response)


if __name__ == '__main__':
    timestamp = str(int(time.time() * 1000))
    message = f'{timestamp}#{API_MEMO}#bitmart.WebSocket'
    sign = hmac.new(API_SECRET.encode(), message.encode(), hashlib.sha256).hexdigest()

    # send login message
    login_message = json.dumps({
        'op': 'login',
        'args': [API_KEY, timestamp, sign]
    })

    subscription_message =  json.dumps({
        'op': 'subscribe',
        'args': ['spot/user/order:BTC_USDT']
    })

    sample_socket_client("wss://ws-manager-compress.bitmart.com/user?protocol=1.1",
                         login_message, subscription_message, on_message)

Golang Quick Start

1. Using The SDK

BitMart provides a lightweight code library in Golang that includes HTTP requests for all API endpoints and subscription to both public and private WebSocket channels. You can clone the library and start using it. It is specifically designed for Golang developers.

Usage:

package gotest

import (
    "github.com/bitmartexchange/bitmart-go-sdk-api"
    "log"
)

func main() {

    client := bitmart.NewClient(bitmart.Config{
        Url:"https://api-cloud.bitmart.com", // Ues Https url
        ApiKey:"Your API KEY",
        SecretKey:"Your Secret KEY",
        Memo:"Your Memo",
        TimeoutSecond:10,
        IsPrint:true,
    })

    var ac, err = client.PostSpotSubmitOrder(bitmart.Order{Symbol: TEST_SYMBOL, Side: "buy", Type: "limit", Size: "0.1", Price: "8800", Notional: ""})
    if err != nil {
        log.Panic(err)
    } else {
        bitmart.PrintResponse(ac)
    }

}

2. Simple API Example

If you prefer not to use the SDK and want to implement the API requests yourself, you can refer to the example below:

Implementation of Spot Order API

The example includes the correct method for generating signatures, which is applicable to all BitMart APIs in this document.

Usage:

package main

import (
    "bytes"
    "crypto/hmac"
    "crypto/sha256"
    "encoding/json"
    "fmt"
    "io/ioutil"
    "net/http"
    "strconv"
    "time"
)

const (
    apiKey    = "your_api_key"
    apiSecret = "your_api_secret"
    apiMemo   = "your_api_memo"
    baseURL   = "https://api-cloud.bitmart.com"
)

type OrderParams struct {
    Size   string `json:"size"`
    Price  string `json:"price"`
    Side   string `json:"side"`
    Symbol string `json:"symbol"`
    Type   string `json:"type"`
}

// Get current timestamp
func getTimestamp() int64 {
    return time.Now().UnixNano() / int64(time.Millisecond)
}

// Generate signature
func generateSignature(timestamp int64, body string) string {
    message := fmt.Sprintf("%d#%s#%s", timestamp, apiMemo, body)
    h := hmac.New(sha256.New, []byte(apiSecret))
    h.Write([]byte(message))
    return fmt.Sprintf("%x", h.Sum(nil))
}

// Place order
func main() {
    path := "/spot/v2/submit_order"
    method := "POST"
    timestamp := getTimestamp()
    orderParams := OrderParams{
        Size:   "100",
        Price:  "500000",
        Side:   "sell",
        Symbol: "BTC_USDT",
        Type:   "limit",
    }
    orderParamsJSON, _ := json.Marshal(orderParams)
    body := string(orderParamsJSON)

    signature := generateSignature(timestamp, body)

    req, _ := http.NewRequest(method, baseURL+path, bytes.NewReader(orderParamsJSON))
    req.Header.Add("Content-Type", "application/json")
    req.Header.Add("X-BM-KEY", apiKey)
    req.Header.Add("X-BM-TIMESTAMP", strconv.FormatInt(timestamp, 10))
    req.Header.Add("X-BM-SIGN", signature)

    client := &http.Client{}
    res, err := client.Do(req)
    if err != nil {
        fmt.Println("Error:", err)
        return
    }
    defer res.Body.Close()

    bodyBytes, err := ioutil.ReadAll(res.Body)
    if err != nil {
        fmt.Println("Error:", err)
        return
    }
    bodyString := string(bodyBytes)

    if res.StatusCode == 200 {
        fmt.Println(bodyString)
    } else {
        fmt.Println("Error:", bodyString)
    }
}

3. Simple Websocket Example

Not yet, please wait

Nodejs Quick Start

1. Using The SDK

SDK is currently not available.

2. Simple API Example

If you prefer not to use the SDK and want to implement the API requests yourself, you can refer to the example below:

Implementation of Spot Order API

The example includes the correct method for generating a signature, which is applicable to all BitMart APIs in this document.

Usage:

const axios = require('axios');
const crypto = require('crypto');

const API_KEY = 'your_api_key';
const API_SECRET = 'your_api_secret';
const API_MEMO = 'your_api_memo';

const BASE_URL = 'https://api-cloud.bitmart.com';

// Get current timestamp
function get_timestamp() {
    return new Date().getTime().toString();
}

// Generate signature
function generate_signature(timestamp, body) {
    const message = `${timestamp}#${API_MEMO}#${body}`;
    return crypto.createHmac('sha256', API_SECRET).update(message).digest('hex');
}

// Place order
async function place_order() {
    const path = '/spot/v2/submit_order';
    const timestamp = get_timestamp();
    const body = {
        size: 100,
        price: 50000,
        side: 'sell',
        symbol: 'BTC_USDT',
        type: 'limit',
    };
    const headers = {
        'Content-Type': 'application/json',
        'X-BM-KEY': API_KEY,
        'X-BM-TIMESTAMP': timestamp,
        'X-BM-SIGN': generate_signature(timestamp, JSON.stringify(body)),
    };
    const url = BASE_URL + path;
    try {
        const response = await axios.post(url, body, { headers });
        console.log(response.data);
    } catch (error) {
        console.error(`Error:`);
        console.error(error.response.data);
    }
}

place_order();

3. Simple Websocket Example

Spot Public Channel Subscription Implementation

The example includes the correct methods for decompressing data, which are applicable to all BitMart Spot WebSockets in this document.

Usage:

const WebSocket = require('ws')
const zlib = require('zlib');
const pako = require('pako');

const heartbeatInterval = 10 * 1000;  // Just send it every 10 seconds.

const ws = new WebSocket(
    'wss://ws-manager-compress.bitmart.com/api?protocol=1.1'
)

ws.on('open', function open() {
    reconnect();
})

ws.on('close', function open() {
    reconnect();
})

ws.on('error', function (error) {
    console.error(error)
})



ws.on('message', function incoming(data) {
    if(data.toString() === 'pong') {
        return
    }

    if (!data.toString().startsWith("{")) {
        // const decompressedData = decompressedByPako(data);
        const decompressedData = decompressedByZlib(data);
        console.log("Received buffer message:" + decompressedData)
    } else {
        console.log('Received text message:', data.toString());
    }

})

function decompressedByPako(data) {
    return pako.inflateRaw(data, { to: 'string' });
}

function decompressedByZlib(data) {
    return zlib.inflateRawSync(data);
}

function reconnect() {
    ws.send(JSON.stringify({"op": "subscribe", "args": ["spot/ticker:BTC_USDT"]}))
    startHeartbeat();
}

function startHeartbeat() {
    setInterval(() => {
        if (ws.readyState === WebSocket.OPEN) {
            ws.send('ping');
        }
    }, heartbeatInterval);
}

Spot Private Channel Subscription Implementation

The example includes the correct methods for decompressing data and logging in, which are applicable to all BitMart Spot WebSockets in this document.

Usage:

const WebSocket = require('ws')
const crypto = require('crypto')
const zlib = require('zlib');
const pako = require('pako');


const API_KEY = 'your_api_key';
const API_SECRET = 'your_api_secret';
const API_MEMO = 'your_api_memo';

const timestamp = Date.now()

const message = `${timestamp}#${API_MEMO}#bitmart.WebSocket`

const sign = crypto
    .createHmac('sha256', API_SECRET)
    .update(message)
    .digest('hex')
    .toString();

const heartbeatInterval = 10 * 1000;  // Just send it every 10 seconds.


const ws = new WebSocket(
    'wss://ws-manager-compress.bitmart.com/user?protocol=1.1'
)

ws.on('open', function open() {
    reconnect()
})

ws.on('close', function open() {
    reconnect();
})

ws.on('error', function (error) {
    console.error(error)
})

ws.on('message', function incoming(data) {
    if(data.toString() === 'pong') {
        return
    }

    if (!data.toString().startsWith("{")) {
        const decompressedData = decompressedByPako(data);
        // const decompressedData = decompressedByZlib(data);
        console.log("Received buffer message:" + decompressedData)

    } else {
        console.log('Received text message:', data.toString());
    }

})

function decompressedByPako(data) {
    return pako.inflateRaw(data, { to: 'string' });
}

function decompressedByZlib(data) {
    return zlib.inflateRawSync(data);
}

function reconnect() {
    // send login message
    const loginMessage = {
        op: 'login',
        args: [API_KEY, timestamp, sign],
    }
    ws.send(JSON.stringify(loginMessage))

    // create subscription message
    setTimeout(function(){
        ws.send(JSON.stringify({"op": "subscribe", "args": ["spot/user/order:BTC_USDT"]}))
        console.log("send subscription")
    },2000);

    startHeartbeat();
}


function startHeartbeat() {
    setInterval(() => {
        if (ws.readyState === WebSocket.OPEN) {
            ws.send('ping');
        }
    }, heartbeatInterval);
}

Java Quick Start

1. Using The SDK

BitMart provides a lightweight code library in Java that includes HTTP requests for all API endpoints and subscription to both public and private WebSocket channels. You can clone the library and start using it. It is specifically designed for Java developers.

Usage:

import com.bitmart.api.Call;
import com.bitmart.api.CloudContext;
import com.bitmart.api.request.spot.prv.*;

public class TestSpot {

    private static String API_KEY = "YOUR ACCESS KEY";
    private static String API_SECRET = "YOUR SECRET KEY";
    private static String API_MEMO = "YOUR MEMO";
    private static Call call;

     public static void main(String[] args) {
        CloudContext cloudContext = new CloudContext(new CloudKey(API_KEY, API_SECRET, API_MEMO));
        call = new Call(cloudContext);

        System.out.println(
                call.callCloud(new SubmitOrderRequest()
                        .setSide("sell")
                        .setType("limit")
                        .setSymbol("BTC_USDT")
                        .setPrice("80000")
                        .setSize("100"))
        );
    }

}

2. Simple API Example

If you prefer not to use the SDK and want to implement the API requests yourself, you can refer to the example below:

Implementation of Spot Order API

The example includes the correct method for generating a signature, which is applicable to all BitMart APIs in this document.

Usage:

    <dependencies>
        <dependency>
            <groupId>javax.servlet</groupId>
            <artifactId>javax.servlet-api</artifactId>
            <version>4.0.1</version>
            <scope>provided</scope>
        </dependency>
        <dependency>
            <groupId>com.squareup.okhttp3</groupId>
            <artifactId>okhttp</artifactId>
            <version>4.9.1</version>
        </dependency>
        <dependency>
            <groupId>com.fasterxml.jackson.core</groupId>
            <artifactId>jackson-databind</artifactId>
            <version>2.13.4</version>
        </dependency>
        <dependency>
            <groupId>commons-codec</groupId>
            <artifactId>commons-codec</artifactId>
            <version>1.15</version>
        </dependency>
    </dependencies>

package com.bitmart.demo;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import okhttp3.*;
import org.apache.commons.codec.binary.Hex;

import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;
import java.io.IOException;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import java.time.Instant;
import java.time.temporal.ChronoUnit;
import java.util.HashMap;
import java.util.Map;

public class BitmartAPI {
    private static final String BASE_URL = "https://api-cloud.bitmart.com";
    private static final String API_KEY = "your_api_key";
    private static final String API_SECRET = "your_api_secret";
    private static final String API_MEMO = "your_api_memo";

    private static final String SYMBOL = "BTC_USDT";
    private static final String SIZE = "100";
    private static final String PRICE = "500000";
    private static final String SIDE = "sell";
    private static final String TYPE = "limit";
    private static final String MEDIA_TYPE_JSON = "application/json; charset=utf-8";

    private static final OkHttpClient httpClient = new OkHttpClient();

    public static void main(String[] args) throws NoSuchAlgorithmException, InvalidKeyException, JsonProcessingException {
        placeOrder();
    }

    private static String getTimestamp() {
        return Long.toString(Instant.now().truncatedTo(ChronoUnit.MILLIS).toEpochMilli());
    }

    private static String generateSignature(String timestamp, String body)
            throws NoSuchAlgorithmException, InvalidKeyException {
        String message = timestamp + "#" + API_MEMO + "#" + body;
        Mac mac = Mac.getInstance("HmacSHA256");
        mac.init(new SecretKeySpec(API_SECRET.getBytes(), "HmacSHA256"));
        return Hex.encodeHexString(mac.doFinal(message.getBytes()));
    }

    private static void placeOrder() throws JsonProcessingException, InvalidKeyException, NoSuchAlgorithmException {
        String timestamp = getTimestamp();
        String path = "/spot/v2/submit_order";
        String url = BASE_URL + path;

        ObjectMapper mapper = new ObjectMapper();
        Map<String, String> order = new HashMap<>();
        order.put("symbol", SYMBOL);
        order.put("type", TYPE);
        order.put("side", SIDE);
        order.put("size", SIZE);
        order.put("price", PRICE);
        String body = mapper.writeValueAsString(order);
        String signature = generateSignature(timestamp, body);
        Map<String, String> headers = new HashMap<>();
        headers.put("Content-Type", MEDIA_TYPE_JSON);
        headers.put("X-BM-KEY", API_KEY);
        headers.put("X-BM-TIMESTAMP", timestamp);
        headers.put("X-BM-SIGN", signature);
        RequestBody requestBody = RequestBody.create(body, MediaType.parse(MEDIA_TYPE_JSON));
        Request request = new Request.Builder()
                .url(url)
                .headers(okhttp3.Headers.of(headers))
                .post(requestBody)
                .build();
        try (Response response = httpClient.newCall(request).execute()) {
            if (response.isSuccessful()) {
                System.out.println(response.body().string());
            } else {
                System.err.println("Error: " + response.body().string());
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

3. Simple Websocket Example

Not yet, please wait

PHP Quick Start

1. Using The SDK

The SDK provided by BitMart is a lightweight code library specifically designed for PHP developers. It includes HTTP requests for all BitMart API interfaces and subscription for both public and private WebSocket channels.

Usage:

<?php

namespace Tests;

use BitMart\APISpot;
use BitMart\CloudConfig;

class APISpotClient
{
    protected $APISpot;

    protected function __construct()
    {
        $this->APISpot = new APISpot(new CloudConfig(
            CloudConst::WS_URL_PRO, // Use Https Url: "https://api-cloud.bitmart.com"
            "Your Access Key",
            "Your Secret Key",
            "Your Memo"
        ));
    }

    public function testPostSubmitOrderLimitBuy()
    {
         $this->APISpot->postSubmitOrderLimitBuy(
            'BTC_USDT',
            '0.01',
            '90'
        )['response']->code;
    }

}

2. Simple API Example

If you prefer not to use the SDK and want to implement the API requests yourself, you can refer to the example below:

Implementation of Spot Order API

The example includes the correct method for generating a signature, which is applicable to all BitMart APIs in this document.

Usage:

<?php

$API_KEY = 'your_api_key';
$API_SECRET = 'your_api_secret';
$API_MEMO = 'your_api_memo';


$BASE_URL = 'https://api-cloud.bitmart.com';
$SYMBOL = 'BTC_USDT';
$SIZE = '100';
$PRICE = '500000';
$SIDE = 'sell';
$TYPE = 'limit';

// Get current timestamp
function get_timestamp() {
    return strval(round(microtime(true) * 1000));
}

// Generate signature
function generate_signature($timestamp, $body) {
    $message = $timestamp . '#' . $GLOBALS['API_MEMO'] . '#' . $body;
    return hash_hmac('sha256', $message, $GLOBALS['API_SECRET']);
}

// Place order
function place_order() {
    $path = '/spot/v2/submit_order';
    $timestamp = get_timestamp();
    $body = json_encode(array(
        'size' => $GLOBALS['SIZE'],
        'price' => $GLOBALS['PRICE'],
        'side' => $GLOBALS['SIDE'],
        'symbol' => $GLOBALS['SYMBOL'],
        'type' => $GLOBALS['TYPE']
    ));
    $headers = array(
        'Content-Type: application/json',
        'X-BM-KEY: ' . $GLOBALS['API_KEY'],
        'X-BM-TIMESTAMP: ' . $timestamp,
        'X-BM-SIGN: ' . generate_signature($timestamp, $body)
    );
    $url = $GLOBALS['BASE_URL'] . $path;
    $ch = curl_init($url);
    curl_setopt($ch, CURLOPT_POST, 1);
    curl_setopt($ch, CURLOPT_POSTFIELDS, $body);
    curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
    $response = curl_exec($ch);
    curl_close($ch);
    if ($response) {
        $response_json = json_decode($response, true);
        print_r($response_json);
    } else {
        echo 'Error: ' . curl_error($ch);
    }
}

place_order();

?>

3. Simple Websocket Example

Not yet, please wait

Javascript Quick Start

1. Simple API Example

The example includes the correct method for generating a signature, which is applicable to all BitMart APIs in this document.

Usage:

<script src="https://cdnjs.cloudflare.com/ajax/libs/crypto-js/4.1.1/crypto-js.min.js"></script>
<script src="https://code.jquery.com/jquery-3.6.0.min.js"></script>

<script>

const API_KEY = 'your_api_key';
const API_SECRET = 'your_api_secret';
const API_MEMO = 'your_api_memo';

const BASE_URL = 'https://api-cloud.bitmart.com';
const SYMBOL = 'BTC_USDT';
const SIZE = '100';
const PRICE = '500000';
const SIDE = 'sell';
const TYPE = 'limit';

// Get current timestamp
function getTimestamp() {
    return Date.now();
}

// Generate signature
function generateSignature(timestamp, body) {
    const message = `${timestamp}#${API_MEMO}#${body}`;
    const signature = CryptoJS.HmacSHA256(message, API_SECRET);
    return signature.toString(CryptoJS.enc.Hex);
}

// Place order
function placeOrder() {
    const path = '/spot/v2/submit_order';
    const timestamp = getTimestamp();
    const body = JSON.stringify({
        size: SIZE,
        price: PRICE,
        side: SIDE,
        symbol: SYMBOL,
        type: TYPE,
    });
    const headers = {
        'Content-Type': 'application/json',
        'X-BM-KEY': API_KEY,
        'X-BM-TIMESTAMP': timestamp,
        'X-BM-SIGN': generateSignature(timestamp, body),
    };
    const url = BASE_URL + path;
    $.ajax({
        type: 'POST',
        url: url,
        headers: headers,
        data: body,
        success: function (response) {
            console.log(response);
        },
        error: function (xhr, status, error) {
            console.log('Error: ' + xhr.responseText);
        },
    });
}

placeOrder();

</script>

Ruby Quick Start

1. Simple API Example

The example includes the correct method for generating a signature, which is applicable to all BitMart APIs in this document.

Usage:

require 'json'
require 'openssl'
require 'net/http'

API_KEY = 'your_api_key'
API_SECRET = 'your_api_secret'
API_MEMO = 'your_api_memo'

BASE_URL = 'https://api-cloud.bitmart.com'

def get_timestamp()
  (Time.now.to_f * 1000).to_i.to_s
end

def generate_signature(timestamp, body)
  message = "#{timestamp}##{API_MEMO}##{body}"
  OpenSSL::HMAC.hexdigest('sha256', API_SECRET, message)
end

def generate_header(body)
  timestamp = get_timestamp
  {
      'Content-Type' => 'application/json',
      'X-BM-KEY' => API_KEY,
      'X-BM-TIMESTAMP' => timestamp,
      'X-BM-SIGN' => generate_signature(timestamp, body.to_json)
  }
end

def place_order()
  path = '/spot/v2/submit_order'
  body = {
      'size': '100',
      'price': '500000',
      'side': 'sell',
      'symbol': 'BTC_USDT',
      'type': 'limit'
  }
  url = URI.parse(BASE_URL + path)
  req = Net::HTTP::Post.new(url)
  req.body = body.to_json
  req.initialize_http_header(generate_header(body))
  res = Net::HTTP.start(url.host, url.port, use_ssl: true) do |http|
    http.request(req)
  end

  if res.code.to_i == 200
    puts JSON.parse(res.body)
  else
    puts "Error: #{res.body}"
  end
end

if __FILE__ == $0
  place_order()
end

C# Quick Start

1. Simple API Example

The example includes the correct method for generating a signature, which is applicable to all BitMart APIs in this document.

Usage:

using System;
using System.Net.Http;
using System.Security.Cryptography;
using System.Text;
using System.Text.Json;
using System.Threading.Tasks;

namespace BitMartAPI
{
    class Program
    {
        const string API_KEY = "your_api_key";
        const string API_SECRET = "your_api_secret";
        const string API_MEMO = "your_api_memo";
        const string BASE_URL = "https://api-cloud.bitmart.com";

        static async Task Main(string[] args)
        {
            await PlaceOrderAsync();
        }

        // Get current timestamp
        static string GetTimestamp()
        {
            return DateTimeOffset.Now.ToUnixTimeMilliseconds().ToString();
        }

        // Gennerate sign
        static string GenerateSignature(string timestamp, string body)
        {
            string message = $"{timestamp}#{API_MEMO}#{body}";
            using HMACSHA256 hmac = new HMACSHA256(Encoding.UTF8.GetBytes(API_SECRET));
            byte[] hash = hmac.ComputeHash(Encoding.UTF8.GetBytes(message));
            return BitConverter.ToString(hash).Replace("-", "").ToLower();
        }

        // Place spot order
        static async Task PlaceOrderAsync()
        {
            string path = "/spot/v2/submit_order";
            var body = new
            {
                size = "100",
                price = "500000",
                side = "sell",
                symbol = "BTC_USDT",
                type = "limit"
            };
            string url = BASE_URL + path;
            string requestBody = JsonSerializer.Serialize(body);
            string timestamp = GetTimestamp();
            string signature = GenerateSignature(timestamp, requestBody);
            var request = new HttpRequestMessage(HttpMethod.Post, url);
            request.Content = new StringContent(requestBody, Encoding.UTF8, "application/json");
            request.Headers.Add("X-BM-KEY", API_KEY);
            request.Headers.Add("X-BM-TIMESTAMP", timestamp);
            request.Headers.Add("X-BM-SIGN", signature);
            using var httpClient = new HttpClient();
            HttpResponseMessage response = await httpClient.SendAsync(request);
            string responseBody = await response.Content.ReadAsStringAsync();
            if (response.IsSuccessStatusCode)
            {
                Console.WriteLine(responseBody);
            }
            else
            {
                Console.WriteLine($"Error: {responseBody}");
            }
        }
    }
}

Rust Quick Start

1. Simple API Example

# cargo.toml
[dependencies]
tokio = {version = "1", features = ["full"]}
reqwest = { version = "0.11.17", features = ["json"]}
serde_json = { version = "1.0.96" }
sha2 = "0.10.6"
hmac = "0.12.1"
hex = "0.4.3"

The example includes the correct method for generating a signature, which is applicable to all BitMart APIs in this document.

Usage:

use reqwest::header::{HeaderMap, CONTENT_TYPE};
use serde_json::json;
use std::time::{SystemTime, UNIX_EPOCH};
use sha2::{Sha256};
use hmac::{Hmac, Mac};
use hex;

type HmacSha256 = Hmac<Sha256>;

const API_KEY: &str = "your_api_key";
const API_SECRET: &str = "your_api_secret";
const API_MEMO: &str = "your_api_memo";
const BASE_URL: &str = "https://api-cloud.bitmart.com";

// Get current timestamp
fn get_timestamp() -> String {
    let since_epoch = SystemTime::now().duration_since(UNIX_EPOCH).expect("Time went backwards");
    since_epoch.as_millis().to_string()
}

// Generate signature
fn generate_signature(timestamp: &str, body: &str) -> String {
    let mut hmac = HmacSha256::new_from_slice(API_SECRET.as_bytes()).expect("HMAC error");
    let message = format!("{}#{}#{}", timestamp, API_MEMO, body);
    hmac.update(message.as_bytes());
    let result = hmac.finalize();
    hex::encode(result.into_bytes())
}

// Set key and sign
fn generate_header(body: &serde_json::Value) -> HeaderMap {
    let timestamp = get_timestamp();
    let signature = generate_signature(&timestamp, &body.to_string());
    let mut headers = HeaderMap::new();
    headers.insert(CONTENT_TYPE, "application/json".parse().unwrap());
    headers.insert("X-BM-KEY", API_KEY.parse().unwrap());
    headers.insert("X-BM-TIMESTAMP", timestamp.parse().unwrap());
    headers.insert("X-BM-SIGN", signature.parse().unwrap());
    headers
}

// Place order
#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
    let path = "/spot/v2/submit_order";
    let body = json!({
        "size": "100",
        "price": "500000",
        "side": "sell",
        "symbol": "BTC_USDT",
        "type": "limit"
    });
    let url = format!("{}{}", BASE_URL, path);
    let response = reqwest::Client::new()
        .post(&url)
        .headers(generate_header(&body))
        .json(&body)
        .send()
        .await?;

    if response.status().is_success() {
        let data = response.json::<serde_json::Value>().await?;
        println!("{:#?}", data);

        if data["code"].as_u64() == Some(1000) {
            println!("Success");
        } else {
            println!("Fail Reason:{:#?}", data["message"].as_str());
        }
    } else {
        println!("Error: {}", response.text().await?);
    }

    Ok(())
}

C++ Quick Start

1. Simple API Example

The example includes the correct method for generating a signature, which is applicable to all BitMart APIs in this document.

Usage:

#include <iostream>
#include <string>
#include <chrono>
#include <ctime>
#include <sstream>
#include <iomanip>
#include <openssl/hmac.h>
#include <curl/curl.h>
#include <nlohmann/json.hpp>



using namespace std;
using namespace std::chrono;
using json = nlohmann::json;

string API_KEY = "your_api_key";
string API_SECRET = "your_api_secret";
string API_MEMO = "your_api_memo";


string BASE_URL = "https://api-cloud.bitmart.com";

string get_timestamp() {
    auto now = time_point_cast<milliseconds>(system_clock::now());
    auto value = now.time_since_epoch().count();
    return to_string(value);
}

string generate_signature(string timestamp, string body) {
    string message = timestamp + "#" + API_MEMO + "#" + body;
    unsigned char* digest = HMAC(EVP_sha256(), API_SECRET.c_str(), API_SECRET.size(), (unsigned char*)message.c_str(), message.size(), NULL, NULL);
    stringstream ss;
    for(int i = 0; i < 32; i++) {
        ss << hex << setfill('0') << setw(2) << (int)digest[i];
    }
    return ss.str();
}

size_t curl_callback(char* ptr, size_t size, size_t nmemb, string* stream) {
    size_t bytes = size * nmemb;
    stream->append(ptr, bytes);
    return bytes;
}

void place_order() {
    string path = "/spot/v2/submit_order";
    json body = {
        {"size", "100"},
        {"price", "500000"},
        {"side", "sell"},
        {"symbol", "BTC_USDT"},
        {"type", "limit"}
    };
    string url = BASE_URL + path;
    CURL* curl = curl_easy_init();
    if (curl)
    {
        string timestamp = get_timestamp();
        string signature = generate_signature(timestamp, body.dump().c_str());

        struct curl_slist* headers = NULL;
        headers = curl_slist_append(headers, "Content-Type: application/json");
        headers = curl_slist_append(headers, ("X-BM-KEY: " + API_KEY).c_str());
        headers = curl_slist_append(headers, ("X-BM-TIMESTAMP: " + timestamp).c_str());
        headers = curl_slist_append(headers, ("X-BM-SIGN: " + signature).c_str());
        curl_easy_setopt(curl, CURLOPT_HTTPHEADER, headers);
        curl_easy_setopt(curl, CURLOPT_URL, url.c_str());
        curl_easy_setopt(curl, CURLOPT_CUSTOMREQUEST, "POST");
        curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1L);
        curl_easy_setopt(curl, CURLOPT_DEFAULT_PROTOCOL, "https");
        curl_easy_setopt(curl, CURLOPT_POSTFIELDSIZE, body.dump().size());
        curl_easy_setopt(curl, CURLOPT_POSTFIELDS, strdup(body.dump().c_str()));
        curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, curl_callback);
        curl_easy_setopt(curl, CURLOPT_CONNECTTIMEOUT, 6);
        curl_easy_setopt(curl, CURLOPT_TIMEOUT, 6);
        string response;
        curl_easy_setopt(curl, CURLOPT_WRITEDATA, &response);
        CURLcode res = curl_easy_perform(curl);

        if(res == CURLE_OK) {
            json j = json::parse(response);
            cout << "resp: " << j.dump(4) << endl;
        } else {
            cerr << "Error: " << response << endl;
            cerr << "Error: " << curl_easy_strerror(res) << endl;
        }

        curl_easy_cleanup(curl);
    }

    curl_global_cleanup();

}

int main() {
    place_order();
    return 0;
}

Postman Quick Experience

Now you can quickly experience and use the API interface through BitMart Postman