From 8f43ee0261c1900608543f191b37d2322092edc3 Mon Sep 17 00:00:00 2001 From: Ian Jackson Date: Sat, 27 Mar 2021 11:40:38 +0000 Subject: [PATCH] otter cli: Provide ListAccounts Signed-off-by: Ian Jackson --- daemon/cmdlistener.rs | 13 +++++++++++++ src/accounts.rs | 16 ++++++++++++++++ src/bin/otter.rs | 40 ++++++++++++++++++++++++++++++++++++++++ src/commands.rs | 2 ++ src/mgmtchannel.rs | 2 +- 5 files changed, 72 insertions(+), 1 deletion(-) diff --git a/daemon/cmdlistener.rs b/daemon/cmdlistener.rs index 708ff227..27b1e377 100644 --- a/daemon/cmdlistener.rs +++ b/daemon/cmdlistener.rs @@ -140,6 +140,19 @@ fn execute(cs: &mut CommandStream, cmd: MgmtCommand) -> MgmtResponse { Fine } + MC::ListAccounts { all } => { + let ag = AccountsGuard::lock(); + let names = if all == Some(true) { + let auth = cs.superuser.ok_or(ME::AuthorisationError)?; + ag.list_accounts_all(auth.into()) + } else { + let AccountSpecified { notional_account, auth, .. } = + cs.account.as_ref().ok_or(ME::SpecifyAccount)?; + ag.list_accounts_scope(¬ional_account.scope, *auth) + }; + MR::AccountsList(names) + } + MC::CreateGame { game, insns } => { let mut ag = AccountsGuard::lock(); let mut games = games_lock(); diff --git a/src/accounts.rs b/src/accounts.rs index a04a4847..a5f21141 100644 --- a/src/accounts.rs +++ b/src/accounts.rs @@ -387,6 +387,22 @@ impl AccountsGuard { self.save_accounts_now()?; } + pub fn list_accounts_all(&self, _: AuthorisationSuperuser) + -> Vec> { + let accounts = self.0.as_ref().expect("loaded"); + accounts.names.keys() + .cloned().collect() + } + + pub fn list_accounts_scope(&self, scope: &AccountScope, + _: Authorisation) + -> Vec> { + let accounts = self.0.as_ref().expect("loaded"); + accounts.names.keys() + .filter(|name| &name.scope == scope) + .cloned().collect() + } + #[throws(AccountsSaveError)] pub fn save_accounts_now(&self) { let accounts = self.0.as_ref().expect("loaded"); diff --git a/src/bin/otter.rs b/src/bin/otter.rs index 31071602..9be5b1f8 100644 --- a/src/bin/otter.rs +++ b/src/bin/otter.rs @@ -1303,3 +1303,43 @@ mod list_pieces { call, )} } + +//---------- list-accounts ---------- + +mod list_accounts { + use super::*; + + #[derive(Default,Debug)] + struct Args { + all: bool, + } + + fn subargs(sa: &mut Args) -> ArgumentParser { + use argparse::*; + let mut ap = ArgumentParser::new(); + ap.refer(&mut sa.all) + .add_option(&["--all"],StoreTrue, + "user superuser access to list all accounts"); + ap + } + + #[throws(AE)] + fn call(_sc: &Subcommand, ma: MainOpts, args: Vec) { + let args = parse_args::(args, &subargs, &ok_id, None); + let mut conn = connect(&ma)?; + let all = Some(args.all); + let accounts = match conn.cmd(&MC::ListAccounts { all })? { + MR::AccountsList(g) => g, + x => throw!(anyhow!("unexpected response to ListAccounts: {:?}", &x)), + }; + for a in accounts { + println!("{:?}", a); + } + } + + inventory::submit!{Subcommand( + "list-accounts", + "List accounts in your account scope", + call, + )} +} diff --git a/src/commands.rs b/src/commands.rs index c6e54136..d62f8a54 100644 --- a/src/commands.rs +++ b/src/commands.rs @@ -17,6 +17,7 @@ pub enum MgmtCommand { CreateAccount(AccountDetails), UpdateAccount(AccountDetails), DeleteAccount(AccountName), + ListAccounts { all: Option }, SelectAccount(AccountName), // success does not mean account exists CheckAccount, // success *does* mean account exists and we have access @@ -68,6 +69,7 @@ pub enum MgmtResponse { Fine, Error { error: MgmtError }, AlterGame { error: Option, responses: Vec }, + AccountsList(Vec>), GamesList(Vec>), LibraryItems(Vec), } diff --git a/src/mgmtchannel.rs b/src/mgmtchannel.rs index eac95917..9fd6f4b4 100644 --- a/src/mgmtchannel.rs +++ b/src/mgmtchannel.rs @@ -68,7 +68,7 @@ impl MgmtChannel { self.write(&cmd).context("send command")?; let resp = self.read().context("read response")?; match &resp { - Fine | GamesList{..} | LibraryItems(_) => { }, + Fine | AccountsList{..} | GamesList{..} | LibraryItems(_) => { }, AlterGame { error: None, .. } => { }, Error { error } => { Err(error.clone()).context( -- 2.30.2