use super::super::lookahead_guard::{DataAccessMode, LookAheadGuard};
use crate::data::Timeframe;
use chrono::{DateTime, Utc};
use shape_ast::error::{Result, ShapeError};
impl super::ExecutionContext {
pub fn set_id(&mut self, id: &str) {
self.current_id = Some(id.to_string());
}
pub fn id(&self) -> Result<&str> {
self.current_id
.as_deref()
.ok_or_else(|| ShapeError::RuntimeError {
message: "No ID set".to_string(),
location: None,
})
}
pub fn get_current_id(&self) -> Result<String> {
self.current_id
.clone()
.ok_or_else(|| ShapeError::RuntimeError {
message: "No data loaded".to_string(),
location: None,
})
}
pub fn timeframe(&self) -> Result<&Timeframe> {
self.current_timeframe
.as_ref()
.ok_or_else(|| ShapeError::RuntimeError {
message: "No timeframe set".to_string(),
location: None,
})
}
pub fn get_current_timeframe(&self) -> Result<Timeframe> {
self.current_timeframe
.ok_or_else(|| ShapeError::RuntimeError {
message: "No timeframe set in context".to_string(),
location: None,
})
}
pub fn set_current_timeframe(&mut self, timeframe: Timeframe) -> Result<()> {
self.current_timeframe = Some(timeframe);
Ok(())
}
pub fn update_data(&mut self, data: &super::super::data::DataFrame) {
self.current_id = Some(data.id.clone());
self.current_timeframe = Some(data.timeframe);
self.current_row_index = if data.row_count() == 0 {
0
} else {
data.row_count() - 1
};
}
pub fn get_date_range(&self) -> Option<(DateTime<Utc>, DateTime<Utc>)> {
self.date_range
}
pub fn set_date_range(&mut self, start: DateTime<Utc>, end: DateTime<Utc>) {
self.date_range = Some((start, end));
}
pub fn set_date_range_parsed(&mut self, start: &str, end: &str) -> Result<()> {
let parse_date = |s: &str| -> Result<DateTime<Utc>> {
if let Ok(dt) = DateTime::parse_from_rfc3339(s) {
return Ok(dt.with_timezone(&Utc));
}
if let Ok(nd) = chrono::NaiveDate::parse_from_str(s, "%Y-%m-%d") {
return Ok(nd
.and_hms_opt(0, 0, 0)
.ok_or_else(|| ShapeError::RuntimeError {
message: format!("Invalid time for date: {}", s),
location: None,
})?
.and_utc());
}
Err(ShapeError::RuntimeError {
message: format!("Cannot parse date '{}': expected ISO8601 or YYYY-MM-DD", s),
location: None,
})
};
let start_dt = parse_date(start)?;
let end_dt = parse_date(end)?;
self.date_range = Some((start_dt, end_dt));
Ok(())
}
pub fn set_reference_datetime(&mut self, datetime: DateTime<Utc>) {
self.reference_datetime = Some(datetime);
}
pub fn get_reference_datetime(&self) -> Option<DateTime<Utc>> {
self.reference_datetime
}
pub fn sync_to_reference_datetime(&mut self) -> Result<()> {
if self.reference_datetime.is_some() {
self.current_row_index = 0; }
Ok(())
}
pub fn set_data_access_mode(&mut self, mode: DataAccessMode, strict: bool) {
self.lookahead_guard = Some(LookAheadGuard::new(mode, strict));
}
pub fn lookahead_guard(&self) -> Option<&LookAheadGuard> {
self.lookahead_guard.as_ref()
}
}