bitmex-rs icon indicating copy to clipboard operation
bitmex-rs copied to clipboard

Bulk Cancel Multiple Limit Orders Fails With: value: Custom("unsupported value")

Open algoeng opened this issue 4 years ago • 2 comments

@dovahcrow I just ran my test suite against the latest in master and found out bulk cancel is no longer working. Here is what it is basically doing:

    let ord_id1 = gen_ord_id();
    rt.block_on(bm.request(post_limit_order(6000., 100, ord_id1.clone()))).unwrap();
    let ord_id2 = gen_ord_id();
    rt.block_on(bm.request(post_limit_order(7000., 100, ord_id2.clone()))).unwrap();

    let mut ord_ids: Vec<serde_json::Value> = Vec::new();
    ord_ids.push(serde_json::Value::String(ord_id1.clone()));
    ord_ids.push(serde_json::Value::String(ord_id2.clone()));

    let _ = rt.block_on(bm.request(DeleteOrderRequest {
        cl_ord_id: Some(serde_json::Value::Array(ord_ids)),
        ..Default::default()
    })).unwrap();

Here is post_limit_order:

fn post_limit_order(price: f64, qty: i32, cl_ord_id: String) -> PostOrderRequest {
    PostOrderRequest {
        symbol: "XBTUSD".to_string(),
        side: None,
        simple_order_qty: None,
        order_qty: Some(qty),
        price: Some(price),
        display_qty: None,
        stop_px: None,
        cl_ord_id: Some(cl_ord_id),
        cl_ord_link_id: None,
        peg_offset_value: None,
        peg_price_type: None,
        ord_type: Some(OrdType::Limit),
        time_in_force: None,
        exec_inst: None,
        contingency_type: None,
        text: Some("Shine".into()),
    }
}

Here is the stack:

thread 'main' panicked at 'called `Result::unwrap()` on an `Err` value: Custom("unsupported value")

   0: backtrace::backtrace::dbghelp::trace
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\backtrace-0.3.55\src\backtrace\dbghelp.rs:98
   1: backtrace::backtrace::trace_unsynchronized<closure-0>
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\backtrace-0.3.55\src\backtrace\mod.rs:66
   2: backtrace::backtrace::trace<closure-0>
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\backtrace-0.3.55\src\backtrace\mod.rs:53
   3: backtrace::capture::Backtrace::create
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\backtrace-0.3.55\src\capture.rs:176
   4: backtrace::capture::Backtrace::new_unresolved
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\backtrace-0.3.55\src\capture.rs:170
   5: failure::backtrace::internal::InternalBacktrace::new
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\failure-0.1.8\src\backtrace\internal.rs:46
   6: failure::backtrace::Backtrace::new
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\failure-0.1.8\src\backtrace\mod.rs:121
   7: failure::error::error_impl::{{impl}}::from<serde_urlencoded::ser::Error>
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\failure-0.1.8\src\error\error_impl.rs:19
   8: failure::error::{{impl}}::from<serde_urlencoded::ser::Error>
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\failure-0.1.8\src\error\mod.rs:36
   9: bitmex::rest::client::{{impl}}::request::{{closure}}<bitmex::rest::models::requests::DeleteOrderRequest>
             at C:\Users\kr\.cargo\git\checkouts\bitmex-rs-2861a3a714a639fb\8dfa7d7\src\rest\client.rs:63
  10: core::future::from_generator::{{impl}}::poll<generator-0>
             at C:\Users\kr\.rustup\toolchains\stable-x86_64-pc-windows-msvc\lib\rustlib\src\rust\src\libcore\future\mod.rs:66
  11: tokio::runtime::enter::{{impl}}::block_on::{{closure}}<core::future::from_generator::GenFuture<generator-0>>
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\tokio-0.2.22\src\runtime\enter.rs:160
  12: tokio::coop::with_budget::{{closure}}<core::task::poll::Poll<core::result::Result<alloc::vec::Vec<bitmex::rest::models::definitions::Order>, failure::error::Error>>,closure-0>
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\tokio-0.2.22\src\coop.rs:127
  13: std::thread::local::LocalKey<core::cell::Cell<tokio::coop::Budget>>::try_with<core::cell::Cell<tokio::coop::Budget>,closure-0,core::task::poll::Poll<core::result::Result<alloc::vec::Vec<bitmex::rest::models::definitions::Order>, failure::error::Error>>>
             at C:\Users\kr\.rustup\toolchains\stable-x86_64-pc-windows-msvc\lib\rustlib\src\rust\src\libstd\thread\local.rs:263
  14: std::thread::local::LocalKey<core::cell::Cell<tokio::coop::Budget>>::with<core::cell::Cell<tokio::coop::Budget>,closure-0,core::task::poll::Poll<core::result::Result<alloc::vec::Vec<bitmex::rest::models::definitions::Order>, failure::error::Error>>>
             at C:\Users\kr\.rustup\toolchains\stable-x86_64-pc-windows-msvc\lib\rustlib\src\rust\src\libstd\thread\local.rs:239
  15: tokio::coop::with_budget
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\tokio-0.2.22\src\coop.rs:120
  16: tokio::coop::budget
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\tokio-0.2.22\src\coop.rs:96
  17: tokio::runtime::enter::Enter::block_on<core::future::from_generator::GenFuture<generator-0>>
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\tokio-0.2.22\src\runtime\enter.rs:160
  18: tokio::runtime::thread_pool::ThreadPool::block_on<core::future::from_generator::GenFuture<generator-0>>
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\tokio-0.2.22\src\runtime\thread_pool\mod.rs:82
  19: tokio::runtime::{{impl}}::block_on::{{closure}}<core::future::from_generator::GenFuture<generator-0>>
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\tokio-0.2.22\src\runtime\mod.rs:446
  20: tokio::runtime::context::enter<closure-0,core::result::Result<alloc::vec::Vec<bitmex::rest::models::definitions::Order>, failure::error::Error>>
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\tokio-0.2.22\src\runtime\context.rs:72
  21: tokio::runtime::handle::Handle::enter<closure-0,core::result::Result<alloc::vec::Vec<bitmex::rest::models::definitions::Order>, failure::error::Error>>
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\tokio-0.2.22\src\runtime\handle.rs:76
  22: tokio::runtime::Runtime::block_on<core::future::from_generator::GenFuture<generator-0>>
             at C:\Users\kr\.cargo\registry\src\github.com-1ecc6299db9ec823\tokio-0.2.22\src\runtime\mod.rs:441
  23: rust::main
             at src\main.rs:29
  24: std::rt::lang_start::{{closure}}<()>
             at C:\Users\kr\.rustup\toolchains\stable-x86_64-pc-windows-msvc\lib\rustlib\src\rust\src\libstd\rt.rs:67
  25: std::rt::lang_start_internal::{{closure}}
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\rt.rs:52
  26: std::panicking::try::do_call
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\panicking.rs:331
  27: std::panicking::try
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\panicking.rs:274
  28: std::panic::catch_unwind
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\panic.rs:394
  29: std::rt::lang_start_internal
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\rt.rs:51
  30: std::rt::lang_start<()>
             at C:\Users\kr\.rustup\toolchains\stable-x86_64-pc-windows-msvc\lib\rustlib\src\rust\src\libstd\rt.rs:67
  31: main
  32: invoke_main
             at d:\agent\_work\1\s\src\vctools\crt\vcstartup\src\startup\exe_common.inl:78
  33: __scrt_common_main_seh
             at d:\agent\_work\1\s\src\vctools\crt\vcstartup\src\startup\exe_common.inl:288
  34: BaseThreadInitThunk
  35: RtlUserThreadStart
', src\main.rs:29:13
stack backtrace:
   0: backtrace::backtrace::trace_unsynchronized
             at C:\Users\VssAdministrator\.cargo\registry\src\github.com-1ecc6299db9ec823\backtrace-0.3.46\src\backtrace\mod.rs:66
   1: std::sys_common::backtrace::_print_fmt
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\sys_common\backtrace.rs:78
   2: std::sys_common::backtrace::_print::{{impl}}::fmt
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\sys_common\backtrace.rs:59
   3: core::fmt::write
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libcore\fmt\mod.rs:1069
   4: std::io::Write::write_fmt<std::sys::windows::stdio::Stderr>
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\io\mod.rs:1504
   5: std::sys_common::backtrace::_print
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\sys_common\backtrace.rs:62
   6: std::sys_common::backtrace::print
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\sys_common\backtrace.rs:49
   7: std::panicking::default_hook::{{closure}}
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\panicking.rs:198
   8: std::panicking::default_hook
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\panicking.rs:218
   9: std::panicking::rust_panic_with_hook
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\panicking.rs:511
  10: std::panicking::begin_panic_handler
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\panicking.rs:419
  11: core::panicking::panic_fmt
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libcore\panicking.rs:111
  12: core::option::expect_none_failed
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libcore\option.rs:1268
  13: core::result::Result<alloc::vec::Vec<bitmex::rest::models::definitions::Order>, failure::error::Error>::unwrap<alloc::vec::Vec<bitmex::rest::models::definitions::Order>,failure::error::Error>
             at C:\Users\kr\.rustup\toolchains\stable-x86_64-pc-windows-msvc\lib\rustlib\src\rust\src\libcore\result.rs:1005
  14: rust::main
             at .\src\main.rs:29
  15: std::rt::lang_start::{{closure}}<()>
             at C:\Users\kr\.rustup\toolchains\stable-x86_64-pc-windows-msvc\lib\rustlib\src\rust\src\libstd\rt.rs:67
  16: std::rt::lang_start_internal::{{closure}}
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\rt.rs:52
  17: std::panicking::try::do_call
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\panicking.rs:331
  18: std::panicking::try
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\panicking.rs:274
  19: std::panic::catch_unwind
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\panic.rs:394
  20: std::rt::lang_start_internal
             at /rustc/c7087fe00d2ba919df1d813c040a5d47e43b0fe7\/src\libstd\rt.rs:51
  21: std::rt::lang_start<()>
             at C:\Users\kr\.rustup\toolchains\stable-x86_64-pc-windows-msvc\lib\rustlib\src\rust\src\libstd\rt.rs:67
  22: main
  23: invoke_main
             at d:\agent\_work\1\s\src\vctools\crt\vcstartup\src\startup\exe_common.inl:78
  24: __scrt_common_main_seh
             at d:\agent\_work\1\s\src\vctools\crt\vcstartup\src\startup\exe_common.inl:288
  25: BaseThreadInitThunk
  26: RtlUserThreadStart

algoeng avatar Dec 27 '20 23:12 algoeng

I created a minimal reproducible case:

use bitmex::rest::DeleteOrderRequest;

use serde_urlencoded::to_string as to_ustring;

fn main() {
    let mut ord_ids: Vec<serde_json::Value> = Vec::new();
    ord_ids.push(serde_json::Value::String("asdf".to_string()));
    let req = DeleteOrderRequest {
        cl_ord_id: Some(serde_json::Value::Array(ord_ids)),
        ..Default::default()
    };
    println!("{}", to_ustring(&req).unwrap());
}

It seems like we need to provide our own array serializer for vector type when doing the URL encoding.

dovahcrow avatar Jan 11 '21 18:01 dovahcrow

I also took a look at serde_qs, it does not support serialize a vec of strings to a comma-separated string too. I think the solution here would be to annotate the corresponding vec fields with #[serde(deserialize_with)]. Unfortunately, I don't have much time recently for this.

dovahcrow avatar Jan 11 '21 18:01 dovahcrow