Skip to content

Commit

Permalink
feat: Improve info command and introduce no-defaults flag (#1344)
Browse files Browse the repository at this point in the history
  • Loading branch information
kamilogorek authored Oct 3, 2022
1 parent 91a9371 commit 42345d0
Show file tree
Hide file tree
Showing 9 changed files with 134 additions and 36 deletions.
83 changes: 50 additions & 33 deletions src/commands/info.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
use std::collections::HashMap;
use std::io;

use anyhow::Result;
Expand All @@ -19,14 +18,21 @@ pub struct AuthStatus {

#[derive(Serialize, Default)]
pub struct ConfigStatus {
config: HashMap<String, Option<String>>,
org: Option<String>,
project: Option<String>,
url: Option<String>,
}

#[derive(Serialize, Default)]
pub struct Status {
config: ConfigStatus,
auth: AuthStatus,
have_dsn: bool,
}

pub fn make_command(command: Command) -> Command {
command
.about("Print information about the Sentry server.")
.about("Print information about the configuration and verify authentication.")
.arg(
Arg::new("config_status_json")
.long("config-status-json")
Expand All @@ -36,6 +42,11 @@ pub fn make_command(command: Command) -> Command {
the user towards configuration.",
),
)
.arg(Arg::new("no_defaults").long("no-defaults").help(
"Skip default organization and project checks. \
This allows you to verify your authentication method, \
without the need for setting other defaults.",
))
}

fn describe_auth(auth: Option<&Auth>) -> &str {
Expand All @@ -48,13 +59,12 @@ fn describe_auth(auth: Option<&Auth>) -> &str {

fn get_config_status_json() -> Result<()> {
let config = Config::current();
let mut rv = ConfigStatus::default();
let mut rv = Status::default();

let (org, project) = config.get_org_and_project_defaults();
rv.config.insert("org".into(), org);
rv.config.insert("project".into(), project);
rv.config
.insert("url".into(), Some(config.get_base_url()?.to_string()));
rv.config.org = org;
rv.config.project = project;
rv.config.url = Some(config.get_base_url()?.to_string());

rv.auth.auth_type = config.get_auth().map(|val| match val {
Auth::Token(_) => "token".into(),
Expand All @@ -75,9 +85,15 @@ pub fn execute(matches: &ArgMatches) -> Result<()> {

let config = Config::current();
let (org, project) = config.get_org_and_project_defaults();
let org = org.filter(|s| !s.is_empty());
let project = project.filter(|s| !s.is_empty());
let info_rv = Api::current().get_auth_info();
let errors =
project.is_none() || org.is_none() || config.get_auth().is_none() || info_rv.is_err();
let mut errors = config.get_auth().is_none() || info_rv.is_err();

// If `no-defaults` is present, only authentication should be verified.
if !matches.is_present("no_defaults") {
errors = errors || project.is_none() || org.is_none();
}

if is_quiet_mode() {
return if errors {
Expand All @@ -88,32 +104,33 @@ pub fn execute(matches: &ArgMatches) -> Result<()> {
}

println!("Sentry Server: {}", config.get_base_url().unwrap_or("-"));
println!(
"Default Organization: {}",
org.unwrap_or_else(|| "-".into())
);
println!("Default Project: {}", project.unwrap_or_else(|| "-".into()));

if config.get_auth().is_some() {
println!();
println!("Authentication Info:");
println!(" Method: {}", describe_auth(config.get_auth()));
match info_rv {
Ok(info) => {
if let Some(ref user) = info.user {
println!(" User: {}", user.email);
}
if let Some(ref auth) = info.auth {
println!(" Scopes:");
for scope in &auth.scopes {
println!(" - {}", scope);
}
}

if !matches.is_present("no_defaults") {
println!(
"Default Organization: {}",
org.unwrap_or_else(|| "-".into())
);
println!("Default Project: {}", project.unwrap_or_else(|| "-".into()));
}

println!();
println!("Authentication Info:");
println!(" Method: {}", describe_auth(config.get_auth()));
match info_rv {
Ok(info) => {
if let Some(ref user) = info.user {
println!(" User: {}", user.email);
}
Err(err) => {
println!(" (failure on authentication: {})", err);
if let Some(ref auth) = info.auth {
println!(" Scopes:");
for scope in &auth.scopes {
println!(" - {}", scope);
}
}
}
Err(err) => {
println!(" (failure on authentication: {})", err);
}
}

if errors {
Expand Down
2 changes: 1 addition & 1 deletion tests/integration/_cases/help/help-windows.trycmd
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ SUBCOMMANDS:
events Manage events on Sentry.
files Manage release artifacts.
help Print this message or the help of the given subcommand(s)
info Print information about the Sentry server.
info Print information about the configuration and verify authentication.
issues Manage issues in Sentry.
login Authenticate with the Sentry server.
organizations Manage organizations on Sentry.
Expand Down
2 changes: 1 addition & 1 deletion tests/integration/_cases/help/help.trycmd
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ SUBCOMMANDS:
events Manage events on Sentry.
files Manage release artifacts.
help Print this message or the help of the given subcommand(s)
info Print information about the Sentry server.
info Print information about the configuration and verify authentication.
issues Manage issues in Sentry.
login Authenticate with the Sentry server.
organizations Manage organizations on Sentry.
Expand Down
5 changes: 4 additions & 1 deletion tests/integration/_cases/info/info-help.trycmd
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
$ sentry-cli info --help
? success
sentry-cli[EXE]-info
Print information about the Sentry server.
Print information about the configuration and verify authentication.

USAGE:
sentry-cli[EXE] info [OPTIONS]
Expand All @@ -17,6 +17,9 @@ OPTIONS:
in key:value format.
--log-level <LOG_LEVEL> Set the log output verbosity. [possible values: trace, debug,
info, warn, error]
--no-defaults Skip default organization and project checks. This allows you
to verify your authentication method, without the need for
setting other defaults.
--quiet Do not print any output while preserving correct exit code.
This flag is currently implemented only for selected
subcommands. [aliases: silent]
Expand Down
17 changes: 17 additions & 0 deletions tests/integration/_cases/info/info-json-no-defaults.trycmd
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
```
$ sentry-cli info --config-status-json
? success
{
"config": {
"org": "",
"project": "",
"url": "[SERVER]"
},
"auth": {
"type": "token",
"successful": true
},
"have_dsn": true
}

```
17 changes: 17 additions & 0 deletions tests/integration/_cases/info/info-json.trycmd
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
```
$ sentry-cli info --config-status-json
? success
{
"config": {
"org": "wat-org",
"project": "wat-project",
"url": "[SERVER]"
},
"auth": {
"type": "token",
"successful": true
},
"have_dsn": true
}

```
13 changes: 13 additions & 0 deletions tests/integration/_cases/info/info-no-defaults.trycmd
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
```
$ sentry-cli info --no-defaults
? success
Sentry Server: [SERVER]

Authentication Info:
Method: Auth Token
User: kamil@sentry.io
Scopes:
- project:read
- project:releases

```
3 changes: 3 additions & 0 deletions tests/integration/_cases/info/info-no-token.trycmd
Original file line number Diff line number Diff line change
Expand Up @@ -5,4 +5,7 @@ Sentry Server: https://sentry.io
Default Organization: -
Default Project: -

Authentication Info:
Method: Unauthorized

```
28 changes: 28 additions & 0 deletions tests/integration/info.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,3 +22,31 @@ fn command_info_basic() {
let t = register_test("info/info-basic.trycmd");
t.insert_var("[SERVER]", server_url()).unwrap();
}

#[test]
fn command_info_no_defaults() {
let _server = mock_endpoint(
EndpointOptions::new("GET", "/api/0/", 200).with_response_file("info/get-info.json"),
);
let t = register_test("info/info-json.trycmd");
t.insert_var("[SERVER]", server_url()).unwrap();
}

#[test]
fn command_info_json() {
let _server = mock_endpoint(
EndpointOptions::new("GET", "/api/0/", 200).with_response_file("info/get-info.json"),
);
let t = register_test("info/info-basic.trycmd");
t.insert_var("[SERVER]", server_url()).unwrap();
}

#[test]
fn command_info_json_without_defaults() {
let _server = mock_endpoint(
EndpointOptions::new("GET", "/api/0/", 200).with_response_file("info/get-info.json"),
);
let t = register_test("info/info-json-no-defaults.trycmd");
t.env("SENTRY_ORG", "").env("SENTRY_PROJECT", "");
t.insert_var("[SERVER]", server_url()).unwrap();
}

0 comments on commit 42345d0

Please sign in to comment.