1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
use reqwest;
use std::io::Read;
use {AwsCredentials, CredentialsError, ProvideAwsCredentials, parse_credentials_from_aws_service};
const AWS_CREDENTIALS_PROVIDER_IP: &'static str = "169.254.169.254";
const AWS_CREDENTIALS_PROVIDER_PATH: &'static str = "latest/meta-data/iam/security-credentials";
#[derive(Debug)]
pub struct InstanceMetadataProvider;
impl ProvideAwsCredentials for InstanceMetadataProvider {
fn credentials(&self) -> Result<AwsCredentials, CredentialsError> {
get_credentials_from_role()
}
}
fn get_role_name() -> Result<String, CredentialsError> {
let role_name_address = format!(
"http://{}/{}",
AWS_CREDENTIALS_PROVIDER_IP,
AWS_CREDENTIALS_PROVIDER_PATH
);
let response = reqwest::get(&role_name_address);
match response {
Ok(mut resp) => {
if resp.status().is_success() {
let mut role_name = String::new();
if resp.read_to_string(&mut role_name).is_err() {
return Err(CredentialsError::new(
"Didn't get a parsable role name from metadata service",
));
}
Ok(role_name)
} else {
return Err(CredentialsError::new(format!(
"Couldn't connect to credentials provider: {}",
resp.status()
)));
}
}
Err(err) => {
return Err(CredentialsError::new(
format!("Couldn't connect to credentials provider: {}", err),
))
}
}
}
fn get_credentials_from_role() -> Result<AwsCredentials, CredentialsError> {
let role_name = try!(get_role_name());
let credentials_provider_url = format!(
"http://{}/{}/{}",
AWS_CREDENTIALS_PROVIDER_IP,
AWS_CREDENTIALS_PROVIDER_PATH,
role_name
);
let response = reqwest::get(&credentials_provider_url);
match response {
Ok(mut resp) => {
if resp.status().is_success() {
let mut credentials_response = String::new();
if resp.read_to_string(&mut credentials_response).is_err() {
return Err(CredentialsError::new(
"Had issues with reading iam role response: {}",
));
}
parse_credentials_from_aws_service(&credentials_response)
} else {
return Err(CredentialsError::new(format!(
"Couldn't connect to credentials provider: {}",
resp.status()
)));
}
}
Err(err) => {
return Err(CredentialsError::new(
format!("Couldn't connect to credentials provider: {}", err),
))
}
}
}