diff --git a/Cargo.toml b/Cargo.toml index 750b4284..0d784136 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "ibapi" -version = "1.0.3" +version = "1.0.4" edition = "2021" authors = ["Wil Boayue "] description = "A Rust implementation of the Interactive Brokers TWS API, providing a reliable and user friendly interface for TWS and IB Gateway. Designed with a focus on simplicity and performance." diff --git a/src/market_data/realtime/decoders.rs b/src/market_data/realtime/decoders.rs index 56e5b480..64bca209 100644 --- a/src/market_data/realtime/decoders.rs +++ b/src/market_data/realtime/decoders.rs @@ -13,10 +13,6 @@ use super::{ mod tests; pub(super) fn decode_realtime_bar(message: &mut ResponseMessage) -> Result { - if message.len() < 11 { - return Err(Error::Simple("Invalid message length".into())); - } - message.skip(); // message type message.skip(); // message version message.skip(); // message request id diff --git a/src/messages.rs b/src/messages.rs index 0bd2e492..57796c1f 100644 --- a/src/messages.rs +++ b/src/messages.rs @@ -439,6 +439,10 @@ impl ResponseMessage { } pub fn peek_int(&self, i: usize) -> Result { + if self.i >= self.fields.len() { + return Err(Error::Simple("expected int and found end of message".into())); + } + let field = &self.fields[i]; match field.parse() { Ok(val) => Ok(val), @@ -451,6 +455,10 @@ impl ResponseMessage { } pub fn next_int(&mut self) -> Result { + if self.i >= self.fields.len() { + return Err(Error::Simple("expected int and found end of message".into())); + } + let field = &self.fields[self.i]; self.i += 1; @@ -461,6 +469,10 @@ impl ResponseMessage { } pub fn next_optional_int(&mut self) -> Result, Error> { + if self.i >= self.fields.len() { + return Err(Error::Simple("expected optional int and found end of message".into())); + } + let field = &self.fields[self.i]; self.i += 1; @@ -475,6 +487,10 @@ impl ResponseMessage { } pub fn next_bool(&mut self) -> Result { + if self.i >= self.fields.len() { + return Err(Error::Simple("expected bool and found end of message".into())); + } + let field = &self.fields[self.i]; self.i += 1; @@ -482,6 +498,10 @@ impl ResponseMessage { } pub fn next_long(&mut self) -> Result { + if self.i >= self.fields.len() { + return Err(Error::Simple("expected long and found end of message".into())); + } + let field = &self.fields[self.i]; self.i += 1; @@ -492,6 +512,10 @@ impl ResponseMessage { } pub fn next_optional_long(&mut self) -> Result, Error> { + if self.i >= self.fields.len() { + return Err(Error::Simple("expected optional long and found end of message".into())); + } + let field = &self.fields[self.i]; self.i += 1; @@ -506,6 +530,10 @@ impl ResponseMessage { } pub fn next_date_time(&mut self) -> Result { + if self.i >= self.fields.len() { + return Err(Error::Simple("expected datetime and found end of message".into())); + } + let field = &self.fields[self.i]; self.i += 1; @@ -522,12 +550,20 @@ impl ResponseMessage { } pub fn next_string(&mut self) -> Result { + if self.i >= self.fields.len() { + return Err(Error::Simple("expected string and found end of message".into())); + } + let field = &self.fields[self.i]; self.i += 1; Ok(String::from(field)) } pub fn next_double(&mut self) -> Result { + if self.i >= self.fields.len() { + return Err(Error::Simple("expected double and found end of message".into())); + } + let field = &self.fields[self.i]; self.i += 1; @@ -542,6 +578,10 @@ impl ResponseMessage { } pub fn next_optional_double(&mut self) -> Result, Error> { + if self.i >= self.fields.len() { + return Err(Error::Simple("expected optional double and found end of message".into())); + } + let field = &self.fields[self.i]; self.i += 1; diff --git a/src/scanner.rs b/src/scanner.rs index 8b3417ab..b0615b4a 100644 --- a/src/scanner.rs +++ b/src/scanner.rs @@ -21,6 +21,8 @@ pub(super) fn scanner_parameters(client: &Client) -> Result { } } +#[derive(Debug, Clone, Serialize, Deserialize, PartialEq)] +/// Scanner subscription parameters. pub struct ScannerSubscription { /// The number of rows to be returned for the query pub number_of_rows: i32,