use tower::{Layer, Service};
use std::task::{Context, Poll};
use std::pin::Pin;
use futures::future::BoxFuture;
use crate::pipeline::types::{AudioRequest, WavAudioRequest, AudioResponse, PipelineError};
#[derive(Clone, Debug, Default)]
pub struct WavConversionLayer;
impl<S> Layer<S> for WavConversionLayer {
type Service = WavConversionService<S>;
fn layer(&self, inner: S) -> Self::Service {
WavConversionService { inner }
}
}
#[derive(Clone, Debug)]
pub struct WavConversionService<S> {
pub(crate) inner: S,
}
impl<S> Service<AudioRequest> for WavConversionService<S>
where
S: Service<WavAudioRequest, Response = AudioResponse, Error = PipelineError> + Send + 'static,
S::Future: Send + 'static,
{
type Response = AudioResponse;
type Error = PipelineError;
type Future = BoxFuture<'static, Result<Self::Response, Self::Error>>;
fn poll_ready(&mut self, cx: &mut Context<'_>) -> Poll<Result<(), Self::Error>> {
self.inner.poll_ready(cx).map_err(|e| PipelineError::WavConversionError(format!("Inner service not ready: {}", e)))
}
fn call(&mut self, req: AudioRequest) -> Self::Future {
let wav_data = match crate::transcription::convert_samples_to_wav(&req.0.data) {
Ok(data) => data,
Err(e) => return Box::pin(async move { Err(PipelineError::WavConversionError(e.to_string())) }),
};
let wav_req = WavAudioRequest {
wav_data,
timestamp: req.0.timestamp,
};
let fut = self.inner.call(wav_req);
Box::pin(async move { fut.await })
}
}