how to seed data in table storage? - c#

How do we seed table storage tables in order to automate the deployment process?
We've got the following resources all in the same resource group in our dev subscription:
storage account
events in the storage account for blob created
config data in table storage
function app
logic app
In order to automate the deployment of these resources, I've downloaded the ARM template from the resource group:
We can then simply redeploy to any destination resource group:
However, this will not deploy resources like the storage tables, events, seeding data into the tables.
How do we automatically seed table storage tables in order to automate the deployment?

Do something like this.
In your project check in your CSV file
In your build definition add a step to copy files - https://learn.microsoft.com/en-us/azure/devops/pipelines/tasks/utility/copy-files?view=azure-devops&tabs=yaml
In your release pipeline run your PS script like I mentioned in my comment above - https://learn.microsoft.com/en-us/azure/devops/pipelines/tasks/utility/powershell?view=azure-devops
You can use something like this for your PS script to load the csv file
# Load the CSV
$csv = Import-CSV $PSScriptRoot'\yourSeedData.csv'
# And push it to storage
ForEach ($line in $csv)
{
$entity = New-Object -TypeName Microsoft.WindowsAzure.Storage.Table.DynamicTableEntity -ArgumentList $line.PartitionKey, $line.RowKey
if($line.Description -ne $null) {
$entity.Properties.Add("Property1", $line.Property1)
}
$entity.Properties.Add("Property2", $line.Property2)
$result = $table.CloudTable.Execute([Microsoft.WindowsAzure.Storage.Table.TableOperation]::InsertOrReplace($entity))
}

I went with this option to seed data automatically using powershell:
$partitionKey1 = "partition1"
$partitionKey2 = "partition2"
# add four rows
Add-AzTableRow `
-table $cloudTable `
-partitionKey $partitionKey1 `
-rowKey ("CA") -property #{"username"="Chris";"userid"=1}
Add-AzTableRow `
-table $cloudTable `
-partitionKey $partitionKey2 `
-rowKey ("NM") -property #{"username"="Jessie";"userid"=2}
Add-AzTableRow `
-table $cloudTable `
-partitionKey $partitionKey1 `
-rowKey ("WA") -property #{"username"="Christine";"userid"=3}
Add-AzTableRow `
-table $cloudTable `
-partitionKey $partitionKey2 `
-rowKey ("TX") -property #{"username"="Steven";"userid"=4}

Related

How to check whether folder exists on multiple servers?

I have written below PowerShell script in one server to search for folder existence in other servers.
$Servers = Get-Content C:\scripts\serverlist.txt
foreach ($Server in $Servers) {
$Test = Test-Path -Path "\\$Server\c$\Documents and Settings\"
if ($Test -eq $true) {
Write-Host "Path exists on $Server."
} else {
Write-Host "Path NOT exist on $Server."
}
}
I am getting correct answer if I search for folders present in same server, but if I search for folders present in other server am getting "Path NOT exist on $Server" even though it is present.
Later I tried this one. With this also am facing the same issue
Get-Content c:\Users\jason\Documents\Scripts\Serverlist.txt |
Select-Object #{Name='ComputerName';Expression={$_}},
#{Name='FolderExist';Expression={Test-Path "\\$_\c$\program files\folder"}}
Also, please let me know if there is any method for this using C#.

How Do I Configure Changable Connection Strings in a Powershell Binary Module?

I have a PowerShell module I wrote in C# which using Entity Framework to access a MS SQL server. In my project I have created a module.psd1 file. This file specifies a script (LoadAppConfig.ps1) to run before loading the dll. The script reads app.config and adds the connection string to the current app domain.
Is there a better way to do this? I know some modules can take parameters when you load them, but I haven't been able to find a way to implement this in C#. Or, is there a way to embed a default value in the module, which can be changed by a cmdlet? I would like to avoid having to recompile the module to change data sources if possible.
LoadAppConfig.ps1
Add-Type -AssemblyName System.Configuration
$path = $PSScriptRoot
$configPath = Join-Path -Path $path -ChildPath "App.Config"
$connectionstrings = [System.Configuration.ConfigurationManager]::ConnectionStrings
$collection = [System.Configuration.ConfigurationElementCollection]
$field = $collection.GetField(
"bReadOnly",
[System.Reflection.BindingFlags]::NonPublic -bor [System.Reflection.BindingFlags]::Instance)
$field.SetValue($connectionstrings, $false)
[xml]$xml = gc $configPath
$name = $xml.configuration.connectionStrings.add.name
$newconnectionstring = $xml.configuration.connectionStrings.add.connectionString
$provider = "System.Data.EntityClient"
if ($connectionstrings.name -notcontains $name)
{
$Entities = [System.Configuration.ConnectionStringSettings]::new($name, $newconnectionstring, $provider)
$connectionstrings.add($Entities)
}

How to update url stored in Sharepoint add-in app file?

I created an High-Trust add-in for SharePoint 2013 with custom ribbon action and custom menu action.
For this, I have an ASP.NET MVC WebSite with the methods in the controller which match with the virtual urls put as custom action url. So, in the different elements.xml files, I filled action urls using the token 'remoteUrl', so no problem with the mapping.
When i create a package with VS2013, I write the url of my website which is on VM reachable from SP Server, and the client ID (I got from SP while registring my app). When I click on 'Finish', VS2013 generates a file '.app' which can be imported in SP online store or SP internal store.
Here is my problem, if I need to change the address of my website (which is stored in the app file, VS2013 just replaces the token 'RemoteUrl' with the url I give to it), is there any clean way to update the app file or may be if possible, directly the app stored in the SP application store (local to the server) ?
I found nothing for this problem. I saw few things about updating app with events and web services, but I didn't understood.
[EDIT] : I didn't understood that I have to change app version each time I need to update it that's why It didn't worked. Also, it seems that there is no other way to update the url in app file than modifying the AppManifest.xml in app file (which is a zip).
In one of my projects we used to do it with the following PowerShell script. It extracted the app file (it's just a ZIP) and modified multiple nodes in the manifest XML.
For packaging it uses a local copy of 7zip.
function ModifyAppPackage($appPackagePath, $applicationUrl, $clientId){
[Reflection.Assembly]::LoadWithPartialName("System.IO.Compression.FileSystem");
$item = get-item $appPackagePath;
$zipFilePath = Join-Path $item.Directory.FullName $($item.BaseName + ".zip");
Copy-Item $item $zipFilePath;
$unzipDirectory = Join-Path $PSScriptRoot "\Temp";
New-Item -ItemType Directory -Force -Path $unzipDirectory;
if (Test-Path -Path $unzipDirectory\*)
{
Remove-Item $unzipDirectory\* -Force -Confirm:$false -Recurse:$true;
}
[System.IO.Compression.ZipFile]::ExtractToDirectory($zipFilePath, $unzipDirectory);
$modifiedFile = Join-Path $unzipDirectory "modified.txt"
if (Test-Path -Path $modifiedFile)
{
$modifiedContent = Get-Content $modifiedFile
if ($modifiedContent -eq $applicationUrl)
{
Remove-Item $unzipDirectory -Confirm:$false -Recurse:$true;
Remove-Item $zipFilePath;
return;
}
Remove-Item $modifiedFile;
}
$modifiedFileContent = $applicationUrl;
$modifiedFileContent >> $modifiedFile;
$manifestFileName = "AppManifest.xml";
$manifestFilePath = Join-Path $unzipDirectory $manifestFileName;
$manifestXml = [xml](get-content $manifestFilePath);
$nameSpaceManager = New-Object System.Xml.XmlNamespaceManager($manifestXml.NameTable);
$nameSpaceManager.AddNamespace("ns", $manifestXml.DocumentElement.NamespaceURI);
$startPageElement = $manifestXml.SelectSingleNode("/ns:App/ns:Properties/ns:StartPage", $nameSpaceManager);
$StartPage = $applicationUrl + "?{StandardTokens}"
$startPageElement.'#text' = $StartPage
$InstalledEventEndpointElement = $manifestXml.SelectSingleNode("/ns:App/ns:Properties/ns:InstalledEventEndpoint", $nameSpaceManager);
$InstalledEventEndpoint = $applicationUrl + "/Services/AppEventReceiver.svc"
$InstalledEventEndpointElement.'#text' = $InstalledEventEndpoint
$clientIdElement = $manifestXml.SelectSingleNode("/ns:App/ns:AppPrincipal/ns:RemoteWebApplication", $nameSpaceManager);
$clientIdElement.ClientId = $clientId;
$manifestXml.Save($manifestFilePath);
if (Test-Path -Path $zipFilePath)
{
Remove-Item $zipFilePath;
}
$pathToZipExe = $("$PSScriptRoot\7za.exe");
[Array]$arguments = "a", "-tzip", "$zipFilePath", "$unzipDirectory\*.*", "-r";
& $pathToZipExe $arguments;
# Cleanup
Remove-Item $unzipDirectory -Confirm:$false -Recurse:$true;
Remove-Item $appPackagePath -Confirm:$false;
# Rename new zip to .app
Rename-Item $zipFilePath $appPackagePath -Force -Confirm:$false;
return $true;
}
I think it would be possible to store the url in one of custom list in the app. Refer the url from the list. Whenever you need to change the url it can be done from the app itself.

Azure, Increase Worker Count Programatically, Management API / Cmdlets? (without reboot) [duplicate]

Is it possible to update the value of a setting in an Azure Cloud Service with Azure Powershell?
So far there is no way to update just a single setting (the Service Management API does not allow it - it only accepts the whole service configuration). So, in order to update a single setting, you will have to update the entire configuration. And you can do this with PowerShell:
# Add the Azure Account first - this will create a login promppt
Add-AzureAccount
# when you have more then one subscription - you have explicitly select the one
# which holds your cloud service you want to update
Select-AzureSubscription "<Subscription name with spaces goes here>"
# then Update the configuration for the cloud service
Set-AzureDeployment -Config -ServiceName "<cloud_service_name_goes_here>" `
-Configuration "D:/tmp/cloud/ServiceConfiguration.Cloud.cscfg" `
-Slot "Production"
For the the `-Configuration' parameter I have provided full local path to the new config file I want to use with my cloud service.
This is verified and working solution.
As astaykov says, you can't update a single cloud config value using Powershell.
But you can read all of the settings, update the one you wish to change, save it to a temp file, and then set all the settings again, like so:
UpdateCloudConfig.ps1:
param
(
[string] $cloudService,
[string] $publishSettings,
[string] $subscription,
[string] $role,
[string] $setting,
[string] $value
)
# param checking code removed for brevity
Import-AzurePublishSettingsFile $publishSettings -ErrorAction Stop | Out-Null
function SaveNewSettingInXmlFile($cloudService, [xml]$configuration, $setting, [string]$value)
{
# get the <Role name="Customer.Api"> or <Role name="Customer.NewsletterSubscription.Api"> or <Role name="Identity.Web"> element
$roleElement = $configuration.ServiceConfiguration.Role | ? { $_.name -eq $role }
if (-not($roleElement))
{
Throw "Could not find role $role in existing cloud config"
}
# get the existing AzureServiceBusQueueConfig.ConnectionString element
$settingElement = $roleElement.ConfigurationSettings.Setting | ? { $_.name -eq $setting }
if (-not($settingElement))
{
Throw "Could not find existing element in cloud config with name $setting"
}
if ($settingElement.value -eq $value)
{
Write-Host "No change detected, so will not update cloud config"
return $null
}
# update the value
$settingElement.value = $value
# write configuration out to a file
$filename = $cloudService + ".cscfg"
$configuration.Save("$pwd\$filename")
return $filename
}
Write-Host "Updating setting for $cloudService" -ForegroundColor Green
Select-AzureSubscription -SubscriptionName $subscription -ErrorAction Stop
# get the current settings from Azure
$deployment = Get-AzureDeployment $cloudService -ErrorAction Stop
# save settings with new value to a .cscfg file
$filename = SaveNewSettingInXmlFile $cloudService $deployment.Configuration $setting $value
if (-not($filename)) # there was no change to the cloud config so we can exit nicely
{
return
}
# change the settings in Azure
Set-AzureDeployment -Config -ServiceName $cloudService -Configuration "$pwd\$filename" -Slot Production
# clean up - delete .cscfg file
Remove-Item ("$pwd\$filename")
Write-Host "done"

using powershell to set an event logs "Maximum Size" action

When viewing an Event Logs properties (in Server 2008) you can set three actions for what to happen when the maximum event log size has been reached:
Overwrite events as needed
Archive the log when full
Do not overwrite events
Using Powershell I can use limit-eventlog to set the event log retention to set the OverflowAction to DoNotOverwrite or OverwriteAsNeeded, but I cannot seem to be able to get the Archive the log when full action selected.
Any ideas how I could select this option via powershell?
The only way (IMO) is to modifying the registry. Here an example to set 'Archive the log when full' action for the Application log:
new-ItemProperty -path HKLM:\SYSTEM\CurrentControlSet\services\eventlog\Application `
-name AutoBackupLogFiles -Value 1 -PropertyType 'dword'
if the options have been selected previously, the key is already present so just need set to 1 the key value:
set-ItemProperty -path HKLM:\SYSTEM\CurrentControlSet\services\eventlog\Application `
-name AutoBackupLogFiles -Value 1

Categories

Resources