Multithreaded connection
This commit is contained in:
+21
-10
@@ -1,5 +1,5 @@
|
||||
use std::{
|
||||
net::TcpListener,
|
||||
net::{TcpListener, TcpStream},
|
||||
path::{Path, PathBuf},
|
||||
sync::{Arc, Mutex},
|
||||
};
|
||||
@@ -14,7 +14,7 @@ pub mod vfs;
|
||||
pub use anyhow::Result;
|
||||
use tungstenite::accept;
|
||||
|
||||
use crate::plugin::Plugin;
|
||||
use crate::plugin::DynPlugin;
|
||||
pub use once_cell;
|
||||
|
||||
#[derive(serde::Serialize, serde::Deserialize)]
|
||||
@@ -23,7 +23,7 @@ pub struct ServerConfig {
|
||||
}
|
||||
|
||||
pub struct Server {
|
||||
plugins: Mutex<Vec<Box<dyn Plugin>>>,
|
||||
plugins: Mutex<Vec<DynPlugin>>,
|
||||
root: PathBuf,
|
||||
config: ServerConfig,
|
||||
}
|
||||
@@ -79,14 +79,16 @@ impl Server {
|
||||
for stream in listener.incoming() {
|
||||
match stream {
|
||||
Ok(stream) => {
|
||||
Self::LOGGER.info(format!("New connection: {}", stream.peer_addr()?));
|
||||
let mut ws = accept(stream)?;
|
||||
|
||||
let msg = ws.read()?;
|
||||
ws.send(msg)?;
|
||||
std::thread::spawn({
|
||||
let srv = self.clone();
|
||||
move || match srv.handle_client(stream) {
|
||||
Ok(_) => {}
|
||||
Err(e) => Self::LOGGER.error(format!("Client handler failed: {e}")),
|
||||
}
|
||||
});
|
||||
}
|
||||
Err(e) => {
|
||||
Self::LOGGER.error(format!("Connection failed: {}", e));
|
||||
Self::LOGGER.error(format!("Connection failed: {e}"));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -94,7 +96,16 @@ impl Server {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub fn add_plugin(self: &Arc<Self>, plugin: Box<dyn Plugin>) {
|
||||
pub fn add_plugin(self: &Arc<Self>, plugin: DynPlugin) {
|
||||
self.plugins.lock().unwrap().push(plugin);
|
||||
}
|
||||
|
||||
fn handle_client(self: &Arc<Self>, stream: TcpStream) -> anyhow::Result<()> {
|
||||
Self::LOGGER.info(format!("New connection: {}", stream.peer_addr()?));
|
||||
let mut ws = accept(stream)?;
|
||||
|
||||
let msg = ws.read()?;
|
||||
ws.send(msg)?;
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
+4
-4
@@ -2,22 +2,22 @@ use std::path::Path;
|
||||
|
||||
use libloading::{Library, Symbol};
|
||||
|
||||
use crate::{logger, plugin::Plugin, vfs};
|
||||
use crate::{logger, plugin::DynPlugin, vfs};
|
||||
|
||||
logger! {
|
||||
const LOGGER "Loader"
|
||||
}
|
||||
|
||||
pub fn load_plugin(path: &Path) -> anyhow::Result<Box<dyn Plugin>> {
|
||||
pub fn load_plugin(path: &Path) -> anyhow::Result<DynPlugin> {
|
||||
unsafe {
|
||||
LOGGER.info(format!("Loading plugin: {:?}", path));
|
||||
let lib = Library::new(path)?;
|
||||
let func: Symbol<extern "C" fn() -> Box<dyn Plugin>> = lib.get(b"load_plugin").unwrap();
|
||||
let func: Symbol<extern "C" fn() -> DynPlugin> = lib.get(b"load_plugin").unwrap();
|
||||
Ok(func())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn load_plugins(arr: &mut Vec<Box<dyn Plugin>>, path: &Path) -> crate::Result<()> {
|
||||
pub fn load_plugins(arr: &mut Vec<DynPlugin>, path: &Path) -> crate::Result<()> {
|
||||
LOGGER.info("Loading plugins");
|
||||
vfs::dir(path)?;
|
||||
if path.is_dir() {
|
||||
|
||||
+1
-1
@@ -2,7 +2,7 @@
|
||||
macro_rules! export_plugin {
|
||||
($p:expr) => {
|
||||
#[unsafe(no_mangle)]
|
||||
pub extern "C" fn load_plugin() -> Box<dyn Plugin> {
|
||||
pub extern "C" fn load_plugin() -> $crate::plugin::DynPlugin {
|
||||
$p
|
||||
}
|
||||
};
|
||||
|
||||
@@ -2,6 +2,8 @@ use std::sync::Arc;
|
||||
|
||||
use crate::Server;
|
||||
|
||||
pub type DynPlugin = Box<dyn Plugin + Send + Sync>;
|
||||
|
||||
pub trait Plugin {
|
||||
fn init(&mut self, server: &Arc<Server>);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user