or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

docs

credentials.mdec2rolecreds.mdendpointcreds.mdindex.mdlogincreds.mdprocesscreds.mdssocreds.mdstscreds.md
tile.json

ec2rolecreds.mddocs/

EC2 Instance Role Credentials Provider

Package: github.com/aws/aws-sdk-go-v2/credentials/ec2rolecreds

The ec2rolecreds package provides credential retrieval from Amazon EC2 Instance Roles via the EC2 Instance Metadata Service (IMDS).

Import

import (
    "github.com/aws/aws-sdk-go-v2/credentials/ec2rolecreds"
    "github.com/aws/aws-sdk-go-v2/feature/ec2/imds"
)

Overview

When EC2 instances are launched with an attached IAM role, temporary credentials are made available through IMDS. This provider retrieves those credentials automatically without requiring explicit configuration.

Important: The Provider is not safe for concurrent use. Wrap it with aws.CredentialsCache to provide concurrency safety and credential caching.

Usage Example

Basic Usage

package main

import (
    "context"
    "github.com/aws/aws-sdk-go-v2/aws"
    "github.com/aws/aws-sdk-go-v2/credentials/ec2rolecreds"
    "github.com/aws/aws-sdk-go-v2/feature/ec2/imds"
    "github.com/aws/aws-sdk-go-v2/service/s3"
)

func main() {
    // Create EC2 role credentials provider
    provider := ec2rolecreds.New()

    // Wrap with CredentialsCache for concurrency safety and caching
    credentials := aws.NewCredentialsCache(provider)

    // Use with AWS service clients
    cfg := aws.Config{
        Region:      "us-east-1",
        Credentials: credentials,
    }

    client := s3.NewFromConfig(cfg)
    // Use client
}

Custom IMDS Client Configuration

package main

import (
    "context"
    "net/http"
    "time"
    "github.com/aws/aws-sdk-go-v2/aws"
    "github.com/aws/aws-sdk-go-v2/credentials/ec2rolecreds"
    "github.com/aws/aws-sdk-go-v2/feature/ec2/imds"
)

func main() {
    // Create custom IMDS client
    imdsClient := imds.New(imds.Options{
        HTTPClient: &http.Client{
            Timeout: 5 * time.Second,
        },
    })

    // Create provider with custom IMDS client
    provider := ec2rolecreds.New(func(o *ec2rolecreds.Options) {
        o.Client = imdsClient
    })

    credentials := aws.NewCredentialsCache(provider)
    // Use credentials
}

API Reference

Constants

const ProviderName = "EC2RoleProvider"

Provider name identifier for EC2 role credentials.

New

func New(optFns ...func(*Options)) *Provider

Returns an initialized Provider configured to retrieve credentials from EC2 Instance Metadata service.

Parameters:

  • optFns (...func(*Options)): Functional options for configuring the provider

Returns:

  • *Provider: Initialized EC2 role credentials provider

Example:

// Default configuration
provider := ec2rolecreds.New()

// With custom IMDS client
provider := ec2rolecreds.New(func(o *ec2rolecreds.Options) {
    o.Client = customIMDSClient
})

Options

type Options struct {
    Client            GetMetadataAPIClient
    CredentialSources []aws.CredentialSource
}

Configuration options for the Provider.

Fields:

  • Client (GetMetadataAPIClient): The API client for EC2 IMDS operations. If nil, defaults to the standard EC2 IMDS client
  • CredentialSources ([]aws.CredentialSource): Credential chain information for reporting purposes (not meant to be set directly)

Provider

type Provider struct {
    // Has unexported fields
}

Retrieves credentials from the EC2 service and tracks credential expiration.

Note: Not safe for concurrent use. Wrap with aws.CredentialsCache for production use.

Retrieve

func (p *Provider) Retrieve(ctx context.Context) (aws.Credentials, error)

Retrieves credentials from the EC2 Instance Metadata Service.

Parameters:

  • ctx (context.Context): Context for the request, supports cancellation and timeouts

Returns:

  • aws.Credentials: Retrieved temporary credentials with expiration time
  • error: Error if request fails or unable to extract credentials

Example:

creds, err := provider.Retrieve(context.TODO())
if err != nil {
    log.Fatalf("Failed to retrieve credentials: %v", err)
}

fmt.Printf("Access Key: %s\n", creds.AccessKeyID)
fmt.Printf("Expires: %s\n", creds.Expires)

ProviderSources

func (p *Provider) ProviderSources() []aws.CredentialSource

Returns the credential chain that was used to construct this provider.

Returns:

  • []aws.CredentialSource: Credential source chain for debugging

AdjustExpiresBy

func (p *Provider) AdjustExpiresBy(creds aws.Credentials, dur time.Duration) (aws.Credentials, error)

Adds the specified duration to the credential's expiration time, unless the time until expiration is less than 15 minutes. Returns the credentials even if not updated.

Parameters:

  • creds (aws.Credentials): The credentials to adjust
  • dur (time.Duration): Duration to add to the expiration time

Returns:

  • aws.Credentials: Credentials with potentially adjusted expiration
  • error: Error if adjustment fails

Example:

// Extend credentials expiration by 5 minutes
adjustedCreds, err := provider.AdjustExpiresBy(creds, 5*time.Minute)
if err != nil {
    log.Fatal(err)
}

HandleFailToRefresh

func (p *Provider) HandleFailToRefresh(ctx context.Context, prevCreds aws.Credentials, err error) (aws.Credentials, error)

Extends the credential expiration time if the credentials are expired. If the credentials will not expire within the minimum time, they are returned unchanged. If the credentials cannot expire, the original error is returned.

Parameters:

  • ctx (context.Context): Context for the operation
  • prevCreds (aws.Credentials): Previously retrieved credentials
  • err (error): The error that occurred during refresh attempt

Returns:

  • aws.Credentials: Credentials with potentially extended expiration
  • error: Original error if credentials cannot be extended

Example:

newCreds, err := provider.Retrieve(ctx)
if err != nil {
    // Try to extend previous credentials on failure
    extendedCreds, extErr := provider.HandleFailToRefresh(ctx, prevCreds, err)
    if extErr != nil {
        log.Fatal(extErr)
    }
    newCreds = extendedCreds
}

GetMetadataAPIClient

type GetMetadataAPIClient interface {
    GetMetadata(context.Context, *imds.GetMetadataInput, ...func(*imds.Options)) (*imds.GetMetadataOutput, error)
}

Interface for an EC2 IMDS API client. Allows for custom IMDS client implementations or mocking in tests.

Methods:

  • GetMetadata: Retrieves metadata from EC2 IMDS

Configuration via AWS Shared Config

The EC2 Instance role credentials provider is automatically used by the SDK's default credential chain when no other credential provider is resolved first.

You can explicitly configure it in the AWS shared config file:

[default]
credential_source = Ec2InstanceMetadata

Error Handling

Common error scenarios:

  • Not running on EC2: Provider fails when code runs outside EC2 or without IMDS access
  • No IAM role attached: Instance must have an IAM role attached for credentials to be available
  • Network errors: IMDS endpoint is unreachable
  • Expired credentials: Credentials expire and need refreshing (handled automatically by CredentialsCache)

Example:

creds, err := provider.Retrieve(ctx)
if err != nil {
    if strings.Contains(err.Error(), "no EC2 IMDS role found") {
        log.Fatal("EC2 instance does not have an IAM role attached")
    }
    log.Fatalf("Failed to retrieve credentials: %v", err)
}

Integration with AWS Config

import (
    "context"
    "github.com/aws/aws-sdk-go-v2/config"
    "github.com/aws/aws-sdk-go-v2/service/s3"
)

func main() {
    // Load default config - will use EC2 role credentials if available
    cfg, err := config.LoadDefaultConfig(context.TODO())
    if err != nil {
        panic(err)
    }

    // Create service client
    client := s3.NewFromConfig(cfg)
    // Use client
}

Best Practices

  1. Always wrap with CredentialsCache: The provider is not thread-safe and doesn't cache credentials internally

    provider := ec2rolecreds.New()
    creds := aws.NewCredentialsCache(provider)
  2. Use default credential chain: Prefer using config.LoadDefaultConfig() which includes EC2 role credentials automatically

  3. IMDSv2: The default IMDS client supports both IMDSv1 and IMDSv2. IMDSv2 is recommended for enhanced security

  4. Credential expiration: EC2 role credentials typically expire after 6 hours. CredentialsCache handles automatic refresh

  5. Context timeouts: Use appropriate context timeouts for IMDS requests:

    ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second)
    defer cancel()
    creds, err := provider.Retrieve(ctx)

Credential Lifecycle

  1. Provider queries IMDS for available role credentials
  2. IMDS returns temporary credentials with expiration time
  3. CredentialsCache monitors expiration and refreshes automatically
  4. Credentials typically expire after 6 hours and are refreshed before expiration