Using Azure File Services to Deploy Applications on Remote Computers

If you read my other posts recently then you know I have been doing some Office 365 migrations lately. There are a lot of moving parts with the projects. Today I would like to talk about one more of those moving parts and how we used Azure Files Services to solve it. I used Shares Access Signatures to create temporary storage rights. This is great and worked for us because you don’t have to log in.

With this project, we used a tool called Skykick. Skykick is great for this as it allows you to migrate the mail in the background. It also can install an agent on the machine and handle the reconfiguring of Outlook. If you have an Active Directory domain you can deploy it through a GPO. The problem we had is that 70% of the workforce were remote employees. This section of the workforce were also not computer savy. We came up to a problem where deploying the application without a connection to the domain controller.

Enter Azure File Services

The one main tool that we did have is a RMM tool called Continuum. Continuum’s scripting platform suffers in comparison to its competitors. Kaseya, Labtech, and most other RMM tools allow you to have a central file repository. You put a file on the server and then push it to the client. Once at the client you can execute the file to install. Continuum does not have this capability but it does allow us to execute Powershell scripts on the client.

Setting up Azure

The first thing that you will need to do is setup your Azure account with a valid subscription. Once you have a valid subscription in Azure install the AzureRM module on your computer using install-module azurerm. Once you have the module installed you now need to log in to Azure using Powershell. Use the Login-AzureRmAccount cmdlet to do this.

Setting up the storage

Now that you are connected to Azure it is time to setup the storage. We are going to create a new resource group called skykickrg in the EastUS region. You can choose whatever region is closest to you. The storage that we used is Standard Locally Redundant Storage and you can use whatever is best for you. We used this because we have no need to keep the storage long term. Then we use the New-AzureRMStorageAccount cmdlet to create the storage account in Azure.

$location = “eastus”
$storageAccountName = “skykickcontoso”
$resourceGroupName = “skykickrg”
$storageSku = 'Standard_LRS'
New-AzureRmResourceGroup -Name $resourcegroupname -Location $location
New-AzureRmStorageAccount -ResourceGroupName $resourcegroupName -Name $storageAccountName -Location $location -SkuName $storageSku

Creating new container and access policy

We need to get the storage account key. We will use the Get-AzureRMStorageAccountKey cmdlet to get it. We will then use the key to create the storage context. Now that we have the key and context created we can now create the storage container. We will create on called skykickdeploy using the New-AzureStorageContainer cmdlet. We will set the expire date to today’s date plus one year. If you have real security concerns then you will want to set this to a much smaller range. I set it like this because I only needed it for a day. I personally removed it the next day. Last, we need to created the stored access policy. To do this, we use New-AzureStorageContainerStoredAccessPolicy. That is a long worded cmdlet!!

$storageAccountKey = (Get-AzureRmStorageAccountKey -ResourceGroupName $resourceGroupName -Name $storageAccountName).Value[0]
$storageContext = New-AzureStorageContext -StorageAccountName $storageAccountName -StorageAccountKey $storageAccountKey
$storageContainer = New-AzureStorageContainer -Name skykickdeploy -Context $storageContext
$storagePolicyName = “skykick-policy”
$expiryTime = (Get-Date).AddYears(1)
New-AzureStorageContainerStoredAccessPolicy -Container skykickdeploy -Policy $storagePolicyName -Permission rl -ExpiryTime $expiryTime -Context $storageContext

Creating storage context

We are first going to create a SAS token and then use that to create the client context. Do not skip this step it is absolutely necessary!

$sasToken = (New-AzureStorageContainerSASToken -Name skykickdeploy -Policy $storagePolicyName -Context $storageContext).substring(1)
$containerName = 'skykickdeploy'
$clientContext = New-AzureStorageContext -SasToken $sasToken -StorageAccountName $StorageAccountName

Uploading files

We placed the two Skykick files in c:\temp. Now we are going to use the Get-ChildItem cmdlet to get the files. Then we will use the Set-AzureStorageBlobContent cmdlet to place the 2 files into the storage container.

$localpath = 'c:\temp'
Get-ChildItem $localpath -File -Recurse | Set-AzureStorageBlobContent -Container $containername -context $clientContext

Downloading and installing the app from the client

Now we have our files in a container on Azure. We have a Shared Access Signature policy that will live for one year that we can use to access it. Now take a moment to get the contents of the $sasToken variable and overwrite mine below. Don’t worry, I have deleted my resource group and giving you my key is useless. Not to mention I changed the characters!!

You can do this how you want but this is how I did it since we use Continuum. I created a custom Powershell script. I put the below script in that script. We need to install the Azure module so that is how we start. Next we will initialize our variables with the information that we need. Since you are not logging into Azure from each computer you will need the SAS token and the name of the files. If you were logging in you could get this dynamically but logging in defeats the purpose. It also would be very very insecure to pass your Azure credentials in clear text to each computer. Also to store them in a Continuum script.

install-module azurerm
$sasToken = 'sv=2017-07-29&sr=c&si=skykick-policy&sig=6%2FB%2DE5gjncNukdd9jr%497RS554egvau2sYHJ5UB3lhZ8f4o%3D'
$storageAccountName = “skykickcontoso”
$containerName = 'skykickdeploy'
$localpath = 'c:\temp'
$BlobName1 = "outlookassistant.msi" 
$BlobName2 = "mapi64helper.msi" 
$clientContext = New-AzureStorageContext -SasToken $sasToken -StorageAccountName $StorageAccountName

Now we will utilize the Get-AzureStorageBlobContent cmdlet to download each file. Once the files are downloaded you can use Start-Process to start msiexec.exe to install the files.

Get-AzureStorageBlobContent -Blob $BlobName1 -Container $containerName -Destination $localpath -Context $clientContext
Get-AzureStorageBlobContent -Blob $BlobName2 -Container $containerName -Destination $localpath -Context $clientContext
Start-Process msiexec.exe -Wait -ArgumentList "/I C:\temp\$BlobName1 /qn"
Start-Process msiexec.exe -Wait -ArgumentList "/I C:\temp\$BlobName2 /qn"

Skykick agents are now installed. Have your users log in and begin the process to prep the machine for the cutover. Hope this helps! Thanks for reading!!

Here is the full code, enjoy!!!….

$location = “eastus”
$storageAccountName = “skykickcontoso”
$resourceGroupName = “skykickrg”
$storageSku = 'Standard_LRS'
New-AzureRmResourceGroup -Name $resourcegroupname -Location $location
New-AzureRmStorageAccount -ResourceGroupName $resourcegroupName -Name $storageAccountName -Location $location -SkuName $storageSku

$storageAccountKey = (Get-AzureRmStorageAccountKey -ResourceGroupName $resourceGroupName -Name $storageAccountName).Value[0]
$storageContext = New-AzureStorageContext -StorageAccountName $storageAccountName -StorageAccountKey $storageAccountKey
$storageContainer = New-AzureStorageContainer -Name skykickdeploy -Context $storageContext
$storagePolicyName = “skykick-policy”
$expiryTime = (Get-Date).AddYears(1)
New-AzureStorageContainerStoredAccessPolicy -Container skykickdeploy -Policy $storagePolicyName -Permission rl -ExpiryTime $expiryTime -Context $storageContext

$sasToken = (New-AzureStorageContainerSASToken -Name skykickdeploy -Policy $storagePolicyName -Context $storageContext).substring(1)
$containerName = 'skykickdeploy'
$clientContext = New-AzureStorageContext -SasToken $sasToken -StorageAccountName $StorageAccountName

$localpath = 'c:\temp'
Get-ChildItem $localpath -File -Recurse | Set-AzureStorageBlobContent -Container $containername -context $clientContext

Downloading and installing the app from the client

install-module azurerm
$sasToken = 'sv=2017-04-17&sr=c&si=skykick-policy&sig=VOCWZTe1SXdZ10hf6Z4IcB920HCoorgo5nksq4h4%2BYM%3D'
$storageAccountName = “skykickcontoso”
$containerName = 'skykickdeploy'
$localpath = 'c:\temp'
$BlobName1 = "outlookassistant.msi" 
$BlobName2 = "mapi64helper.msi" 
$clientContext = New-AzureStorageContext -SasToken $sasToken -StorageAccountName $StorageAccountName
Get-AzureStorageBlobContent -Blob $BlobName1 -Container $containerName -Destination $localpath -Context $clientContext
Get-AzureStorageBlobContent -Blob $BlobName2 -Container $containerName -Destination $localpath -Context $clientContext
Start-Process msiexec.exe -Wait -ArgumentList "/I C:\temp\$BlobName1 /qn"
Start-Process msiexec.exe -Wait -ArgumentList "/I C:\temp\$BlobName2 /qn"

Leave a Reply

Your email address will not be published.