#[non_exhaustive]pub struct RequestOpen {
pub side: Side,
pub price: Option<Decimal>,
pub quantity: Decimal,
pub kind: OrderKind,
pub time_in_force: TimeInForce,
pub position_id: Option<PositionId>,
pub reduce_only: ReduceOnly,
pub market: Option<MarketSnapshot>,
pub margin_effect: Option<MarginEffect>,
}Expand description
Parameters for opening a new order.
§Warning: reduce_only Default Behavior
The reduce_only field defaults to ReduceOnly::No, which means:
- A
Sellorder defaults toSellToOpen(open short / write option) - A
Buyorder defaults toBuyToOpen(open long)
For closing positions, callers MUST explicitly set reduce_only to
ReduceOnly::Position (or ReduceOnly::PositionAndFreeBase).
Failure to do so on non-crypto instruments (equities, options) will:
- On non-margin accounts: result in a 422 rejection from the exchange
- On margin accounts: silently open a short position instead of closing the long
The close_open_positions_with_market_orders helper sets this correctly. A caller building
its own closing request must set it with with_reduce_only.
#[non_exhaustive], so a field can be added without breaking a caller. Outside this crate,
build one with RequestOpen::new and the with_* methods, and change a copy by assigning
its public fields.
Fields (Non-exhaustive)§
This struct is marked as non-exhaustive
Struct { .. } syntax; cannot be matched against without a wildcard ..; and struct update syntax will not work.side: Side§price: Option<Decimal>Limit price for the order. Required for Limit/StopLimit orders, and for
TrailingStopFixedLimit orders, whose limit stays fixed while the trigger trails.
None for Market/Stop/TrailingStop orders (which execute at market price when triggered),
and for TrailingStopLimit orders, whose limit price follows from their stop and
limit_offset. A price given with a Market order anyway is ignored, by the simulated venue
and by the live clients that accept market orders.
quantity: Decimal§kind: OrderKind§time_in_force: TimeInForce§position_id: Option<PositionId>Target PositionId for this order in OmsMode::Hedging.
For opening orders: the position this fill should open or add to.
For closing orders: the position this fill should reduce or close.
In OmsMode::Netting, leave as None (ignored).
reduce_only: ReduceOnlyConstrain this order to only reduce existing positions, never open new ones: see
ReduceOnly.
Used by exchanges that require explicit open/close intent (Alpaca, Interactive
Brokers, Schwab). Adapters derive venue-specific semantics from
ReduceOnly::is_reduce_only + side, so both reduce-only values map alike:
- not reduce-only, Buy → BuyToOpen (open long / add to long)
- not reduce-only, Sell → SellToOpen (open short / write option)
- reduce-only, Buy → BuyToClose (close short)
- reduce-only, Sell → SellToClose (close long)
Exchanges that infer intent from positions (Binance, Deribit) may map this to
their reduceOnly parameter or ignore it entirely.
The rustrade engine enforces it on fills, whatever the venue did with it: a fill of a
reduce-only order never grows or flips the engine’s position. A fill larger than the
opposite position is cut so the position lands flat, and the excess is reported rather
than applied. See Trade::holding_move.
#[serde(default)] so requests serialised before this field existed still load, and a
true or false serialised before it was a ReduceOnly loads as
ReduceOnly::Position or ReduceOnly::No.
market: Option<MarketSnapshot>Market state observed at the instant this request was created, if any was sampled.
This is decision-time provenance, not an instruction to the venue. It records what the sender was looking at when it chose to trade, which is the one price a fill can be measured against after the fact — implementation shortfall is the difference between this and the price actually obtained.
§Live venues must ignore this field
No live exchange adapter reads it and none should: a venue prices a fill from its own book, and an adapter that forwarded these prices would be sending the client’s view of the market back as an instruction. Every adapter in this crate leaves it untouched.
§A simulated venue fills from it only when it has no book of its own
SimulatedVenue reads this only in
VenueRegime::RequestPriced, where it
has no market feed and this snapshot is its only price source. That is the regime
MockExecution and
MockExchange use: the request’s snapshot is priced
through the venue’s FillModel, and without it a market order
has no limit price to fall back on — the venue ignores price on an
OrderKind::Market — so the venue can only reject.
A MarketDriven venue ignores it and
prices from its own book, like a live one. This field is then decision-time provenance
alone, and the difference between it and the price obtained is implementation shortfall.
Sampling it at creation rather than at fill time is deliberate. It is the one instant with a well-defined position on a simulated timeline for the sender: everything the sender had seen by then is in it, and nothing it had not seen can be. What makes it safe for a venue to hold a book instead is that its driver paces the feed — routing each market event to the venue before the client that reacts to it sees the same event, and booking each request at the instant it arrives. A venue that sampled a stream it shares with the engine but does not pace could fill against prices from arbitrarily far in the future, which is why the regime is a property of how the venue is driven rather than a configuration flag.
§None versus an empty snapshot
None means no snapshot was taken — a live path, or a caller that constructed the request
directly. Some holding a MarketSnapshot::is_empty snapshot means one was taken and the
instrument had no price yet, which is what a cold start looks like. A RequestPriced
simulated venue distinguishes the two in its rejection, because the fixes differ.
#[serde(default)] so requests serialised before this field existed still load.
margin_effect: Option<MarginEffect>What this order does to a margin account’s loans, or None to take the client’s default.
Only a margin client or a simulated venue with spot margin acts on a borrow or a repay; see
MarginEffect for the three values. A client that cannot honour a Some refuses the
order unsent with
OrderError::UnsupportedMarginEffect:
a cash or spot-only account takes Some(NoSideEffect) alone, and a client that cannot
promise it (account-level margin, or implicit borrowing as under Hyperliquid’s portfolio
margin) takes no Some at all, NoSideEffect included. A caller that sets an effect on
every order must leave it None for those venues.
#[serde(default)] so requests serialised before this field existed still load.
Implementations§
Source§impl RequestOpen
impl RequestOpen
Sourcepub fn new(
side: Side,
price: Option<Decimal>,
quantity: Decimal,
kind: OrderKind,
time_in_force: TimeInForce,
) -> Self
pub fn new( side: Side, price: Option<Decimal>, quantity: Decimal, kind: OrderKind, time_in_force: TimeInForce, ) -> Self
A request with no position_id, not
reduce_only, and no market snapshot. Set those
with the with_* methods.
Sourcepub fn with_position_id(self, position_id: PositionId) -> Self
pub fn with_position_id(self, position_id: PositionId) -> Self
This request with the position_id it targets in
OmsMode::Hedging.
Sourcepub fn with_reduce_only(self, reduce_only: ReduceOnly) -> Self
pub fn with_reduce_only(self, reduce_only: ReduceOnly) -> Self
This request with its reduce_only set to reduce_only.
Sourcepub fn with_market(self, market: MarketSnapshot) -> Self
pub fn with_market(self, market: MarketSnapshot) -> Self
This request with the market its sender observed when it created it.
Sourcepub fn with_margin_effect(self, margin_effect: MarginEffect) -> Self
pub fn with_margin_effect(self, margin_effect: MarginEffect) -> Self
This request with its margin_effect set to margin_effect,
instead of the client’s default.
Trait Implementations§
Source§impl Clone for RequestOpen
impl Clone for RequestOpen
Source§impl Debug for RequestOpen
impl Debug for RequestOpen
Source§impl<'de> Deserialize<'de> for RequestOpen
impl<'de> Deserialize<'de> for RequestOpen
Source§fn deserialize<__D>(__deserializer: __D) -> Result<Self, __D::Error>where
__D: Deserializer<'de>,
fn deserialize<__D>(__deserializer: __D) -> Result<Self, __D::Error>where
__D: Deserializer<'de>,
impl Eq for RequestOpen
Source§impl Hash for RequestOpen
impl Hash for RequestOpen
Source§impl Ord for RequestOpen
impl Ord for RequestOpen
1.21.0 (const: unstable) · Source§fn max(self, other: Self) -> Selfwhere
Self: Sized,
fn max(self, other: Self) -> Selfwhere
Self: Sized,
1.21.0 (const: unstable) · Source§fn min(self, other: Self) -> Selfwhere
Self: Sized,
fn min(self, other: Self) -> Selfwhere
Self: Sized,
Source§impl PartialEq for RequestOpen
impl PartialEq for RequestOpen
Source§impl PartialOrd for RequestOpen
impl PartialOrd for RequestOpen
Source§impl Serialize for RequestOpen
impl Serialize for RequestOpen
impl StructuralPartialEq for RequestOpen
Auto Trait Implementations§
impl Freeze for RequestOpen
impl RefUnwindSafe for RequestOpen
impl Send for RequestOpen
impl Sync for RequestOpen
impl Unpin for RequestOpen
impl UnsafeUnpin for RequestOpen
impl UnwindSafe for RequestOpen
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
Source§impl<Q, K> Comparable<K> for Q
impl<Q, K> Comparable<K> for Q
impl<T> DeserializeOwned for Twhere
T: for<'de> Deserialize<'de>,
Source§impl<Q, K> Equivalent<K> for Q
impl<Q, K> Equivalent<K> for Q
Source§impl<Q, K> Equivalent<K> for Q
impl<Q, K> Equivalent<K> for Q
Source§fn equivalent(&self, key: &K) -> bool
fn equivalent(&self, key: &K) -> bool
key and return true if they are equal.Source§impl<T> FmtForward for T
impl<T> FmtForward for T
Source§fn fmt_binary(self) -> FmtBinary<Self>where
Self: Binary,
fn fmt_binary(self) -> FmtBinary<Self>where
Self: Binary,
self to use its Binary implementation when Debug-formatted.Source§fn fmt_display(self) -> FmtDisplay<Self>where
Self: Display,
fn fmt_display(self) -> FmtDisplay<Self>where
Self: Display,
self to use its Display implementation when
Debug-formatted.Source§fn fmt_lower_exp(self) -> FmtLowerExp<Self>where
Self: LowerExp,
fn fmt_lower_exp(self) -> FmtLowerExp<Self>where
Self: LowerExp,
self to use its LowerExp implementation when
Debug-formatted.Source§fn fmt_lower_hex(self) -> FmtLowerHex<Self>where
Self: LowerHex,
fn fmt_lower_hex(self) -> FmtLowerHex<Self>where
Self: LowerHex,
self to use its LowerHex implementation when
Debug-formatted.Source§fn fmt_octal(self) -> FmtOctal<Self>where
Self: Octal,
fn fmt_octal(self) -> FmtOctal<Self>where
Self: Octal,
self to use its Octal implementation when Debug-formatted.Source§fn fmt_pointer(self) -> FmtPointer<Self>where
Self: Pointer,
fn fmt_pointer(self) -> FmtPointer<Self>where
Self: Pointer,
self to use its Pointer implementation when
Debug-formatted.Source§fn fmt_upper_exp(self) -> FmtUpperExp<Self>where
Self: UpperExp,
fn fmt_upper_exp(self) -> FmtUpperExp<Self>where
Self: UpperExp,
self to use its UpperExp implementation when
Debug-formatted.Source§fn fmt_upper_hex(self) -> FmtUpperHex<Self>where
Self: UpperHex,
fn fmt_upper_hex(self) -> FmtUpperHex<Self>where
Self: UpperHex,
self to use its UpperHex implementation when
Debug-formatted.Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
Source§fn in_current_span(self) -> Instrumented<Self> ⓘ
fn in_current_span(self) -> Instrumented<Self> ⓘ
Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
Source§fn in_current_span(self) -> Instrumented<Self> ⓘ
fn in_current_span(self) -> Instrumented<Self> ⓘ
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreimpl<T> JsonSchemaMaybe for T
Source§impl<T> Pipe for Twhere
T: ?Sized,
impl<T> Pipe for Twhere
T: ?Sized,
Source§fn pipe<R>(self, func: impl FnOnce(Self) -> R) -> Rwhere
Self: Sized,
fn pipe<R>(self, func: impl FnOnce(Self) -> R) -> Rwhere
Self: Sized,
Source§fn pipe_ref<'a, R>(&'a self, func: impl FnOnce(&'a Self) -> R) -> Rwhere
R: 'a,
fn pipe_ref<'a, R>(&'a self, func: impl FnOnce(&'a Self) -> R) -> Rwhere
R: 'a,
self and passes that borrow into the pipe function. Read moreSource§fn pipe_ref_mut<'a, R>(&'a mut self, func: impl FnOnce(&'a mut Self) -> R) -> Rwhere
R: 'a,
fn pipe_ref_mut<'a, R>(&'a mut self, func: impl FnOnce(&'a mut Self) -> R) -> Rwhere
R: 'a,
self and passes that borrow into the pipe function. Read moreSource§fn pipe_borrow<'a, B, R>(&'a self, func: impl FnOnce(&'a B) -> R) -> R
fn pipe_borrow<'a, B, R>(&'a self, func: impl FnOnce(&'a B) -> R) -> R
Source§fn pipe_borrow_mut<'a, B, R>(
&'a mut self,
func: impl FnOnce(&'a mut B) -> R,
) -> R
fn pipe_borrow_mut<'a, B, R>( &'a mut self, func: impl FnOnce(&'a mut B) -> R, ) -> R
Source§fn pipe_as_ref<'a, U, R>(&'a self, func: impl FnOnce(&'a U) -> R) -> R
fn pipe_as_ref<'a, U, R>(&'a self, func: impl FnOnce(&'a U) -> R) -> R
self, then passes self.as_ref() into the pipe function.Source§fn pipe_as_mut<'a, U, R>(&'a mut self, func: impl FnOnce(&'a mut U) -> R) -> R
fn pipe_as_mut<'a, U, R>(&'a mut self, func: impl FnOnce(&'a mut U) -> R) -> R
self, then passes self.as_mut() into the pipe
function.Source§fn pipe_deref<'a, T, R>(&'a self, func: impl FnOnce(&'a T) -> R) -> R
fn pipe_deref<'a, T, R>(&'a self, func: impl FnOnce(&'a T) -> R) -> R
self, then passes self.deref() into the pipe function.Source§impl<T> Pointable for T
impl<T> Pointable for T
Source§impl<T> PolicyExt for Twhere
T: ?Sized,
impl<T> PolicyExt for Twhere
T: ?Sized,
Source§impl<T> Tap for T
impl<T> Tap for T
Source§fn tap_borrow<B>(self, func: impl FnOnce(&B)) -> Self
fn tap_borrow<B>(self, func: impl FnOnce(&B)) -> Self
Borrow<B> of a value. Read moreSource§fn tap_borrow_mut<B>(self, func: impl FnOnce(&mut B)) -> Self
fn tap_borrow_mut<B>(self, func: impl FnOnce(&mut B)) -> Self
BorrowMut<B> of a value. Read moreSource§fn tap_ref<R>(self, func: impl FnOnce(&R)) -> Self
fn tap_ref<R>(self, func: impl FnOnce(&R)) -> Self
AsRef<R> view of a value. Read moreSource§fn tap_ref_mut<R>(self, func: impl FnOnce(&mut R)) -> Self
fn tap_ref_mut<R>(self, func: impl FnOnce(&mut R)) -> Self
AsMut<R> view of a value. Read moreSource§fn tap_deref<T>(self, func: impl FnOnce(&T)) -> Self
fn tap_deref<T>(self, func: impl FnOnce(&T)) -> Self
Deref::Target of a value. Read moreSource§fn tap_deref_mut<T>(self, func: impl FnOnce(&mut T)) -> Self
fn tap_deref_mut<T>(self, func: impl FnOnce(&mut T)) -> Self
Deref::Target of a value. Read moreSource§fn tap_dbg(self, func: impl FnOnce(&Self)) -> Self
fn tap_dbg(self, func: impl FnOnce(&Self)) -> Self
.tap() only in debug builds, and is erased in release builds.Source§fn tap_mut_dbg(self, func: impl FnOnce(&mut Self)) -> Self
fn tap_mut_dbg(self, func: impl FnOnce(&mut Self)) -> Self
.tap_mut() only in debug builds, and is erased in release
builds.Source§fn tap_borrow_dbg<B>(self, func: impl FnOnce(&B)) -> Self
fn tap_borrow_dbg<B>(self, func: impl FnOnce(&B)) -> Self
.tap_borrow() only in debug builds, and is erased in release
builds.Source§fn tap_borrow_mut_dbg<B>(self, func: impl FnOnce(&mut B)) -> Self
fn tap_borrow_mut_dbg<B>(self, func: impl FnOnce(&mut B)) -> Self
.tap_borrow_mut() only in debug builds, and is erased in release
builds.Source§fn tap_ref_dbg<R>(self, func: impl FnOnce(&R)) -> Self
fn tap_ref_dbg<R>(self, func: impl FnOnce(&R)) -> Self
.tap_ref() only in debug builds, and is erased in release
builds.Source§fn tap_ref_mut_dbg<R>(self, func: impl FnOnce(&mut R)) -> Self
fn tap_ref_mut_dbg<R>(self, func: impl FnOnce(&mut R)) -> Self
.tap_ref_mut() only in debug builds, and is erased in release
builds.Source§fn tap_deref_dbg<T>(self, func: impl FnOnce(&T)) -> Self
fn tap_deref_dbg<T>(self, func: impl FnOnce(&T)) -> Self
.tap_deref() only in debug builds, and is erased in release
builds.