Skip to content

Commit

Permalink
feat: squash config show into config whoami (#323)
Browse files Browse the repository at this point in the history
  • Loading branch information
EverlastingBugstopper authored Mar 3, 2021
1 parent c1da6bc commit 8a68b84
Show file tree
Hide file tree
Showing 8 changed files with 79 additions and 75 deletions.
78 changes: 57 additions & 21 deletions crates/houston/src/profile/mod.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
mod sensitive;

use crate::{Config, HoustonProblem};
use regex::Regex;
use sensitive::Sensitive;
use serde::{Deserialize, Serialize};

Expand All @@ -21,7 +20,7 @@ pub struct LoadOpts {
}

/// Represents all possible configuration options.
pub struct Opts {
pub struct ProfileData {
/// Apollo API Key
pub api_key: Option<String>,
}
Expand Down Expand Up @@ -56,10 +55,10 @@ impl Profile {

/// Writes an api_key to the filesystem (`$APOLLO_CONFIG_HOME/profiles/<profile_name>/.sensitive`).
pub fn set_api_key(name: &str, config: &Config, api_key: &str) -> Result<(), HoustonProblem> {
let opts = Opts {
let data = ProfileData {
api_key: Some(api_key.to_string()),
};
Profile::save(name, config, opts)?;
Profile::save(name, config, data)?;
Ok(())
}

Expand Down Expand Up @@ -92,8 +91,8 @@ impl Profile {

/// Saves configuration options for a specific profile to the file system,
/// splitting sensitive information into a separate file.
pub fn save(name: &str, config: &Config, opts: Opts) -> Result<(), HoustonProblem> {
if let Some(api_key) = opts.api_key {
pub fn save(name: &str, config: &Config, data: ProfileData) -> Result<(), HoustonProblem> {
if let Some(api_key) = data.api_key {
Sensitive { api_key }.save(name, config)?;
}
Ok(())
Expand Down Expand Up @@ -150,7 +149,7 @@ impl Profile {

impl fmt::Display for Profile {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "{}", self.sensitive)
write!(f, "{}", &self.sensitive)
}
}

Expand All @@ -160,26 +159,63 @@ impl fmt::Display for Profile {
// are printed, so we don't need to worry about strings 8 chars or less,
// which this fn would just print back out
pub fn mask_key(key: &str) -> String {
let ex = Regex::new(r"(?im)^(.{4})(.*)(.{4})$").expect("Could not create regular expression.");
ex.replace(key, "$1******************$3").to_string()
let mut masked_key = "".to_string();
for (i, char) in key.chars().enumerate() {
if i <= 3 || i >= key.len() - 4 {
masked_key.push(char);
} else {
masked_key.push('*');
}
}
masked_key
}

#[cfg(test)]
mod tests {
use super::mask_key;

#[test]
#[allow(clippy::many_single_char_names)]
fn masks_valid_keys_properly() {
let a = "user:gh.foo:djru4788dhsg3657fhLOLO";
assert_eq!(mask_key(a), "user******************LOLO".to_string());
let b = "service:foo:dh47dh27sg18aj49dkLOLO";
assert_eq!(mask_key(b), "serv******************LOLO".to_string());
let c = "some nonsense";
assert_eq!(mask_key(c), "some******************ense".to_string());
let d = "";
assert_eq!(mask_key(d), "".to_string());
let e = "short";
assert_eq!(mask_key(e), "short".to_string());
fn it_can_mask_user_key() {
let input = "user:gh.foo:djru4788dhsg3657fhLOLO";
assert_eq!(
mask_key(input),
"user**************************LOLO".to_string()
);
}

#[test]
fn it_can_mask_long_user_key() {
let input = "user:veryveryveryveryveryveryveryveryveryveryveryverylong";
assert_eq!(
mask_key(input),
"user*************************************************long".to_string()
);
}

#[test]
fn it_can_mask_graph_key() {
let input = "service:foo:djru4788dhsg3657fhLOLO";
assert_eq!(
mask_key(input),
"serv**************************LOLO".to_string()
);
}

#[test]
fn it_can_mask_nonsense() {
let input = "some nonsense";
assert_eq!(mask_key(input), "some*****ense".to_string());
}

#[test]
fn it_can_mask_nothing() {
let input = "";
assert_eq!(mask_key(input), "".to_string());
}

#[test]
fn it_can_mask_short() {
let input = "short";
assert_eq!(mask_key(input), "short".to_string());
}
}
2 changes: 1 addition & 1 deletion crates/houston/src/profile/sensitive.rs
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,6 @@ impl Sensitive {

impl fmt::Display for Sensitive {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "API Key: \"{}\"", self.api_key)
write!(f, "{}", super::mask_key(&self.api_key))
}
}
7 changes: 1 addition & 6 deletions src/command/config/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@ mod auth;
mod clear;
mod delete;
mod list;
mod show;
mod whoami;

use serde::Serialize;
Expand Down Expand Up @@ -34,9 +33,6 @@ pub enum Command {
/// List all configuration profiles
List(list::List),

/// View a configuration profile's details
Show(show::Show),

/// View the identity of a user/api key
Whoami(whoami::WhoAmI),
}
Expand All @@ -50,10 +46,9 @@ impl Config {
match &self.command {
Command::Auth(command) => command.run(config),
Command::List(command) => command.run(config),
Command::Show(command) => command.run(config),
Command::Delete(command) => command.run(config),
Command::Clear(command) => command.run(config),
Command::Whoami(command) => command.run(client_config),
Command::Whoami(command) => command.run(config, client_config),
}
}
}
32 changes: 0 additions & 32 deletions src/command/config/show.rs

This file was deleted.

16 changes: 15 additions & 1 deletion src/command/config/whoami.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,8 @@ use crate::utils::client::StudioClientConfig;
use crate::utils::env::RoverEnvKey;
use crate::Result;

use houston as config;

#[derive(Debug, Serialize, StructOpt)]
pub struct WhoAmI {
/// Name of configuration profile to use
Expand All @@ -20,7 +22,11 @@ pub struct WhoAmI {
}

impl WhoAmI {
pub fn run(&self, client_config: StudioClientConfig) -> Result<RoverStdout> {
pub fn run(
&self,
config: config::Config,
client_config: StudioClientConfig,
) -> Result<RoverStdout> {
let client = client_config.get_client(&self.profile_name)?;
eprintln!("Checking identity of your API key against the registry.");

Expand Down Expand Up @@ -68,6 +74,14 @@ impl WhoAmI {

message.push_str(&format!("{}: {}", Green.normal().paint("Origin"), &origin));

let opts = config::LoadOpts { sensitive: true };
let profile = config::Profile::load(&self.profile_name, &config, opts)?;
message.push_str(&format!(
"\n{}: {}",
Green.normal().paint("API Key"),
profile
));

eprintln!("{}", message);

Ok(RoverStdout::None)
Expand Down
6 changes: 2 additions & 4 deletions src/error/metadata/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -89,9 +89,6 @@ impl From<&mut anyhow::Error> for Metadata {

if let Some(houston_problem) = error.downcast_ref::<HoustonProblem>() {
let (suggestion, code) = match houston_problem {
HoustonProblem::NoNonSensitiveConfigFound(_) => {
(Some(Suggestion::RerunWithSensitive), None)
}
HoustonProblem::CouldNotCreateConfigHome(_)
| HoustonProblem::DefaultConfigDirNotFound
| HoustonProblem::InvalidOverrideConfigDir(_) => {
Expand All @@ -108,7 +105,8 @@ impl From<&mut anyhow::Error> for Metadata {
}
HoustonProblem::NoConfigProfiles => (Some(Suggestion::NewUserNoProfiles), None),
HoustonProblem::ProfileNotFound(_) => (Some(Suggestion::ListProfiles), None),
HoustonProblem::TomlDeserialization(_)
HoustonProblem::NoNonSensitiveConfigFound(_)
| HoustonProblem::TomlDeserialization(_)
| HoustonProblem::TomlSerialization(_)
| HoustonProblem::IOError(_) => (Some(Suggestion::SubmitIssue), None),
};
Expand Down
7 changes: 0 additions & 7 deletions src/error/metadata/suggestion.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@ use crate::utils::env::RoverEnvKey;
#[derive(Debug)]
pub enum Suggestion {
SubmitIssue,
RerunWithSensitive,
SetConfigHome,
MigrateConfigHomeOrCreateConfig,
CreateConfig,
Expand All @@ -35,12 +34,6 @@ impl Display for Suggestion {
Suggestion::SubmitIssue => {
format!("This error was unexpected! Please submit an issue with any relevant details about what you were trying to do: {}", Cyan.normal().paint("https://github.com/apollographql/rover/issues/new"))
}
Suggestion::RerunWithSensitive => {
format!(
"Try re-running this command with the {} flag",
Yellow.normal().paint("`--sensitive`")
)
}
Suggestion::SetConfigHome => {
format!(
"You can override this path by setting the {} environment variable.",
Expand Down
6 changes: 3 additions & 3 deletions src/utils/telemetry.rs
Original file line number Diff line number Diff line change
Expand Up @@ -141,15 +141,15 @@ mod tests {

#[test]
fn it_can_serialize_commands_with_arguments() {
let args = vec![PKG_NAME, "config", "show", "default", "--sensitive"];
let args = vec![PKG_NAME, "config", "list", "--help"];
let rover = Rover::from_iter(args);
let actual_serialized_command = rover
.serialize_command()
.expect("could not serialize command");
let mut expected_arguments = HashMap::new();
expected_arguments.insert("sensitive".to_string(), json!(true));
expected_arguments.insert("help".to_string(), json!(true));
let expected_serialized_command = Command {
name: "config show".to_string(),
name: "config whoami".to_string(),
arguments: expected_arguments,
};
assert_eq!(actual_serialized_command, expected_serialized_command);
Expand Down

0 comments on commit 8a68b84

Please sign in to comment.