Downloading files from multiple file paths with Powershell + WinSCP

Hi everyone!

I have made a script for downloading files and giving them a random name-extension (as i need to download alot of files with the same name, from different remote domain directories, in order to search among their data).

My issue is, that i have to download from several domains, and that part is not working out.
An example of what i need to accomplish:

I need to download wp-config-sample.php from several domains.
Server root:confused:
jonatantest/wp-config-sample-php
jonatantest2/wp-config-sample.php

(the files are then given an extension, allowing me to download several files with the same name to the one folder locally).

$remotePath = “jonatantest/” works fine, but this only lets me download from one domain folder…
$remotePath = (“jonatantest/”,“jonatantest2/”), does not seem to want to work, still trying to merge both paths into one.

Am i approaching this in a stupid way? - Am i missing some way to use Foreach?

Also, my print function of what files have been downloadet does not seem to work, and does not give me an error either?.

I would really appreciate some feedback!

Script:
https://gist.github.com/Jonatantwn/c6e40989061721057c52ef2814653bb2

Yes, you need a loop. Regardless if you see a loop, Powershell is looping for you.

PS C:\Users\rasim> $services = Get-Service | Select -First 5

PS C:\Users\rasim> $services.Name #Implicit Loop

AarSvc_b1099
AESMService
AJRouter   
ALG        
AppIDSvc   
PS C:\Users\rasim> $services | foreach{$_.Name} #Explicit Loop

AarSvc_b1099
AESMService
AJRouter   
ALG        
AppIDSvc   
PS C:\Users\rasim> Get-Service | Select -First 5 | Stop-Service -WhatIf

What if: Performing the operation "Stop-Service" on target "Agent Activation Runtime_b1099 (AarSvc_b1099)".
What if: Performing the operation "Stop-Service" on target "Intel® SGX AESM (AESMService)".
What if: Performing the operation "Stop-Service" on target "AllJoyn Router Service (AJRouter)".
What if: Performing the operation "Stop-Service" on target "Application Layer Gateway Service (ALG)".
What if: Performing the operation "Stop-Service" on target "Application Identity (AppIDSvc)".
PS C:\Users\rasim> 

If you looked at the documentation for Set-Service, Name is using ByValue:

-Name
Specifies the service name of the service to be changed. Wildcard characters aren't permitted. You can use the pipeline to send a service name to Set-Service.

TABLE 7
Type:	String
Aliases:	ServiceName, SN
Position:	0
Default value:	None
Accept pipeline input:	True (ByPropertyName, ByValue)
Accept wildcard characters:	False

If you look at the code (https://github.com/PowerShell/PowerShell/blob/master/src/Microsoft.PowerShell.Commands.Management/commands/management/Service.cs), line 1306 to be exact, there is a loop that processes each Name from the pipeline. Here is something to start:

param (
    $localPath = "C:\Users\Dern\Desktop\WINSCP PS DOWNLOAD\",
    $remotePath = ("jonatantest/","jonatantest2/"),
    $fileName = "wp-config-sample.php"
)
         
try
{
    # Load WinSCP .NET assembly
    Add-Type -Path "C:\Users\Dern\Desktop\WINSCP PS\WinSCPnet.dll"

    # Setup session options
    $sessionOptions = New-Object WinSCP.SessionOptions -Property @{
        Protocol = [WinSCP.Protocol]::ftp
        HostName = "xxx"
        UserName = "xxxx"
        Password = "xxxx"
     }
 
    $session = New-Object WinSCP.Session
 
    try
    {
        # Connect
        $session.Open($sessionOptions)

        foreach ($rp in $remotePath) {
            # Download files
            $transferOptions = New-Object WinSCP.TransferOptions
            $transferOptions.TransferMode = [WinSCP.TransferMode]::Binary
    
            # Format timestamp
            $stamp = $(Get-Random)
    
            # Download the file and throw on any error
            $transferResult =
            $session.GetFiles(
                ($rp + $fileName),
                ($localPath + $fileName + "." + $stamp)).Check()


            # Print results
            foreach ($transfer in $transferResult.Transfers)
            {
                Write-Host "Download of $($transfer.FileName) succeeded"
            }
    }

    }
    finally
    {
        # Disconnect, clean up
        $session.Dispose()
    }
 
    exit 0
}
catch
{
    Write-Host "Error: $($_.Exception.Message)"
    exit 1
}

As far as the print “not working”, you’re enumerating $transferResult.Transfers. Is there anything in $transferResult? Is there a property Transfers? You should be able to run this code in ISE or VSCode and see what is in $transferResult.

Hi Rob!

Thank you a whole bunch for your swift answer, i really appreciate it.

Got me right back on track and i now finished the script intirely!

For anyone else wondering how the final script might look, have a look at:
https://gist.github.com/Jonatantwn/e1b166aea7c0b3a0897f896f80cb5349