2

I have the script where I am trying to put my AWS credentials in a remote server using powershell script.

Issue I am facing : Leading zeros of the AWS AccountID (one of the powershell script argument) is not getting retained. I am new to PS script. Need guidance on retaining the zeros of the accountID.

Example -- AccountID -- 000009876543 - Here leading zeros are not getting retained and an entry without zeros gets created in the server. However, 900000876543 is handed successfully.

Script -

$user = $args[7]  #userid   
$pass = $args[8]  #password
$pair = "$($user):$($pass)" #pair

$bytes = [System.Text.Encoding]::ASCII.GetBytes($pair) 
$base64 = [System.Convert]::ToBase64String($bytes)

$basicAuthValue = "Basic $base64"

$headers = @{ Authorization = $basicAuthValue }


$c1=$args[0]
$path=$args[1]
$cert=$args[2]
$p1=$args[3]
$awsacct=$args[4] #account_id
$awsak=$args[5]   #access_key 
$awssk=$args[6]   #secret_key 



$body9="{`"project`": { `"href`": `"/tenants/$c1/projects/$p1`"},`"account`": {`"href`": `"/tenants/$c1/accounts/$awsacct`"},`"credential`":{ `"type`": `"key`",`"accessKey`": `""+$awsak+"`", `"secretKey`": `""+$awssk+"`"}}"

$r=Invoke-WebRequest -uri "$path/tenants/$c1/credentials/$awsak" -Headers $headers -Certificate $cert -ContentType application/json -Method PUT -Body $body9

$r.Content
Sneha
  • 83
  • 1
  • 11
  • 4
    Don't use the automatic variable `$args` but instead define named parameters and define `$awsacct` as a string: `Param( $c1, $path, $cert, $p1, [String]$awsacct, $awsak, $awssk )` – iRon Dec 26 '19 at 09:08
  • @iRon I am running this script in a remote server, we have embedded PS, hence can not define named parameters. We have the arguments and their value and pass it to the powershell embedded script. How can we define the $awsacct as string in the mentioned script? – Sneha Dec 26 '19 at 09:11
  • 1
    I don't see why you can't use `Param` but you can also consider to serialize you parameters, see: https://stackoverflow.com/q/34076478/1701026 – iRon Dec 26 '19 at 09:26
  • 1
    Cast a supplied value to string as follows: `$user = [string]$args[7]` or `$user = "$($args[7])"` or `$user = $args[7] -as [string]`… – JosefZ Dec 26 '19 at 10:25
  • @JosefZ Should the casting be done as [String]$awsacct=$args[4] OR $awsacct=[String]$args[4] ? Also, $user = "$($args[7])" and $user = $args[7] -as [string] does not work – Sneha Dec 26 '19 at 10:40
  • @iRon As mentioned above, we have embedded script in the orchestrator, where we can work with script in terms of variables $args. That's something can not be changed. Args valued are defined and later on we give this argument values to the variables. Please suggest otherwise. – Sneha Dec 26 '19 at 10:45
  • 3
    Then enlighten us more about how you call this script (especially the parameters) using orchestrator. As it is now, the AccountID is treated as a numeric value and you need to send it as string. Another way would be pad the value with zero's in the code like `$awsacct = "$args[4]".PadLeft(12,"0")` or `$awsacct = '{0:000000000000}' -f $args[4]` – Theo Dec 26 '19 at 10:53

2 Answers2

1

Either supply a string value e.g. '000009876543' ("000009876543") instead of numeric value 000009876543, or cast/convert a supplied value to string, see the following self-explained code snippet:

if ( $args.Count -lt 1 ) {
    Write-Verbose 'Supply at least one parameter' -Verbose
    exit
}
Remove-Variable val_* -ErrorAction SilentlyContinue
$val_a = $args[0]               # unchanged
$val_b = [string]$args[0]       # dynamically typed variable
[string]$val_c = $args[0]       # strongly typed variable
$val_d = $args[0] -as [string]  # convert the input object, see about_Type_Operators
$val_e = "$($args[0])"          # wrong: removes leading zeroes

Get-Variable val_* | 
    Select-Object -Property Name,
                            Value,
                            @{ L='type'; E={ $_.Value.GetType().Name } },
                            @{ L='test'; E={ $_.Value * 2 } }

Output:

PS D:\PShell> D:\PShell\SO\59486037.ps1 '000123'

Name  Value  type   test
----  -----  ----   ----
val_a 000123 String 000123000123
val_b 000123 String 000123000123
val_c 000123 String 000123000123
val_d 000123 String 000123000123
val_e 000123 String 000123000123

PS D:\PShell> D:\PShell\SO\59486037.ps1 000123

Name   Value type           test
----   ----- ----           ----
val_a 000123 Int32           246
val_b 000123 String 000123000123
val_c 000123 String 000123000123
val_d 000123 String 000123000123
val_e    123 String       123123
JosefZ
  • 28,460
  • 5
  • 44
  • 83
0

As commented, if you cannot send the arguments using Orchestrator as string, you can always manipulate the integer value inside the code. In your case, the account_id value is sent to the script as $args[4] and in the process it is converted to integer, removing any padding leading zeros.

Since in your organization you use these id's as 12 digit numbers, you can recreate that by using the String.PadLeft method:

$awsacct = $args[4].ToString().PadLeft(12,"0")

or by using the -f format operator:

$awsacct = '{0:000000000000}' -f $args[4]

or for short:

$awsacct = '{0:d12}' -f $args[4]

Using any of the above will result in

      9876543 --> 000009876543
 900000876543 --> 900000876543
Theo
  • 57,719
  • 8
  • 24
  • 41
  • Tested what's mentioned above in local PS and it did not seems to work. /* Script -- $args = 1,3,4,00987654321 $args[3] $aa = "$args[3]".PadLeft(12,"0") $aa Output -- 987654321 1 3 4 987654321[3] */ – Sneha Jan 03 '20 at 14:16
  • @Sneha, You should not use `$args` as a user-defined variable, because that is an [Automatic variable](https://learn.microsoft.com/en-us/powershell/module/microsoft.powershell.core/about/about_automatic_variables?view=powershell-6#args). I have updated the answer to use `$awsacct = $args[4].ToString().PadLeft(12,"0")`. Personally, I like the third example most. – Theo Jan 03 '20 at 14:30