From 06b1b3f1c1ee6abdf5deea2210876ec0c7930f1e Mon Sep 17 00:00:00 2001 From: rizer1980 <4340180@gmail.com> Date: Wed, 10 Apr 2024 17:27:18 +0300 Subject: [PATCH] fix bybit futures error "symbol invalid" --- .../xchange/bybit/BybitAuthenticated.java | 27 ++---- .../dto/trade/BybitPlaceOrderPayload.java | 37 ++++++++ .../bybit/service/BybitTradeServiceRaw.java | 28 ++---- .../org/knowm/xchange/bybit/TradeExample.java | 94 +++++++++++++++++++ xchange-bybit/src/test/resources/logback.xml | 2 +- 5 files changed, 149 insertions(+), 39 deletions(-) create mode 100644 xchange-bybit/src/main/java/org/knowm/xchange/bybit/dto/trade/BybitPlaceOrderPayload.java create mode 100644 xchange-bybit/src/test/java/org/knowm/xchange/bybit/TradeExample.java diff --git a/xchange-bybit/src/main/java/org/knowm/xchange/bybit/BybitAuthenticated.java b/xchange-bybit/src/main/java/org/knowm/xchange/bybit/BybitAuthenticated.java index 9b39862e6ed..16fb0dea3d8 100644 --- a/xchange-bybit/src/main/java/org/knowm/xchange/bybit/BybitAuthenticated.java +++ b/xchange-bybit/src/main/java/org/knowm/xchange/bybit/BybitAuthenticated.java @@ -4,7 +4,7 @@ import static org.knowm.xchange.bybit.service.BybitDigest.X_BAPI_SIGN; import static org.knowm.xchange.bybit.service.BybitDigest.X_BAPI_TIMESTAMP; -import jakarta.ws.rs.FormParam; +import jakarta.ws.rs.Consumes; import jakarta.ws.rs.GET; import jakarta.ws.rs.HeaderParam; import jakarta.ws.rs.POST; @@ -13,7 +13,7 @@ import jakarta.ws.rs.QueryParam; import jakarta.ws.rs.core.MediaType; import java.io.IOException; -import java.math.BigDecimal; +import org.knowm.xchange.bybit.dto.trade.BybitPlaceOrderPayload; import org.knowm.xchange.bybit.dto.BybitResult; import org.knowm.xchange.bybit.dto.account.allcoins.BybitAllCoinsBalance; import org.knowm.xchange.bybit.dto.account.feerates.BybitFeeRates; @@ -84,16 +84,12 @@ BybitResult> getOpenOrders( */ @POST @Path("/order/create") + @Consumes(MediaType.APPLICATION_JSON) BybitResult placeMarketOrder( @HeaderParam(X_BAPI_API_KEY) String apiKey, @HeaderParam(X_BAPI_SIGN) ParamsDigest signature, @HeaderParam(X_BAPI_TIMESTAMP) SynchronizedValueFactory timestamp, - @FormParam("category") String category, - @FormParam("symbol") String symbol, - @FormParam("side") String side, - @FormParam("orderType") String orderType, - @FormParam("qty") BigDecimal qty, - @FormParam("orderLinkId") String orderLinkId) + BybitPlaceOrderPayload payload) throws IOException, BybitException; /** @@ -101,18 +97,13 @@ BybitResult placeMarketOrder( */ @POST @Path("/order/create") + @Consumes(MediaType.APPLICATION_JSON) BybitResult placeLimitOrder( @HeaderParam(X_BAPI_API_KEY) String apiKey, @HeaderParam(X_BAPI_SIGN) ParamsDigest signature, @HeaderParam(X_BAPI_TIMESTAMP) SynchronizedValueFactory timestamp, - @FormParam("category") String category, - @FormParam("symbol") String symbol, - @FormParam("side") String side, - @FormParam("orderType") String orderType, - @FormParam("qty") BigDecimal qty, - @FormParam("price") BigDecimal price, - @FormParam("positionIdx") Integer positionIdx, - @FormParam("orderLinkId") String orderLinkId, - @FormParam("reduceOnly") Boolean reduceOnly) - throws IOException, BybitException; + BybitPlaceOrderPayload payload) +// @FormParam("positionIdx") +// @FormParam("reduceOnly") + throws IOException,BybitException; } diff --git a/xchange-bybit/src/main/java/org/knowm/xchange/bybit/dto/trade/BybitPlaceOrderPayload.java b/xchange-bybit/src/main/java/org/knowm/xchange/bybit/dto/trade/BybitPlaceOrderPayload.java new file mode 100644 index 00000000000..3a870d035d9 --- /dev/null +++ b/xchange-bybit/src/main/java/org/knowm/xchange/bybit/dto/trade/BybitPlaceOrderPayload.java @@ -0,0 +1,37 @@ +package org.knowm.xchange.bybit.dto.trade; + +import java.math.BigDecimal; +import lombok.Getter; + +@Getter +public class BybitPlaceOrderPayload { + + private String category; + private String symbol; + private String side; + private String orderType; + private String qty; + private String orderLinkId; + private String price; + + public BybitPlaceOrderPayload(String category, String symbol, String side, String orderType, + BigDecimal qty, + String orderLinkId) { + this.category = category; + this.symbol = symbol; + this.side = side; + this.orderType = orderType; + this.qty = qty.toString(); + this.orderLinkId = orderLinkId; + } + public BybitPlaceOrderPayload(String category, String symbol, String side, String orderType, + BigDecimal qty, String orderLinkId, BigDecimal price) { + this.category = category; + this.symbol = symbol; + this.side = side; + this.orderType = orderType; + this.qty = qty.toString(); + this.orderLinkId = orderLinkId; + this.price = price.toString(); + } +} diff --git a/xchange-bybit/src/main/java/org/knowm/xchange/bybit/service/BybitTradeServiceRaw.java b/xchange-bybit/src/main/java/org/knowm/xchange/bybit/service/BybitTradeServiceRaw.java index db89d7312e0..37e2f4f430f 100644 --- a/xchange-bybit/src/main/java/org/knowm/xchange/bybit/service/BybitTradeServiceRaw.java +++ b/xchange-bybit/src/main/java/org/knowm/xchange/bybit/service/BybitTradeServiceRaw.java @@ -6,6 +6,7 @@ import java.math.BigDecimal; import org.knowm.xchange.Exchange; import org.knowm.xchange.bybit.dto.BybitCategory; +import org.knowm.xchange.bybit.dto.trade.BybitPlaceOrderPayload; import org.knowm.xchange.bybit.dto.BybitResult; import org.knowm.xchange.bybit.dto.trade.BybitOrderResponse; import org.knowm.xchange.bybit.dto.trade.BybitOrderType; @@ -33,17 +34,14 @@ public BybitResult> getBybitOrder( public BybitResult placeMarketOrder( BybitCategory category, String symbol, BybitSide side, BigDecimal qty, String orderLinkId) throws IOException { + BybitPlaceOrderPayload payload = new BybitPlaceOrderPayload(category.getValue(), + symbol, side.getValue(), BybitOrderType.MARKET.getValue(), qty, orderLinkId); BybitResult placeOrder = bybitAuthenticated.placeMarketOrder( apiKey, signatureCreator, nonceFactory, - category.getValue(), - symbol, - side.getValue(), - BybitOrderType.MARKET.getValue(), - qty, - orderLinkId); + payload); if (!placeOrder.isSuccess()) { throw createBybitExceptionFromResult(placeOrder); } @@ -51,27 +49,17 @@ public BybitResult placeMarketOrder( } public BybitResult placeLimitOrder( - BybitCategory category, - String symbol, - BybitSide side, - BigDecimal qty, - BigDecimal limitPrice, + BybitCategory category, String symbol, BybitSide side, BigDecimal qty, BigDecimal limitPrice, String orderLinkId) throws IOException { + BybitPlaceOrderPayload payload = new BybitPlaceOrderPayload(category.getValue(), + symbol, side.getValue(), BybitOrderType.LIMIT.getValue(), qty, orderLinkId, limitPrice); BybitResult placeOrder = bybitAuthenticated.placeLimitOrder( apiKey, signatureCreator, nonceFactory, - category.getValue(), - symbol, - side.getValue(), - BybitOrderType.LIMIT.getValue(), - qty, - limitPrice, - 0, - orderLinkId, - false); + payload); if (!placeOrder.isSuccess()) { throw createBybitExceptionFromResult(placeOrder); } diff --git a/xchange-bybit/src/test/java/org/knowm/xchange/bybit/TradeExample.java b/xchange-bybit/src/test/java/org/knowm/xchange/bybit/TradeExample.java new file mode 100644 index 00000000000..401da4889c1 --- /dev/null +++ b/xchange-bybit/src/test/java/org/knowm/xchange/bybit/TradeExample.java @@ -0,0 +1,94 @@ +package org.knowm.xchange.bybit; + +import static org.knowm.xchange.bybit.BybitExchange.SPECIFIC_PARAM_ACCOUNT_TYPE; + +import java.io.IOException; +import java.math.BigDecimal; +import org.knowm.xchange.Exchange; +import org.knowm.xchange.ExchangeFactory; +import org.knowm.xchange.ExchangeSpecification; +import org.knowm.xchange.bybit.dto.account.walletbalance.BybitAccountType; +import org.knowm.xchange.currency.CurrencyPair; +import org.knowm.xchange.derivative.FuturesContract; +import org.knowm.xchange.dto.Order.OrderType; +import org.knowm.xchange.dto.marketdata.Ticker; +import org.knowm.xchange.dto.trade.LimitOrder; +import org.knowm.xchange.dto.trade.MarketOrder; +import org.knowm.xchange.instrument.Instrument; + +public class TradeExample { + + public static void main(String[] args) throws InterruptedException { + try { + testTrade(); + } catch (IOException e) { + throw new RuntimeException(e); + } + } + + public static void testTrade() throws IOException { + ExchangeSpecification exchangeSpecification = + new BybitExchange().getDefaultExchangeSpecification(); + exchangeSpecification.setApiKey(System.getProperty("test_api_key")); + exchangeSpecification.setSecretKey(System.getProperty("test_secret_key")); + exchangeSpecification.setExchangeSpecificParametersItem( + SPECIFIC_PARAM_ACCOUNT_TYPE, BybitAccountType.UNIFIED); // or FUND + Exchange exchange = ExchangeFactory.INSTANCE.createExchange( + exchangeSpecification); + Instrument ETH_USDT = new CurrencyPair("ETH/USDT"); + Instrument BTC_USDT_PERP = new FuturesContract(new CurrencyPair("BTC/USDT"), "PERP"); + Instrument ETH_USDT_PERP = new FuturesContract(new CurrencyPair("ETH/USDT"), "PERP"); + + System.out.printf("Wallets: %n%s%n", + exchange.getAccountService().getAccountInfo().getWallets()); + Ticker ticker = exchange + .getMarketDataService() + .getTicker(ETH_USDT_PERP); + System.out.println(ticker.toString()); + + System.out.printf("Instrument %s:%n %s", ETH_USDT, exchange.getExchangeMetaData() + .getInstruments().get(ETH_USDT)); + System.out.printf("Instrument %s:%n %s", ETH_USDT_PERP, exchange.getExchangeMetaData() + .getInstruments().get(ETH_USDT_PERP)); + + BigDecimal minAmountSpot = exchange.getExchangeMetaData().getInstruments().get(ETH_USDT) + .getMinimumAmount(); + BigDecimal minUSDTSpot = minAmountSpot.multiply(ticker.getLast()); + //buy + String marketSpotOrderId = + exchange + .getTradeService() + .placeMarketOrder( + new MarketOrder(OrderType.BID, minUSDTSpot, ETH_USDT)); + System.out.println("Market Spot order id: " + marketSpotOrderId); + //sell + marketSpotOrderId = + exchange + .getTradeService() + .placeMarketOrder( + new MarketOrder(OrderType.ASK, minAmountSpot, ETH_USDT)); + + System.out.println("Market Spot order id: " + marketSpotOrderId); + + BigDecimal minAmountFuture = exchange.getExchangeMetaData().getInstruments().get(ETH_USDT_PERP) + .getMinimumAmount(); + + //long + String marketFutureOrderId = + exchange + .getTradeService() + .placeMarketOrder( + new MarketOrder(OrderType.BID, minAmountFuture, ETH_USDT_PERP)); + System.out.println("Market Future order id: " + marketFutureOrderId); + + //short + String limitFutureOrderId = + exchange + .getTradeService() + .placeLimitOrder( + new LimitOrder(OrderType.ASK, minAmountFuture, ETH_USDT_PERP, "123213", null, + ticker.getLast())); + System.out.println("Limit Future order id: " + limitFutureOrderId); + } + +} diff --git a/xchange-bybit/src/test/resources/logback.xml b/xchange-bybit/src/test/resources/logback.xml index b193ec04c03..2a586567a6e 100644 --- a/xchange-bybit/src/test/resources/logback.xml +++ b/xchange-bybit/src/test/resources/logback.xml @@ -18,6 +18,6 @@ - + \ No newline at end of file