Page 1 of 2

Using Start-Job with credentials

Posted: Thu Apr 11, 2019 10:42 am
by Shelltastic
I am looking for some assistance using the Start-Job cmdlet. I am trying to run a background job to query some data from my Exchange environment. I need to build the connection to Exchange first, I currently use the following code to do so...

Code: Select all

$usercred = Get-Credential
$s = New-PSSession -ConfigurationName Microsoft.Exchange -ConnectionUri http://ServerName.domain.com/PowerShell/ -Credential $usercred -Authentication Kerberos
Import-Module (Import-PSSession $s -AllowClobber) -DisableNameChecking
This code will not work inside the scriptblock for Start-Job since it's a different thread and will not allow me to interact with it. What methods could I look at to go about connecting to my Exchange environment so I can query data inside the Start-Job scriptblock?

Re: Using Start-Job with credentials

Posted: Thu Apr 11, 2019 12:21 pm
by davidc
[TOPIC MOVED TO WINDOWS POWERSHELL FORUM BY MODERATOR]

Re: Using Start-Job with credentials

Posted: Thu Apr 11, 2019 1:12 pm
by jvierra
You would have to run all of your code as a job. Why use a job? The connection only takes 10 seconds even on a slow computer.

Your scriptblock is also not written correctly which may cause many weird issues.

Code: Select all

$usercred = Get-Credential
$s = New-PSSession -ConfigurationName Microsoft.Exchange -ConnectionUri http://ServerName.domain.com/PowerShell/ -Credential $usercred -Authentication Kerberos
Import-PSSession $s -AllowClobber

Re: Using Start-Job with credentials

Posted: Thu Apr 11, 2019 1:16 pm
by jvierra
I would also suggest this for ease of management and simplicity:

Code: Select all


$splat = @{
    ConfigurationName = 'Microsoft.Exchange'
    ConnectionUri = 'http://ServerName.domain.com/PowerShell/'
    Credential = 'domain\userid'
    AllowClobber = $true
}
$s = New-PSSession @splat
Import-PSSession $s 
Credentials are automatically prompted.

Re: Using Start-Job with credentials

Posted: Thu Apr 11, 2019 2:44 pm
by Shelltastic
jvierra wrote: Thu Apr 11, 2019 1:12 pm You would have to run all of your code as a job. Why use a job? The connection only takes 10 seconds even on a slow computer.

Your scriptblock is also not written correctly which may cause many weird issues.

Code: Select all

$usercred = Get-Credential
$s = New-PSSession -ConfigurationName Microsoft.Exchange -ConnectionUri http://ServerName.domain.com/PowerShell/ -Credential $usercred -Authentication Kerberos
Import-PSSession $s -AllowClobber
I'm aware that the connection runs rather quickly, that is not the part I am worried about, and it is not written incorrectly, I run it a dozen times a day, you may chose to modify it, but it runs with the desired result as per my configuration requires.

I am trying to query large amounts of data in my Exchange environment, that is the code I use to build the connection from my local PC, I can't just run the Exchange cmdlet's in the Start-Job script block because the Exchange module needs to be loaded, which gets pulled down upon making the connection. My issue is, I can't just run the connection code I posted above in the Start-Job script block because I need it to prompt for my credentials so I can enter them. So I am trying to figure out the best approach to this here, which is the help I am asking for.

Re: Using Start-Job with credentials

Posted: Thu Apr 11, 2019 3:16 pm
by jvierra
You can pass the credentials to the script block easily enough.

Re: Using Start-Job with credentials

Posted: Thu Apr 11, 2019 4:00 pm
by jvierra
Since you are already in a domain and using Kerberos you can very easily just do this.

Code: Select all


$sb = {
    $splat = @{
        ConfigurationName = 'Microsoft.Exchange'
        ConnectionUri = 'http://ServerName.domain.com/PowerShell/'
        AllowClobber = $true
    }
    $s = New-PSSession @splat
    Import-PSSession $s
    # other code
}
Start-Job -ScriptBlock $sb -Credential domain\userid

Re: Using Start-Job with credentials

Posted: Fri Apr 12, 2019 5:26 am
by Shelltastic
jvierra wrote: Thu Apr 11, 2019 4:00 pm Since you are already in a domain and using Kerberos you can very easily just do this.

Code: Select all


$sb = {
    $splat = @{
        ConfigurationName = 'Microsoft.Exchange'
        ConnectionUri = 'http://ServerName.domain.com/PowerShell/'
        AllowClobber = $true
    }
    $s = New-PSSession @splat
    Import-PSSession $s
    # other code
}
Start-Job -ScriptBlock $sb -Credential domain\userid
Ok, thanks for the help on that one. I actually prompt the user for their credentials at the start of my program. Is there any way I could take those credentials already entered and just pass them through here? In your example above, the user is prompted. It wouldn't scale very well if I had to make the user enter their credentials every time I try to run a job.

Re: Using Start-Job with credentials

Posted: Fri Apr 12, 2019 8:28 am
by Shelltastic
Here is an example of what I have...

Code: Select all

	$sb = {
		$splat = @{
			ConfigurationName = 'Microsoft.Exchange'
			ConnectionUri	  = 'http://ServerName.doamin.com/PowerShell/'
			AllowClobber	  = $true
		}
		$s = New-PSSession @splat -Credential $global:usercred -Authentication Kerberos
		Import-PSSession $s
		
		(Get-MailboxDatabase | where { $_.MasterServerOrAvailabilityGroup -eq "DAG1" }).count
	}
	
	Start-Job -Name Job1 -ArgumentList $global:usercred -ScriptBlock $sb
	
	$Job1Results = Receive-Job 'Job1'
The $global:usercred variable looks like this...

Code: Select all

$global:usercred = Get-Credential
$s = New-PSSession -ConfigurationName Microsoft.Exchange -ConnectionUri http://ServerName.domain.com/PowerShell/ -Credential $global:usercred -Authentication Kerberos
Import-Module (Import-PSSession $s -AllowClobber) -DisableNameChecking

Re: Using Start-Job with credentials

Posted: Fri Apr 12, 2019 11:12 am
by jvierra
Just pass the credential object as the job credential.

Code: Select all

$sb = {
    $splat = @{
        ConfigurationName = 'Microsoft.Exchange'
        ConnectionUri     = 'http://ServerName.doamin.com/PowerShell/'
        AllowClobber      = $true
    }
    $s = New-PSSession @splat
    Import-PSSession $s
    
    (Get-MailboxDatabase | Where-Object { $_.MasterServerOrAvailabilityGroup -eq "DAG1" }).count
}

Start-Job -Name Job1 -Credential $global:usercred -ScriptBlock $sb

$Job1Results = Receive-Job 'Job1'
You do not need to use the credential in the job if the job is running with the correct credential. You don't need to specify the authentication as that will be automatic.