Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for using PropertiesFileCredentialsProvider in vault IAM authentication #245

Closed
sreenivassvs123 opened this issue Sep 17, 2018 · 5 comments

Comments

@sreenivassvs123
Copy link

sreenivassvs123 commented Sep 17, 2018

I have aws credentials stored in a property file which has to be used for vault IAM authentication. I have planned to use com.amazonaws.auth.PropertiesFileCredentialsProvider to read from the properties file and use them for aws authentications. I was able to use this for S3 connectivity. For vault IAM authentication using spring-cloud-vault, I couldn't succeed.

Upon the code reading, I see that only DefaultAWSCredentialsProviderChain is being used for aws credentials lookup (https://github.com/spring-cloud/spring-cloud-vault/blob/v2.0.1.RELEASE/spring-cloud-vault-config/src/main/java/org/springframework/cloud/vault/config/ClientAuthenticationFactory.java#L291). Due to the usage of DefaultAWSCredentialsProviderChain, the credentials providers are restricted to only these four: EnvironmentVariableCredentialsProvider, SystemPropertiesCredentialsProvider, ProfileCredentialsProvider, EC2ContainerCredentialsProvider.

Can you please make AwsCredentialProvider configurable for spring-cloud vault authentication so that vault authentication can use the credentials from else where?

If there is already any way to achieve this, can you please provide me the details?

@mp911de
Copy link
Member

mp911de commented Sep 18, 2018

Spring Cloud Vault configures authentication as Spring bean. You can configure and provide your own ClientAuthentication bean so Spring Cloud Vault backs off from configuring authentication.

Providing an own authentication requires you to follow these two steps:

  1. Create a bootstrap configuration
@Configuration
public class MyVaultBootstrapConfiguration {
	@Bean
	public ClientAuthentication clientAuthentication(ClientFactoryWrapper clientFactoryWrapper) {

		AwsIamAuthenticationOptions options = AwsIamAuthenticationOptions.builder()
				.credentialsProvider(new PropertiesFileCredentialsProvider(…))
				.build();

		RestTemplate restTemplate = new RestTemplate(clientFactoryWrapper.getClientHttpRequestFactory());
		return new AwsIamAuthentication(options, restTemplate);
	}
}
  1. Registering your bootstrap configuration in META-INF/spring.factories
org.springframework.cloud.bootstrap.BootstrapConfiguration=com.acme.MyVaultBootstrapConfiguration

PropertiesFileCredentialsProvider requires additional configuration options and that would require us to introduce additional configuration properties which increase complexity and introduce ambiguity. Therefore, we'd keep things as is.

@sreenivassvs123
Copy link
Author

sreenivassvs123 commented Sep 20, 2018

Thank you @mp911de for the quick response and suggesting me to define spring configuration. I have done some code reading for spring vault and slightly modified your code to achieve my task. With the code I tried, seeing below error:

expected IAM user "some user-name" to resolve to unique AWS ID "xxxxx" but got "yyyyy" instead
at org.springframework.vault.authentication.AwsIamAuthentication.createTokenUsingAwsIam(AwsIamAuthentication.java:149)

`
@configuration
public class BootStrapConfig extends AbstractVaultConfiguration{

    @Value("${bin.aws.credentials.file.path}")
    private String credentialsFilePath;

    @Value("${spring.cloud.vault.host}")
    private String vaultHost;

    @Value("${spring.cloud.vault.port}")
    private int vaultPort;

    @Bean
    public ClientAuthentication clientAuthentication() {
        AwsIamAuthenticationOptions options = AwsIamAuthenticationOptions.builder()
                .credentialsProvider(new PropertiesFileCredentialsProvider(credentialsFilePath))
                .serverName(vaultHost)
                .build();
        return new AwsIamAuthentication(options, super.restOperations());
    }
    
    @Override
    public VaultEndpoint vaultEndpoint() {
        return VaultEndpoint.create(vaultHost, vaultPort);
    }
}

`

During login, below headerJson is used with header names and authorization:
GetSignedHeaders String:
{"Authorization":["AWS4-HMAC-SHA256 Credential=My-access-key-id/20180920/us-east-1/sts/aws4_request, SignedHeaders=content-length;content-type;host;x-amz-date;x-vault-aws-iam-server-id, Signature=alphanumericsignaturec26f8473483b5a7576826d56773798a9d4"],
"X-Amz-Date":["20180920T181910Z"],
"Host":["sts.amazonaws.com"],
"Content-Length":["43"],
"X-Vault-AWS-IAM-Server-ID":["vault.lab.myaws.net"],
"Content-Type":["application/x-www-form-urlencoded"]}

Am I missing any required headers or something? Any help would be highly appreciated.

@mp911de
Copy link
Member

mp911de commented Sep 20, 2018

Everything fine in your code.

expected IAM user "some user-name" to resolve to unique AWS ID "xxxxx" but got "yyyyy" instead

looks like hashicorp/vault#2979 and not a Spring Vault/Spring Cloud Vault.

Make sure to use a recent Vault version as the mentioned issue was fixed with 0.8.0.

@sreenivassvs123
Copy link
Author

Thank you for the quick reply. We use Vault version 0.9.5.

@mp911de
Copy link
Member

mp911de commented Sep 21, 2018

In that case, it might be good to file an issue in Vault and report your scenario there. There's nothing we can do from our side.

@mp911de mp911de closed this as completed Sep 21, 2018
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants