use tokio::sync::broadcast;
use bat_markets_core::{
CommandLaneEvent, CommandOperation, CommandReceipt, PrivateLaneEvent, PublicLaneEvent,
ReconcileReport, ReconcileTrigger, RequestId, Result,
};
use crate::{
client::BatMarkets, diagnostics::RuntimeDiagnosticsSnapshot, native::NativeClient, runtime,
};
pub struct AdvancedClient<'a> {
inner: &'a BatMarkets,
}
impl<'a> AdvancedClient<'a> {
pub(crate) const fn new(inner: &'a BatMarkets) -> Self {
Self { inner }
}
pub fn ingest_public_json(&self, payload: &str) -> Result<Vec<PublicLaneEvent>> {
let events = self.inner.adapter.as_adapter().parse_public(payload)?;
self.inner.shared.apply_public_events(&events);
Ok(events)
}
pub fn ingest_private_json(&self, payload: &str) -> Result<Vec<PrivateLaneEvent>> {
let events = self.inner.adapter.as_adapter().parse_private(payload)?;
self.inner.shared.apply_private_events(&events);
Ok(events)
}
#[must_use]
pub fn subscribe_public_events(&self) -> broadcast::Receiver<PublicLaneEvent> {
self.inner.shared.subscribe_public_events()
}
#[must_use]
pub fn subscribe_private_events(&self) -> broadcast::Receiver<PrivateLaneEvent> {
self.inner.shared.subscribe_private_events()
}
#[must_use]
pub fn subscribe_command_events(&self) -> broadcast::Receiver<CommandLaneEvent> {
self.inner.shared.subscribe_command_events()
}
pub fn classify_command_json(
&self,
operation: CommandOperation,
payload: Option<&str>,
request_id: Option<RequestId>,
) -> Result<CommandReceipt> {
let receipt = self
.inner
.adapter
.as_adapter()
.classify_command(operation, payload, request_id)?;
self.inner
.write_state(|state| state.apply_command_receipt(&receipt));
self.inner
.shared
.emit_command_event(CommandLaneEvent::Receipt(receipt.clone()));
Ok(receipt)
}
pub async fn reconcile(&self) -> Result<ReconcileReport> {
runtime::reconcile_private(&self.inner.live_context(), ReconcileTrigger::Manual).await
}
#[must_use]
pub fn diagnostics(&self) -> RuntimeDiagnosticsSnapshot {
self.inner.diagnostics().snapshot()
}
#[must_use]
pub fn native(&self) -> NativeClient<'_> {
NativeClient::new(&self.inner.adapter)
}
}