Skip to content

Commit d6ba7a3

Browse files
committed
Auto merge of #11545 - kylematsuda:secret-type, r=Eh2406
Wrapper type for data that should never be logged Fixes #11519. So far this is just creating the new wrapper type. If this looks okay, I'll start adding this wrapper in places where tokens and secret keys are held or passed.
2 parents d73b935 + efb972a commit d6ba7a3

File tree

7 files changed

+191
-77
lines changed

7 files changed

+191
-77
lines changed

src/bin/cargo/commands/login.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ pub fn cli() -> Command {
3636
pub fn exec(config: &mut Config, args: &ArgMatches) -> CliResult {
3737
ops::registry_login(
3838
config,
39-
args.get_one("token").map(String::as_str),
39+
args.get_one::<String>("token").map(|s| s.as_str().into()),
4040
args.get_one("registry").map(String::as_str),
4141
args.flag("generate-keypair"),
4242
args.flag("secret-key"),

src/bin/cargo/commands/owner.rs

+2-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
use crate::command_prelude::*;
22

33
use cargo::ops::{self, OwnersOptions};
4+
use cargo::util::auth::Secret;
45

56
pub fn cli() -> Command {
67
subcommand("owner")
@@ -34,7 +35,7 @@ pub fn exec(config: &mut Config, args: &ArgMatches) -> CliResult {
3435
let registry = args.registry(config)?;
3536
let opts = OwnersOptions {
3637
krate: args.get_one::<String>("crate").cloned(),
37-
token: args.get_one::<String>("token").cloned(),
38+
token: args.get_one::<String>("token").cloned().map(Secret::from),
3839
index: args.get_one::<String>("index").cloned(),
3940
to_add: args
4041
.get_many::<String>("add")

src/bin/cargo/commands/publish.rs

+3-1
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,9 @@ pub fn exec(config: &mut Config, args: &ArgMatches) -> CliResult {
3636
&ws,
3737
&PublishOpts {
3838
config,
39-
token: args.get_one::<String>("token").map(|s| s.to_string()),
39+
token: args
40+
.get_one::<String>("token")
41+
.map(|s| s.to_string().into()),
4042
index,
4143
verify: !args.flag("no-verify"),
4244
allow_dirty: args.flag("allow-dirty"),

src/bin/cargo/commands/yank.rs

+2-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
use crate::command_prelude::*;
22

33
use cargo::ops;
4+
use cargo::util::auth::Secret;
45

56
pub fn cli() -> Command {
67
subcommand("yank")
@@ -37,7 +38,7 @@ pub fn exec(config: &mut Config, args: &ArgMatches) -> CliResult {
3738
config,
3839
krate.map(|s| s.to_string()),
3940
version.map(|s| s.to_string()),
40-
args.get_one::<String>("token").cloned(),
41+
args.get_one::<String>("token").cloned().map(Secret::from),
4142
args.get_one::<String>("index").cloned(),
4243
args.flag("undo"),
4344
registry,

src/cargo/ops/registry.rs

+33-29
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ use crate::ops;
3030
use crate::ops::Packages;
3131
use crate::sources::{RegistrySource, SourceConfigMap, CRATES_IO_DOMAIN, CRATES_IO_REGISTRY};
3232
use crate::util::auth::{
33-
paserk_public_from_paserk_secret, {self, AuthorizationError},
33+
paserk_public_from_paserk_secret, Secret, {self, AuthorizationError},
3434
};
3535
use crate::util::config::{Config, SslVersionConfig, SslVersionConfigRange};
3636
use crate::util::errors::CargoResult;
@@ -45,11 +45,11 @@ use crate::{drop_print, drop_println, version};
4545
pub enum RegistryCredentialConfig {
4646
None,
4747
/// The authentication token.
48-
Token(String),
48+
Token(Secret<String>),
4949
/// Process used for fetching a token.
5050
Process((PathBuf, Vec<String>)),
5151
/// Secret Key and subject for Asymmetric tokens.
52-
AsymmetricKey((String, Option<String>)),
52+
AsymmetricKey((Secret<String>, Option<String>)),
5353
}
5454

5555
impl RegistryCredentialConfig {
@@ -71,9 +71,9 @@ impl RegistryCredentialConfig {
7171
pub fn is_asymmetric_key(&self) -> bool {
7272
matches!(self, Self::AsymmetricKey(..))
7373
}
74-
pub fn as_token(&self) -> Option<&str> {
74+
pub fn as_token(&self) -> Option<Secret<&str>> {
7575
if let Self::Token(v) = self {
76-
Some(&*v)
76+
Some(v.as_deref())
7777
} else {
7878
None
7979
}
@@ -85,7 +85,7 @@ impl RegistryCredentialConfig {
8585
None
8686
}
8787
}
88-
pub fn as_asymmetric_key(&self) -> Option<&(String, Option<String>)> {
88+
pub fn as_asymmetric_key(&self) -> Option<&(Secret<String>, Option<String>)> {
8989
if let Self::AsymmetricKey(v) = self {
9090
Some(v)
9191
} else {
@@ -96,7 +96,7 @@ impl RegistryCredentialConfig {
9696

9797
pub struct PublishOpts<'cfg> {
9898
pub config: &'cfg Config,
99-
pub token: Option<String>,
99+
pub token: Option<Secret<String>>,
100100
pub index: Option<String>,
101101
pub verify: bool,
102102
pub allow_dirty: bool,
@@ -174,7 +174,7 @@ pub fn publish(ws: &Workspace<'_>, opts: &PublishOpts<'_>) -> CargoResult<()> {
174174

175175
let (mut registry, reg_ids) = registry(
176176
opts.config,
177-
opts.token.as_deref(),
177+
opts.token.as_ref().map(Secret::as_deref),
178178
opts.index.as_deref(),
179179
publish_registry.as_deref(),
180180
true,
@@ -512,7 +512,7 @@ fn wait_for_publish(
512512
/// * `token_required`: If `true`, the token will be set.
513513
fn registry(
514514
config: &Config,
515-
token_from_cmdline: Option<&str>,
515+
token_from_cmdline: Option<Secret<&str>>,
516516
index: Option<&str>,
517517
registry: Option<&str>,
518518
force_update: bool,
@@ -786,7 +786,7 @@ fn http_proxy_exists(config: &Config) -> CargoResult<bool> {
786786

787787
pub fn registry_login(
788788
config: &Config,
789-
token: Option<&str>,
789+
token: Option<Secret<&str>>,
790790
reg: Option<&str>,
791791
generate_keypair: bool,
792792
secret_key_required: bool,
@@ -795,7 +795,7 @@ pub fn registry_login(
795795
let source_ids = get_source_id(config, None, reg)?;
796796
let reg_cfg = auth::registry_credential_config(config, &source_ids.original)?;
797797

798-
let login_url = match registry(config, token, None, reg, false, None) {
798+
let login_url = match registry(config, token.clone(), None, reg, false, None) {
799799
Ok((registry, _)) => Some(format!("{}/me", registry.host())),
800800
Err(e) if e.is::<AuthorizationError>() => e
801801
.downcast::<AuthorizationError>()
@@ -830,29 +830,33 @@ pub fn registry_login(
830830
}
831831
_ => (None, None),
832832
};
833-
let secret_key: String;
833+
let secret_key: Secret<String>;
834834
if generate_keypair {
835835
assert!(!secret_key_required);
836836
let kp = AsymmetricKeyPair::<pasetors::version3::V3>::generate().unwrap();
837-
let mut key = String::new();
838-
FormatAsPaserk::fmt(&kp.secret, &mut key).unwrap();
839-
secret_key = key;
837+
secret_key = Secret::default().map(|mut key| {
838+
FormatAsPaserk::fmt(&kp.secret, &mut key).unwrap();
839+
key
840+
});
840841
} else if secret_key_required {
841842
assert!(!generate_keypair);
842843
drop_println!(config, "please paste the API secret key below");
843-
let mut line = String::new();
844-
let input = io::stdin();
845-
input
846-
.lock()
847-
.read_line(&mut line)
848-
.with_context(|| "failed to read stdin")?;
849-
secret_key = line.trim().to_string();
844+
secret_key = Secret::default()
845+
.map(|mut line| {
846+
let input = io::stdin();
847+
input
848+
.lock()
849+
.read_line(&mut line)
850+
.with_context(|| "failed to read stdin")
851+
.map(|_| line.trim().to_string())
852+
})
853+
.transpose()?;
850854
} else {
851855
secret_key = old_secret_key
852856
.cloned()
853857
.ok_or_else(|| anyhow!("need a secret_key to set a key_subject"))?;
854858
}
855-
if let Some(p) = paserk_public_from_paserk_secret(&secret_key) {
859+
if let Some(p) = paserk_public_from_paserk_secret(secret_key.as_deref()) {
856860
drop_println!(config, "{}", &p);
857861
} else {
858862
bail!("not a validly formatted PASERK secret key");
@@ -866,7 +870,7 @@ pub fn registry_login(
866870
));
867871
} else {
868872
new_token = RegistryCredentialConfig::Token(match token {
869-
Some(token) => token.to_string(),
873+
Some(token) => token.owned(),
870874
None => {
871875
if let Some(login_url) = login_url {
872876
drop_println!(
@@ -890,7 +894,7 @@ pub fn registry_login(
890894
.with_context(|| "failed to read stdin")?;
891895
// Automatically remove `cargo login` from an inputted token to
892896
// allow direct pastes from `registry.host()`/me.
893-
line.replace("cargo login", "").trim().to_string()
897+
Secret::from(line.replace("cargo login", "").trim().to_string())
894898
}
895899
});
896900

@@ -938,7 +942,7 @@ pub fn registry_logout(config: &Config, reg: Option<&str>) -> CargoResult<()> {
938942

939943
pub struct OwnersOptions {
940944
pub krate: Option<String>,
941-
pub token: Option<String>,
945+
pub token: Option<Secret<String>>,
942946
pub index: Option<String>,
943947
pub to_add: Option<Vec<String>>,
944948
pub to_remove: Option<Vec<String>>,
@@ -960,7 +964,7 @@ pub fn modify_owners(config: &Config, opts: &OwnersOptions) -> CargoResult<()> {
960964

961965
let (mut registry, _) = registry(
962966
config,
963-
opts.token.as_deref(),
967+
opts.token.as_ref().map(Secret::as_deref),
964968
opts.index.as_deref(),
965969
opts.registry.as_deref(),
966970
true,
@@ -1019,7 +1023,7 @@ pub fn yank(
10191023
config: &Config,
10201024
krate: Option<String>,
10211025
version: Option<String>,
1022-
token: Option<String>,
1026+
token: Option<Secret<String>>,
10231027
index: Option<String>,
10241028
undo: bool,
10251029
reg: Option<String>,
@@ -1051,7 +1055,7 @@ pub fn yank(
10511055

10521056
let (mut registry, _) = registry(
10531057
config,
1054-
token.as_deref(),
1058+
token.as_ref().map(Secret::as_deref),
10551059
index.as_deref(),
10561060
reg.as_deref(),
10571061
true,

0 commit comments

Comments
 (0)