16
votes

I have been trying to create Security Group using AWS SDK, but somehow it fails to authenticate it. For the specific Access Key and Secret Key, i have provided the Administrative rights, then also it fails to validate. On the other side, I tried the same credentials on AWS S3 Example, it successfully executes.

Getting following error while creating security group:

com.amazonaws.AmazonServiceException: AWS was not able to validate the provided access credentials (Service: AmazonEC2; Status Code: 401; Error Code: AuthFailure; Request ID: 1584a035-9a88-4dc7-b5e2-a8b7bde6f43c)
    at com.amazonaws.http.AmazonHttpClient.handleErrorResponse(AmazonHttpClient.java:1077)
    at com.amazonaws.http.AmazonHttpClient.executeOneRequest(AmazonHttpClient.java:725)
    at com.amazonaws.http.AmazonHttpClient.executeHelper(AmazonHttpClient.java:460)
    at com.amazonaws.http.AmazonHttpClient.execute(AmazonHttpClient.java:295)
    at com.amazonaws.services.ec2.AmazonEC2Client.invoke(AmazonEC2Client.java:9393)
    at com.amazonaws.services.ec2.AmazonEC2Client.createSecurityGroup(AmazonEC2Client.java:1146)
    at com.sunil.demo.ec2.SetupEC2.createSecurityGroup(SetupEC2.java:84)
    at com.sunil.demo.ec2.SetupEC2.main(SetupEC2.java:25)

Here is the Java Code:

public class SetupEC2 {
    AWSCredentials credentials = null;
    AmazonEC2Client amazonEC2Client ;

    public static void main(String[] args) {
        SetupEC2 setupEC2Instance = new SetupEC2();
        setupEC2Instance.init();
        setupEC2Instance.createSecurityGroup();
    }

    public void init(){
        // Intialize AWS Credentials
        try {
            credentials = new BasicAWSCredentials("XXXXXXXX", "XXXXXXXXX");
        } catch (Exception e) {
            throw new AmazonClientException(
                    "Cannot load the credentials from the credential profiles file. " +
                            "Please make sure that your credentials file is at the     correct " +
                            "location (/home/sunil/.aws/credentials), and is in valid format.",
                            e);
        }

        // Initialize EC2 instance
        try {
            amazonEC2Client = new AmazonEC2Client(credentials);
            amazonEC2Client.setEndpoint("ec2.ap-southeast-1.amazonaws.com");
            amazonEC2Client.setRegion(Region.getRegion(Regions.AP_SOUTHEAST_1));
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    public boolean createSecurityGroup(){
        boolean securityGroupCreated = false;
        String groupName = "sgec2securitygroup";
        String sshIpRange = "0.0.0.0/0";
        String sshprotocol = "tcp";
        int sshFromPort = 22;
        int sshToPort =22;

        String httpIpRange = "0.0.0.0/0";
        String httpProtocol = "tcp";
        int httpFromPort = 80;
        int httpToPort = 80;

        String httpsIpRange = "0.0.0.0/0";
        String httpsProtocol = "tcp";
        int httpsFromPort = 443;
        int httpsToProtocol = 443;

        try {
            CreateSecurityGroupRequest createSecurityGroupRequest =  new CreateSecurityGroupRequest();
            createSecurityGroupRequest.withGroupName(groupName).withDescription("Created from AWS SDK Security Group");
            createSecurityGroupRequest.setRequestCredentials(credentials);

            CreateSecurityGroupResult csgr = amazonEC2Client.createSecurityGroup(createSecurityGroupRequest);

            String groupid = csgr.getGroupId();
            System.out.println("Security Group Id : " + groupid);

            System.out.println("Create Security Group Permission");
            Collection<IpPermission> ips = new ArrayList<IpPermission>();
            // Permission for SSH only to your ip
            IpPermission ipssh = new IpPermission();
        ipssh.withIpRanges(sshIpRange).withIpProtocol(sshprotocol).withFromPort(sshFromPort).withToPort(sshToPort);
            ips.add(ipssh);

            // Permission for HTTP, any one can access
            IpPermission iphttp = new IpPermission();
        iphttp.withIpRanges(httpIpRange).withIpProtocol(httpProtocol).withFromPort(httpFromPort).withToPort(httpToPort);
            ips.add(iphttp);

            //Permission for HTTPS, any one can accesss
            IpPermission iphttps = new IpPermission();
            iphttps.withIpRanges(httpsIpRange).withIpProtocol(httpsProtocol).withFromPort(httpsFromPort).withToPort(httpsToProtocol);
            ips.add(iphttps);

            System.out.println("Attach Owner to security group");
            // Register this security group with owner
            AuthorizeSecurityGroupIngressRequest authorizeSecurityGroupIngressRequest = new AuthorizeSecurityGroupIngressRequest();
            authorizeSecurityGroupIngressRequest.withGroupName(groupName).withIpPermissions(ips);
            amazonEC2Client.authorizeSecurityGroupIngress(authorizeSecurityGroupIngressRequest);
        securityGroupCreated = true;
        } catch (Exception e) {
            // TODO: handle exception
            e.printStackTrace();
            securityGroupCreated = false;
        }
        System.out.println("securityGroupCreated: " + securityGroupCreated);
        return securityGroupCreated;
    }
}
4
Have permission in S3 doesn't mean you have permission in ec2 and security group. You need check the key again.BMW
Yes i checked the key and also checked on the Policy Simulator for access rights. It shows proper.Sunil Gulabani
then the problem is something else.BMW

4 Answers

23
votes

Try to update your Systemtime.

When the diffrence between AWS-datetime and your datetime are too big, the credentials will not accepted.

For Debian/Ubuntu Users:

when you never set your time-zone you can do this with

sudo dpkg-reconfigure tzdata

Stop the ntp-Service, because too large time diffrences, cannot be changed by running service.

sudo /etc/init.d/ntp stop

Syncronize your time and date (-q Set the time and quit / Run only once) (-g Allow the first adjustment to be Big) (-x Slew up to 600 seconds / Adjuste also time witch large diffrences) (-n Do not fork / process will not going to background)

sudo ntpd -q -g -x -n

Restart service

sudo /etc/init.d/ntp start

check actual system-datetime

sudo date

set system-datetime to your hardware-datetime

sudo hwclock --systohc

show your hardware-datetime

sudo hwclock
1
votes

you must specify the profile and the region aws ec2 describe-instances --profile nameofyourprofile --region eu-west-1

0
votes

If you put your credentials in ~/.aws/credentials then you don't need to provide a parameter to your AmazonEC2Client call. If you do this then on an EC2 instance the same code will work with Assumed STS roles.

For more info see: http://docs.aws.amazon.com/AWSSdkDocsJava/latest/DeveloperGuide/credentials.html

0
votes

"A client error (AuthFailure) occurred when calling the [Fill-in the blanks] operation: AWS was not able to validate the provided access credentials"

  1. If you are confident of the validity of AWS credentials i.e. access key and secret key and corresponding profile name, your date and time being off-track is a very good culprit.

  2. In my case, I was confident but I was wrong - I had used the wrong keys. Doesn't hurt to double check.

  3. Let's say that you created an IAM user called "guignol". Configure "guignol" in ~/.aws/config as follows:

    [profile guignol] region = us-east-1 aws-access-key_id = AKXXXYYY... aws-secret-key-access = ...

Install the aws cli (command level interface) if you haven't already done so. As a test, run aws ec2 describe-instances --profile guignol If you gat an error message that aws was not able to validate the credentials, run aws configure --profile guignol , enter your credentials and run the test command again.