use crate::auth::Auth;
use crate::container::App;
use crate::error::FrameworkError;
use crate::http::{HttpResponse, Request, Response};
use ferro_broadcast::{AuthData, Broadcaster, ChannelType};
use serde::Deserialize;
#[derive(Deserialize)]
struct BroadcastAuthInput {
channel_name: String,
socket_id: String,
}
pub async fn broadcasting_auth(req: Request) -> Response {
let user_id = Auth::id().ok_or_else(|| FrameworkError::domain("Unauthenticated", 401))?;
let input: BroadcastAuthInput = req.input().await?;
let broadcaster = App::get::<Broadcaster>()
.ok_or_else(|| FrameworkError::internal("Broadcasting not configured"))?;
let auth_data = AuthData {
socket_id: input.socket_id.clone(),
channel: input.channel_name.clone(),
auth_token: Some(user_id.to_string()),
};
let authorized = broadcaster.check_auth(&auth_data).await;
if !authorized {
return Err(HttpResponse::json(serde_json::json!({
"error": "Forbidden"
}))
.status(403));
}
let mut response = serde_json::json!({
"auth": "ok",
"socket_id": input.socket_id,
"channel": input.channel_name,
});
let channel_type = ChannelType::from_name(&input.channel_name);
if channel_type == ChannelType::Presence {
response["channel_data"] = serde_json::json!({
"user_id": user_id.to_string(),
});
}
Ok(HttpResponse::json(response))
}