Trying to execute ps script on azure vm's using azure automation using the approach defined at
https://stackoverflow.com/a/62258063/1014275. Script below does copy files between azure vm's. Both Vm's are in same subnet and if we run the copy-item command from VM powershell it copies the files to target VM folder. The same script executes successfully with azure automation runbooks, but without copying files.
Script used:
Copy-Item -Path C:\folder\sample.txt -Destination \\\VmHostname\C$\folder -Force
Updated 1: The script throws exception as below.
Failed
VERBOSE: Performing the operation "Copy File" on target "Item: C:\folder\file.txt Destination:
\\vmhostname\C$\folder". Copy-Item : You can't connect to the file share because it's not secure. This share requires the obsolete SMB1
protocol, which is unsafe and could expose your system to attack.
Your system requires SMB2 or higher.
Update 2:
run the below ps command (Solved update 1 issue)
Enable-WindowsOptionalFeature -Online -FeatureName SMB1Protocol
after this we are getting below error
Failed
Copy-Item : Access is denied
At C:\Packages\Plugins\Microsoft.CPlat.Core.RunCommandWindows\1.1.5\Downloads\script17.ps1:1 char:1
+ Copy-Item -Path C:\folder\file.txt -Destination \\vmhostname ...
Any suggestion would be helpful!
Related
We are using Azure automation runbook using hybrid worker and trying to collect information from on-prem vcenter environment. We are using Get-VICredentialStoreItem to logon to vcenter but logon itself using stored credentials is failing from runbook. When I use this script locally on hybrid worker server it works fine.
The error we are getting is that it can't find the path(most likely for xml file) so it can't logon to vcenter server. Screenshot of error is below.
My understanding is that the script runs locally in hybrid worker server so if it is not complaning about path locally then why would this be causing an issue while running from runbook hybrid worker.
$date = get-date -format dd-MM-yyyy
#Load Module and connect to vCenter
Get-Module -Name VMware.PowerCLI.VCenter* -ListAvailable | Import-Module
Get-Module -Name VMware.Sdk* -ListAvailable | Import-Module
Get-Module -Name VMware.VimAutomation.Core | Import-Module
Set-PowerCLIConfiguration -InvalidCertificateAction Ignore -Confirm:$false
Set-PowerCLIConfiguration -Scope User -ParticipateInCEIP $false -Confirm:$false
$Credentials = Get-VICredentialStoreItem -Host "server1.domain.local" -File "\\mgmtserver.domain.local\Credentials\pwd.xml"
Connect-viserver -server "server1.domain.local" -User $Credentials.User -Password $Credentials.Password
$datastore = "\\mgmtserver.domain.local\myshare2\VMware-Corp-Datastores.csv"
#add VMtools details
New-VIProperty -Name ToolsVersion -ObjectType VirtualMachine -ValueFromExtensionProperty 'Config.tools.ToolsVersion' -Force
New-VIProperty -Name ToolsVersionStatus -ObjectType VirtualMachine -ValueFromExtensionProperty 'Guest.ToolsVersionStatus' -Force
#export datastore list
get-datastore | Select Name, Datacenter, CapacityGB, FreeSpaceGB | export-csv $datastore -NoTypeInformation -UseCulture
disconnect-viserver -Server * -confirm:$false
Error screenshot
The system cannot find the path specified.
A command that prompts the user failed because the host program or the command type does not support user interaction. The host was attempting to request confirmation with the following message: Please specify server credential
Found the issue, credentials have to be created using same account that is going to use it in Automation account.
I'm trying to take specific configuration backup in Azure webapp wwwroot folder with below powershell script which was working fine in public App service plan(Standard and Premium) but the same powershell script is not working fine in Private App service plan(Isolated(App service Environment) - I1,I2,I3). Please find the code below.
Code:
Import-Module Kudu-api
$userNm="`$Testapp"
$password="*******"
$token = New-KuduAuthorizationToken $userNm $password
$sitename="Testapp"
Set-Location "C:\Users\admin\Desktop\Backups"
sleep -Seconds 2
Receive-KuduFile $sitename $token '/site/wwwroot/appsettings.json' ./appsettings.json`
Getting the below error when trying the above script in Isolated(I1) appservice plan:
Error : Invoke-RestMethod : The remote name could not be resolved: 'Testapp.scm.azurewebsites.net'
Please suggest how we can resolve this.
Some context: I have a PowerShell script that gets information about users and their licenses on Azure, and then saves that information to CSV file. It works locally. My goal is to have this script automatically run on Azure (I'm trying to do it in an Azure Function App) once a month, and then have the created CSV file be emailed to a specified email. However all I want to figure out right now is how to get the list of users so that the script can at least just run without errors.
I have very little experience with PowerShell and Azure Function Apps, so I'm stuck on a few errors I'm getting. I have spent the last few days troubleshooting to no luck.
Here is the beginning of the script that I can run from my local PowerShell:
Function main()
{
#Clean up session
Get-PSSession | Remove-PSSession
#Connect AzureAD from PowerShell
Connect-MsolService
#Set output file
$ExportCSV=".\DetailedO365UserLicenseReport_$((Get-Date -format yyyy-MMM-dd-ddd` hh-mm` tt).ToString()).csv"
$ExportSimpleCSV=".\SimpleO365UserLicenseReport_$((Get-Date -format yyyy-MMM-dd-ddd` hh-mm` tt).ToString()).csv"
#FriendlyName list for license plan and service - txt file on local computer
$FriendlyNameHash=Get-Content -Raw -Path .\LicenseFriendlyName.txt -ErrorAction Stop | ConvertFrom-StringData
#txt file on local computer
$ServiceArray=Get-Content -Path .\ServiceFriendlyName.txt -ErrorAction Stop
#Hash table declaration
$Result=""
$Results=#()
$output=""
$outputs=#()
$LicensedUserCount=0
#Get all licensed users
Get-MsolUser -All | where{$_.islicensed -eq "true"} | Foreach{
#this is another function that handles grabbing the user info and writing it to the CSV file
Get_UsersLicenseInfo
$LicensedUserCount++
}
. main
With this script above, it requires some user input for entering credentials. I want this script to be able to run automatically in Azure without any user input, so I've been trying to modify it to do that. I found out that any commands with 'Msol' in the name don't work in Azure Function Apps/Powershell Core, so I found a different module that apparently does work.
This is where I'm currently at with the script to be run in my Azure Function App:
Import-Module AzureAD
Function main()
{
#Clean up session
Get-PSSession | Remove-PSSession
$password = ConvertTo-SecureString "{my password here}" -AsPlainText -Force
$UserCredential = New-Object System.Management.Automation.PSCredential ("myusernamehere", $password)
Connect-AzureAD -Credential $UserCredential
#Set output file
$ExportCSV=".\DetailedO365UserLicenseReport_$((Get-Date -format yyyy-MMM-dd-ddd` hh-mm` tt).ToString()).csv"
$ExportSimpleCSV=".\SimpleO365UserLicenseReport_$((Get-Date -format yyyy-MMM-dd-ddd` hh-mm` tt).ToString()).csv"
#FriendlyName list for license plan and service - hash table here
$FriendlyNameHash= #{AAD_BASIC = "Azure Active Directory Basic"; AAD_PREMIUM= "Azure Active Directory Premium"; AAD_PREMIUM_P1= "Azure Active Directory Premium P1"; AAD_PREMIUM_P2= "Azure Active Directory Premium P2" }
#array of strings, used when getting user info
$ServiceArray= "MCOEV", "Cloud PBX", "MCOPSTN2", "PSTN International", "mcomeetadv"
#Hash table declaration
$Result=""
$Results=#()
$output=""
$outputs=#()
$LicensedUserCount=0
Get-AzureADUser -All | where{$_.islicensed -eq "true"} | Foreach{
Get_UsersLicenseInfo
$LicensedUserCount++}
}
. main
First of all I'm not sure if I even need to authenticate if this script is running from within my Azure account. Second of all, and my main issue, is that when I try to run this script in my Azure Function App, I get this error:
snippet of the azure error
If the picture doesn't work, it says:
The Function app may be missing a module containing the 'Connect-AzureAD' command definition. If this command belongs to a module available on the PowerShell Gallery, add a reference to this module to requirements.psd1. Make sure this module is compatible with PowerShell 7. For more details, see https://aka.ms/functions-powershell-managed-dependency. If the module is installed but you are still getting this error, try to import the module explicitly by invoking Import-Module just before the command that produces the error: this will not fix the issue but will expose the root cause.
2021-06-08T16:48:00.377 [Error] ERROR: The term 'Connect-AzureAD' is not recognized as the name of a cmdlet, function, script file, or operable program.Check the spelling of the name, or if a path was included, verify that the path is correct and try again.Exception
I get that same error for the line with 'Get-AzureADUser' as well. I followed this guide: https://tech.nicolonsky.ch/azure-functions-powershell-modules/ to add the AzureAD module to my managed dependencies, but I still get that same error.
If anything needs clarification, let me know. Any help is appreciated!
Actually, AzureAD needs to be imported a bit differently - it's been a problem for a while per this github issue. This seemed to work for most people:
Setting the application to run as x64 bit: Function App>
Configuration > General Settings > Platform > 64 Bit
Setting the app to run on Powershell 7 instead of 6 on this thread
Use: Import-Module AzureAD -UseWindowsPowerShell
I want to download a file that is on my Azure File storage in FileShare into my release pipeline agent.
Inside the release pipeline I am using a PowerShell step and run the command:
Start-AzStorageFileCopy -SrcShareName "report.xml" -SrcFilePath "." -DestFilePath "$(System.DefaultWorkingDirectory)" -DestShareName "report.xml" -Context $(context)
its asking me now for a parameter -name
2020-05-09T01:43:34.1007773Z ##[error]Cannot process command because of one or more missing mandatory parameters: Name.
Basically my plan is to use this file for a test report in a release pipeline. Therefore I need this file to be used in a Publish Test Result step.
Since you are trying to download single report.xml file from Azure File Share, directly use Get-AzureStorageFileContent command.
Sample:
$ctx = New-AzureStorageContext [storageaccountname] [storageaccountkey]
##sharename is your existed name.
$s = Get-AzureStorageShare [sharename] –Context $ctx
##To download a file from the share to the local computer, use Get-AzureStorageFileContent.
Get-AzureStorageFileContent –Share $s –Path [path to file on the share] [path on local computer]
If you want to download multiple files using one command, you could use Azcopy.
More detail info please take a look at this blog.
You are looking to download the file locally from the release agent job, so i would stick to using this command below:
Get-AzStorageFileContent -Context $Context -ShareName "acishare" -Path "report.xml" -Destination $(System.DefaultWorkingDirectory)
My (dotNET) application is built (using a Windows Hosted agent), from a build pipeline, and in the subsequent Release pipeline, I provision a 16GB-Win2016 VM (enabling RDP, HTTP, HTTPS, WinRM and SSH), into which I RDP manually (there is a Manual Intervention task here), and configure WinRM (following this article: https://learn.microsoft.com/en-us/azure/marketplace/cloud-partner-portal/virtual-machine/cpp-configure-winrm-after-vm-creation#configure-vm-to-enable-winrm). Everything is fine until here. The next task is a Azure File Copy task, which essentially copies the Build artifacts (from $(System.DefaultWorkingDirectory)) and pastes into a directory I specify. Works like a charm. The next task I have is to create a VHD of this whole VM (essentially after the copying is done).
I know I can manually RDP into the VM (again) and sysprep (with oobe/generalize/shutdown), then maybe go back to the Azure Portal and Disk Export the OS Disk (specifying the SAS URL expiration time at whatever (36000 per the article)) BUT can this all be automated?
So, long story short - I'd like to know if sysprep oobe/generalize/shutdown can be performed remotely preferably over a PS task. I understand the other part of it (exporting the disk and all) can be, but if sysprep can be done remotely nothing like it.
I tried this and got what I wanted:
$sysprep= 'C:\Windows\System32\Sysprep\Sysprep.exe'
$arg1 = '/generalize'
$arg2 = '/oobe'
$arg3 = '/shutdown'
$arg4 = '/quiet'
& $sysprep $arg1 $arg2 $arg3 $arg4 -Wait
Make sure you do NOT use Azure custom script extension to run sysprep.
Azure scripts run under the LocalSystem user context: source
Custom Script Extension will run under the LocalSystem Account
This is problematic because sysprep does NOT support running under a system user context: source
Sysprep cannot be run under the context of a System account. Running Sysprep under the context of System account by using Task Scheduler or PSExec, for example, is not supported.
Providing this so that people avoid my mistake :)
So, you dont have to configure winrm manually, you can script it\configure it while provisioning the vm. and if\when winrm is working you can just use powershell remoting to issue a command against the vm with:
Invoke-Command -ComputerName dnsname\ipaddress_goes_hehe
-ScriptBlock { sysprep /shutdown /generalise}
https://github.com/Azure/azure-quickstart-templates/tree/master/201-vm-winrm-windows
You can implement this using an Azure custom script extension. There is a github project:
https://github.com/jlongo62/AzureVMToImage containing powershell scripts to image a VM. These scripts were built to preserve VM when creating an image, instead of destroying the original VM. The scripts can be called from Azure Devops. There is no need to authenticate against the VM.
The meat of what you need is:
1- create a storageaccount blob containing the following script (the -Wait is very important):
Start-Process -FilePath C:\Windows\System32\Sysprep\Sysprep.exe -ArgumentList '/generalize /oobe /quiet /quit' -Wait
2 - invoke it on the VM:
$response = Set-AzureRmVMCustomScriptExtension `
-ResourceGroupName $vm.ResourceGroupName `
-VMName $vm.Name `
-Location $vm.Location `
-Name $ExtensionName `
-FileUri $blobUri `
-Run $FileName