powershellaws-cliamazon-ecr

PowerShell passing password to aws cli with pipe operator


I try to log into my AWS ECR repository. This is my powershell script:

param(
    [string]$profile,
    [string]$ecr_name
)


$accountId = (aws sts get-caller-identity --query "Account" --output text --profile $profile)
$region = (aws configure get region --profile $profile)

$TAG = "latest"
$AccountUrl = "${accountId}.dkr.ecr.${region}.amazonaws.com"

Write-Host "LoginAttempt 1"
docker login --username AWS --password $(aws ecr get-login-password --region $region --profile $profile) $AccountUrl

Write-Host "LoginAttempt 2"
aws ecr get-login-password --region $region --profile $profile | docker login --username AWS --password-stdin  $AccountUrl

Write-Host "LoginAttempt 3"
docker login --username AWS --password $(aws ecr get-login-password --region $region --profile $profile) $AccountUrl

When copy-pasting the code into a powershell termin, everything works. When running the code directly using this command:

powershell.exe -File file_location.ps1 --ecr_name yyy --profile xxx

I get this strange behavior:

LoginAttempt 1
WARNING! Using --password via the CLI is insecure. Use --password-stdin.
Login Succeeded
LoginAttempt 2
Error response from daemon: login attempt to https://1234567890.dkr.ecr.eu-west-1.amazonaws.com/v2/ failed with status: 400 Bad Request
LoginAttempt 3
WARNING! Using --password via the CLI is insecure. Use --password-stdin.
Login Succeeded

I am working on a Windows machine, the script is stored in utf8 with LF. For obvious security reasons i would prefer to pass the password using stdin.


Solution

  • Note:


    Your own attempt to provide the password to docker login via stdin (--password-stdin):

    # OK in PowerShell (Core) 7.4+
    aws ecr get-login-password --region $region --profile $profile | 
      docker login --username AWS --password-stdin  $AccountUrl
    

    should work as-is in PowerShell (Core) v7.4+, where data being piped between external (native) programs is now passed as-is, i.e. as raw byte data.

    In v7.3.x-, as well as in Windows PowerShell, a workaround is required, because in these versions:

    The simplest workaround is to shell out to cmd /c, because cmd.exe's pipeline is and always has been a raw byte conduit, so the problem doesn't arise there:

    # Workaround for PowerShell 7.3.x- and Windows PowerShell
    cmd /c "aws ecr get-login-password --region $region --profile $profile | docker login --username AWS --password-stdin `"$AccountUrl`""
    

    Note:


    For additional background information, see this answer.