From 2665d8a2c818117163f1ec0dd3ecd0be835e3d9a Mon Sep 17 00:00:00 2001 From: Daniel Szoke Date: Thu, 1 Aug 2024 14:38:23 +0200 Subject: [PATCH 1/2] fix: Redact auth tokens when logging CLI args Redact anything that might be an auth token when logging the command line arguments to console. This occurs only when the log level is set to `info` or `debug`; the default is `warn`. --- src/commands/mod.rs | 13 +++++++++++-- src/utils/auth_token/auth_token_impl.rs | 11 ++++++++++- src/utils/auth_token/mod.rs | 5 ++++- src/utils/auth_token/org_auth_token.rs | 3 +-- src/utils/auth_token/user_auth_token.rs | 3 +-- 5 files changed, 27 insertions(+), 8 deletions(-) diff --git a/src/commands/mod.rs b/src/commands/mod.rs index c167dd8901..e221d9b82c 100644 --- a/src/commands/mod.rs +++ b/src/commands/mod.rs @@ -1,8 +1,8 @@ //! This module implements the root command of the CLI tool. -use std::env; use std::io; use std::process; +use std::{env, iter}; use anyhow::{bail, Result}; use clap::{value_parser, Arg, ArgAction, ArgMatches, Command}; @@ -12,6 +12,7 @@ use log::{debug, info, set_logger, set_max_level, LevelFilter}; use crate::api::Api; use crate::config::{Auth, Config}; use crate::constants::{ARCH, PLATFORM, VERSION}; +use crate::utils::auth_token; use crate::utils::auth_token::AuthToken; use crate::utils::logging::set_quiet_mode; use crate::utils::logging::Logger; @@ -281,7 +282,15 @@ pub fn execute() -> Result<()> { info!( "sentry-cli was invoked with the following command line: {}", env::args() - .map(|a| format!("\"{a}\"")) + // Check whether the previous argument is "--auth-token" + .zip(iter::once(false).chain(env::args().map(|arg| arg == "--auth-token"))) + .map(|(a, is_auth_token_arg)| { + // Redact anything that comes after --auth-token or looks like a token + if is_auth_token_arg || auth_token::looks_like_auth_token(&a) { + return String::from("(redacted)"); + } + format!("\"{a}\"") + }) .collect::>() .join(" ") ); diff --git a/src/utils/auth_token/auth_token_impl.rs b/src/utils/auth_token/auth_token_impl.rs index 749ff78bd9..ab44c25363 100644 --- a/src/utils/auth_token/auth_token_impl.rs +++ b/src/utils/auth_token/auth_token_impl.rs @@ -1,6 +1,6 @@ //! Defines the AuthToken type, which stores a Sentry auth token. -use super::AuthTokenPayload; +use super::{AuthTokenPayload, ORG_AUTH_TOKEN_PREFIX, USER_TOKEN_PREFIX}; use super::{OrgAuthToken, UserAuthToken}; use std::fmt::{Display, Formatter, Result}; @@ -100,3 +100,12 @@ impl AuthTokenInner { } } } + +/// Returns whether a given string looks like it might be an auth token. +/// Specifically, we say a string looks like an auth token when it starts with one of the auth +/// token prefixes (sntrys_ or sntryu_) or passes the auth token soft validation. +pub fn looks_like_auth_token(s: &str) -> bool { + s.starts_with(ORG_AUTH_TOKEN_PREFIX) + || s.starts_with(USER_TOKEN_PREFIX) + || AuthToken::from(s).format_recognized() +} diff --git a/src/utils/auth_token/mod.rs b/src/utils/auth_token/mod.rs index dd903b3bef..6624cbb613 100644 --- a/src/utils/auth_token/mod.rs +++ b/src/utils/auth_token/mod.rs @@ -5,7 +5,7 @@ mod error; mod org_auth_token; mod user_auth_token; -pub use auth_token_impl::AuthToken; +pub use auth_token_impl::{looks_like_auth_token, AuthToken}; pub use org_auth_token::AuthTokenPayload; use error::{AuthTokenParseError, Result}; @@ -14,3 +14,6 @@ use user_auth_token::UserAuthToken; #[cfg(test)] mod test; + +const ORG_AUTH_TOKEN_PREFIX: &str = "sntrys_"; +const USER_TOKEN_PREFIX: &str = "sntryu_"; diff --git a/src/utils/auth_token/org_auth_token.rs b/src/utils/auth_token/org_auth_token.rs index 3489881cec..7fe8306998 100644 --- a/src/utils/auth_token/org_auth_token.rs +++ b/src/utils/auth_token/org_auth_token.rs @@ -1,7 +1,6 @@ -use super::{AuthTokenParseError, Result}; +use super::{AuthTokenParseError, Result, ORG_AUTH_TOKEN_PREFIX}; use serde::{Deserialize, Deserializer}; -const ORG_AUTH_TOKEN_PREFIX: &str = "sntrys_"; const ORG_TOKEN_SECRET_BYTES: usize = 32; /// Represents a valid org auth token. diff --git a/src/utils/auth_token/user_auth_token.rs b/src/utils/auth_token/user_auth_token.rs index 4ecb39dc76..6c0aa135d2 100644 --- a/src/utils/auth_token/user_auth_token.rs +++ b/src/utils/auth_token/user_auth_token.rs @@ -1,7 +1,6 @@ -use super::{AuthTokenParseError, Result}; +use super::{AuthTokenParseError, Result, USER_TOKEN_PREFIX}; const USER_TOKEN_BYTES: usize = 32; -const USER_TOKEN_PREFIX: &str = "sntryu_"; /// Represents a valid User Auth Token. #[derive(Debug, Clone)] From 3d05326dd3e7e9239d0f14a1b85b409f7875a8b9 Mon Sep 17 00:00:00 2001 From: Daniel Szoke Date: Thu, 1 Aug 2024 16:31:49 +0200 Subject: [PATCH 2/2] test(tokens): Add test to ensure tokens redacted The test ensures that when the CLI args are echoed back, anything which might reasonably be an auth token is redacted. --- tests/integration/_cases/token-redacted.trycmd | 9 +++++++++ tests/integration/mod.rs | 5 +++++ 2 files changed, 14 insertions(+) create mode 100644 tests/integration/_cases/token-redacted.trycmd diff --git a/tests/integration/_cases/token-redacted.trycmd b/tests/integration/_cases/token-redacted.trycmd new file mode 100644 index 0000000000..f7cacc3d80 --- /dev/null +++ b/tests/integration/_cases/token-redacted.trycmd @@ -0,0 +1,9 @@ +``` +$ sentry-cli sourcemaps upload --auth-token not-following-token-format -o asdf -p sntrys_project_looks_like_token ./ --log-level=info +? failed +[..] +[..] +[..]INFO[..] sentry-cli was invoked with the following command line: "[..]" "sourcemaps" "upload" "--auth-token" (redacted) "-o" "asdf" "-p" (redacted) "./" "--log-level=info" +... + +``` diff --git a/tests/integration/mod.rs b/tests/integration/mod.rs index a5628fafab..5f73a6ffab 100644 --- a/tests/integration/mod.rs +++ b/tests/integration/mod.rs @@ -235,3 +235,8 @@ pub fn assert_endpoints(mocks: &[Mock]) { mock.assert(); } } + +#[test] +pub fn token_redacted() { + register_test("token-redacted.trycmd"); +}