mirror of
https://gitlab.com/veloren/veloren.git
synced 2024-08-30 18:12:32 +00:00
Change admins from Vec<String> into Hashset<Uuid>, add commands to server-cli-bin for adding and removing admins
This commit is contained in:
28
server-cli/src/admin.rs
Normal file
28
server-cli/src/admin.rs
Normal file
@ -0,0 +1,28 @@
|
||||
pub fn admin_subcommand(
|
||||
sub_m: &clap::ArgMatches,
|
||||
server_settings: &server::Settings,
|
||||
editable_settings: &mut server::EditableSettings,
|
||||
data_dir: &std::path::Path,
|
||||
) {
|
||||
let login_provider =
|
||||
server::login_provider::LoginProvider::new(server_settings.auth_server_address.clone());
|
||||
|
||||
match sub_m.subcommand() {
|
||||
("add", Some(sub_m)) => {
|
||||
if let Some(username) = sub_m.value_of("username") {
|
||||
server::add_admin(username, &login_provider, editable_settings, data_dir)
|
||||
}
|
||||
},
|
||||
("remove", Some(sub_m)) => {
|
||||
if let Some(username) = sub_m.value_of("username") {
|
||||
server::remove_admin(username, &login_provider, editable_settings, data_dir)
|
||||
}
|
||||
},
|
||||
// TODO: can clap enforce this?
|
||||
// or make this list current admins or something
|
||||
_ => tracing::error!(
|
||||
"Invalid input, use one of the subcommands listed using: \nveloren-server-cli help \
|
||||
admin"
|
||||
),
|
||||
}
|
||||
}
|
@ -2,6 +2,7 @@
|
||||
#![deny(clippy::clone_on_ref_ptr)]
|
||||
#![feature(bool_to_option)]
|
||||
|
||||
mod admin;
|
||||
mod logging;
|
||||
mod settings;
|
||||
mod shutdown_coordinator;
|
||||
@ -12,11 +13,9 @@ use crate::{
|
||||
shutdown_coordinator::ShutdownCoordinator,
|
||||
tui_runner::{Message, Tui},
|
||||
};
|
||||
use clap::{App, Arg};
|
||||
use clap::{App, Arg, SubCommand};
|
||||
use common::clock::Clock;
|
||||
use server::{Event, Input, Server};
|
||||
#[cfg(any(target_os = "linux", target_os = "macos"))]
|
||||
use signal_hook::SIGUSR1;
|
||||
use std::{
|
||||
io,
|
||||
sync::{atomic::AtomicBool, mpsc, Arc},
|
||||
@ -35,48 +34,54 @@ fn main() -> io::Result<()> {
|
||||
Arg::with_name("basic")
|
||||
.short("b")
|
||||
.long("basic")
|
||||
.help("Disables the tui")
|
||||
.takes_value(false),
|
||||
.help("Disables the tui"),
|
||||
Arg::with_name("interactive")
|
||||
.short("i")
|
||||
.long("interactive")
|
||||
.help("Enables command input for basic mode")
|
||||
.takes_value(false),
|
||||
.help("Enables command input for basic mode"),
|
||||
Arg::with_name("no-auth")
|
||||
.long("no-auth")
|
||||
.help("Runs without auth enabled"),
|
||||
])
|
||||
.subcommand(
|
||||
SubCommand::with_name("admin")
|
||||
.about("Add or remove admins")
|
||||
.subcommands(vec![
|
||||
SubCommand::with_name("add").about("Adds an admin").arg(
|
||||
Arg::with_name("username")
|
||||
.help("Name of the admin to add")
|
||||
.required(true),
|
||||
),
|
||||
SubCommand::with_name("remove")
|
||||
.about("Removes an admin")
|
||||
.arg(
|
||||
Arg::with_name("username")
|
||||
.help("Name of the admin to remove")
|
||||
.required(true),
|
||||
),
|
||||
]),
|
||||
)
|
||||
.get_matches();
|
||||
|
||||
let basic = matches.is_present("basic");
|
||||
let basic = matches.is_present("basic")
|
||||
// Default to basic with these subcommands
|
||||
|| matches
|
||||
.subcommand_name()
|
||||
.filter(|name| ["admin"].contains(name))
|
||||
.is_some();
|
||||
let interactive = matches.is_present("interactive");
|
||||
let no_auth = matches.is_present("no-auth");
|
||||
|
||||
let sigusr1_signal = Arc::new(AtomicBool::new(false));
|
||||
|
||||
#[cfg(any(target_os = "linux", target_os = "macos"))]
|
||||
let _ = signal_hook::flag::register(SIGUSR1, Arc::clone(&sigusr1_signal));
|
||||
let _ = signal_hook::flag::register(signal_hook::SIGUSR1, Arc::clone(&sigusr1_signal));
|
||||
|
||||
logging::init(basic);
|
||||
|
||||
// Load settings
|
||||
let settings = settings::Settings::load();
|
||||
|
||||
// Panic hook to ensure that console mode is set back correctly if in non-basic
|
||||
// mode
|
||||
let hook = std::panic::take_hook();
|
||||
std::panic::set_hook(Box::new(move |info| {
|
||||
Tui::shutdown(basic);
|
||||
hook(info);
|
||||
}));
|
||||
|
||||
let tui = (!basic || interactive).then(|| Tui::run(basic));
|
||||
|
||||
info!("Starting server...");
|
||||
|
||||
// Set up an fps clock
|
||||
let mut clock = Clock::start();
|
||||
|
||||
// Determine folder to save server data in
|
||||
let server_data_dir = {
|
||||
let mut path = common::userdata_dir_workspace!();
|
||||
@ -86,7 +91,33 @@ fn main() -> io::Result<()> {
|
||||
|
||||
// Load server settings
|
||||
let mut server_settings = server::Settings::load(&server_data_dir);
|
||||
let editable_settings = server::EditableSettings::load(&server_data_dir);
|
||||
let mut editable_settings = server::EditableSettings::load(&server_data_dir);
|
||||
match matches.subcommand() {
|
||||
("admin", Some(sub_m)) => {
|
||||
admin::admin_subcommand(
|
||||
sub_m,
|
||||
&server_settings,
|
||||
&mut editable_settings,
|
||||
&server_data_dir,
|
||||
);
|
||||
return Ok(());
|
||||
},
|
||||
_ => {},
|
||||
}
|
||||
|
||||
// Panic hook to ensure that console mode is set back correctly if in non-basic
|
||||
// mode
|
||||
if !basic {
|
||||
let hook = std::panic::take_hook();
|
||||
std::panic::set_hook(Box::new(move |info| {
|
||||
Tui::shutdown(basic);
|
||||
hook(info);
|
||||
}));
|
||||
}
|
||||
|
||||
let tui = (!basic || interactive).then(|| Tui::run(basic));
|
||||
|
||||
info!("Starting server...");
|
||||
|
||||
if no_auth {
|
||||
server_settings.auth_server_address = None;
|
||||
@ -106,6 +137,12 @@ fn main() -> io::Result<()> {
|
||||
|
||||
let mut shutdown_coordinator = ShutdownCoordinator::new(Arc::clone(&sigusr1_signal));
|
||||
|
||||
// Set up an fps clock
|
||||
let mut clock = Clock::start();
|
||||
// Wait for a tick so we don't start with a zero dt
|
||||
// TODO: consider integrating this into Clock::start?
|
||||
clock.tick(Duration::from_millis(1000 / TPS));
|
||||
|
||||
loop {
|
||||
// Terminate the server if instructed to do so by the shutdown coordinator
|
||||
if shutdown_coordinator.check(&mut server, &settings) {
|
||||
@ -144,6 +181,12 @@ fn main() -> io::Result<()> {
|
||||
info!("Closing the server");
|
||||
break;
|
||||
},
|
||||
Message::AddAdmin(username) => {
|
||||
server.add_admin(&username);
|
||||
},
|
||||
Message::RemoveAdmin(username) => {
|
||||
server.remove_admin(&username);
|
||||
},
|
||||
},
|
||||
Err(mpsc::TryRecvError::Empty) | Err(mpsc::TryRecvError::Disconnected) => {},
|
||||
}
|
||||
|
@ -26,6 +26,8 @@ pub enum Message {
|
||||
AbortShutdown,
|
||||
Shutdown { grace_period: Duration },
|
||||
Quit,
|
||||
AddAdmin(String),
|
||||
RemoveAdmin(String),
|
||||
}
|
||||
|
||||
pub struct Command<'a> {
|
||||
@ -37,7 +39,8 @@ pub struct Command<'a> {
|
||||
pub cmd: fn(Vec<String>, &mut mpsc::Sender<Message>),
|
||||
}
|
||||
|
||||
pub const COMMANDS: [Command; 4] = [
|
||||
// TODO: mabye we could be using clap here?
|
||||
pub const COMMANDS: [Command; 5] = [
|
||||
Command {
|
||||
name: "quit",
|
||||
description: "Closes the server",
|
||||
@ -70,6 +73,22 @@ pub const COMMANDS: [Command; 4] = [
|
||||
args: 0,
|
||||
cmd: |_, sender| sender.send(Message::AbortShutdown).unwrap(),
|
||||
},
|
||||
Command {
|
||||
name: "admin",
|
||||
description: "Add or remove an admin via \'admin add/remove <username>\'",
|
||||
split_spaces: true,
|
||||
args: 2,
|
||||
cmd: |args, sender| match args.get(..2) {
|
||||
Some([op, username]) if op == "add" => {
|
||||
sender.send(Message::AddAdmin(username.clone())).unwrap()
|
||||
},
|
||||
Some([op, username]) if op == "remove" => {
|
||||
sender.send(Message::RemoveAdmin(username.clone())).unwrap()
|
||||
},
|
||||
Some(_) => error!("First arg must be add or remove"),
|
||||
_ => error!("Not enough args, should be unreachable"),
|
||||
},
|
||||
},
|
||||
Command {
|
||||
name: "help",
|
||||
description: "List all command available",
|
||||
|
Reference in New Issue
Block a user