Trouble with -TargetPath

I am pretty new at powershell but I am trying to write a script to gather all the Domain Controllers and then Loop through them adding a new DFSN Root Target. I can’t my current object to resolve correctly in the -TargetPath parameter of the script. I can get it to work if I replace the variable manually. I am totally lost on this by now and would love some help.

#Get a list of all Domain Controllers
Get-ADDomainController -Filter * | Select Name |

#Start For-Each Loop
% {

#Displays the server currently being accessed
write-host “Starting Process on:” $_.name

#Create a new directory
invoke-command -computername $_.name -scriptBlock {new-item C:\DFSRoots\UsersNetBackup -type directory}

#Share the Directory
invoke-command -computername $_.name -scriptBlock {new-smbshare -name UsersNetBackup -Path C:\DFSRoots\UsersNetBackup -FullAccess Everyone}

#Add current server to the DFS using the new directory and share just created
invoke-command -computername $.name -scriptBlock {new-DfsnRootTarget -Path “\yourdomain\UsersNetBackup” -TargetPath "\$($.name)\UsersNetBackup"}

[blockquote]the above line is where my script errors out
[/blockquote]

#Shows the current server again after everything is done.
Write-Host “Done with Processes on:” $_.name
}

#Everyting is done. If there are no errors, you did a good job :slight_smile:
Write-Host “Done will all servers”

I think this is one of the powershell “Gotchas”. The problem is variables created outside the scriptblock curly braces aren’t recognized inside the braces. Therefore you have to pass it the variable as you would a parameter to a function. Example:

Invoke-Command -ComputerName $_.Name -ScriptBlock { param($ServerName); New-DfsnRootTarget -Path "\\yourdomain\UsersNetBackup" -TargetPath "\\$Servername\UsersNetBackup" } -ArgumentList $_.Name

Notice how outside the braces the server’s name is represented as “$_.Name”. Then it’s passed in to the scriptblock as an argument and loaded into a new variable called “$ServerName” via the param block.

For more info on variable scope type this in your shell:

Get-Help about_scopes

You are a life saver Jeff :slight_smile:

I was reading through the about_scopes as you indicated and noticed that the method your suggest is from Powershell 2 and there is a newer way (both should work though). I am pasting Example 5 from the help file for reference. I will test all this today and let everyone know the results:

Example 5: Using a Local Variable in a Remote Command

   To indicate that a variable in a remote command was created in the 
   local session, use the Using scope modifier. By default, Windows
   PowerShell assumes that the variables in remote commands were created
   in the remote session.

   The syntax is:
       $Using:       

   For example, the following commands create a $Cred variable in the
   local session and then use the $Cred variable in a remote command: 

       $Cred = Get-Credential
       Invoke-Command $s {Remove-Item .\Test*.ps1 -Credential $Using:Cred}  
   
   The Using scope was introduced in Windows PowerShell 3.0.

   In Windows PowerShell 2.0, to indicate that a variable was created in
   the local session, use the following command format.            
   
       $Cred = Get-Credential
       Invoke-Command $s {param($c) Remove-Item .\Test*.ps1 -Credential $c} -ArgumentList $Cred

Thanks again Jeff,

I was able to get the script to work using the Powershell 3 commands. I had to assign a variable to $_.name to using inside the scriptblock but it worked here is the completed script:

#Get a list of all Domain Controllers
Get-ADDomainController -Filter * | Select Name |

#Start For-Each Loop
% {

#Displays the server currently being accessed
write-host “Starting Process on:” $_.name

#Create a new directory
invoke-command -computername $_.name -scriptBlock {new-item C:\DFSRoots\UsersNetBackup -type directory}

#Share the Directory
invoke-command -computername $.name -scriptBlock {new-smbshare -name UsersNetBackup -Path C:\DFSRoots\UsersNetBackup -FullAccess Everyone}
$Currentcomputer = $
.name

[blockquote]Above is the new variable[/blockquote]

#Add current server to the DFS using the new directory and share just created
invoke-command -computername $_.name -scriptBlock {New-DfsnRootTarget -Path “\yourdomain\UsersNetBackup” -TargetPath “\$($Currentcomputer)\UsersNetBackup” $Using:Currentcomputer}

[blockquote]Notice the powershell 3 commands at the end of the scriptblock[/blockquote]

#Shows the current server again after everything is done.
Write-Host “Done with Processes on:” $_.name
}

#Everyting is done. If there are no errors, you did a good job :slight_smile:
Write-Host “Done Creating Namespace Servers”

Great! Glad you got it. In my environment, the vast majority of my Win7 machines are still on PoSh 2.0 so even though there are way more delicious features in 3, 4 and 5 I generally stick to what is most compatible.