azureazure-web-rolesazure-configuration

How to get full list of CloudConfiguration from inside a web service at runtime?


ConfigurationManager has AppSettings name-value collection but CloudConfigurationManager has only GetSetting(string) method where you can get the config settings 1 by 1 if you know the key.

Is there a way to get the whole config of the role runtime?

The root cause is that I want to make strong typed configuration in order to abstract it away and make my code more testable. Using CloudConfigurationManager directly is implicit dependency which I want to remove with an abstraction which I want to stub in tests. So I find this practical. Which brings me to my question.

I do not want to use library like fx.configuration.azure because I will have to carry its dependency altogether because it requires inheritance of a base class.


Solution

  • AFAIK, there's no direct method available which will give you this information.

    However there's a workaround that you can use. It involves making use of Service Management API's Get Deployment operation. This operation will return an XML and one of the element there is Configuration which contains your service configuration file in Base64 encoded format. You can read this element, convert it into string and parse the XML to get to ConfigurationSettings elements. It's child elements contains all the settings.

    For this, you could either write your own wrapper over Service Management REST API or make use of Azure Management Library.

    UPDATE

    So here's a sample code for listing all configuration settings from Service Configuration File using Azure Management Library. It's a simple console app hacked together in very short amount of time thus has a lot of scope of improvement :). For management certificate, I have used the data from Publish Setting File.

    You just have to install Azure Management Library Nuget Package in your console application:

    Install-Package Microsoft.WindowsAzure.Management.Libraries

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;
    using Microsoft.WindowsAzure;
    using Microsoft.WindowsAzure.Management.Compute;
    using System.Security.Cryptography.X509Certificates;
    using System.Xml.Linq;
    
    namespace ReadConfigurationSettingsUsingAzureManagementLibrary
    {
        class Program
        {
            static string subscriptionId = "<subscription-id>";
            static string managementCertContents = "<Base64 Encoded Management Certificate String from Publish Setting File>";//Certificate string from Azure Publish Settings file
            static string cloudServiceName = "<your cloud service name>";
            static string ns = "http://schemas.microsoft.com/ServiceHosting/2008/10/ServiceConfiguration";
            static void Main(string[] args)
            {
                var managementCetificate = new X509Certificate2(Convert.FromBase64String(managementCertContents));
                var credentials = new CertificateCloudCredentials(subscriptionId, managementCetificate);
    
                var computeManagementClient = new ComputeManagementClient(credentials);
                var response = computeManagementClient.HostedServices.GetDetailed(cloudServiceName);
                var deployment = response.Deployments.FirstOrDefault(d => d.DeploymentSlot == Microsoft.WindowsAzure.Management.Compute.Models.DeploymentSlot.Production);
                if (deployment != null)
                {
                    var config = deployment.Configuration;
                    XElement configXml = XElement.Parse(config);
                    var roles = configXml.Descendants(XName.Get("Role", ns));
                    foreach (var role in roles)
                    {
                        Console.WriteLine(role.Attribute("name").Value);
                        Console.WriteLine("-----------------------------");
                        var configurationSettings = role.Element(XName.Get("ConfigurationSettings", ns));
                        foreach (var element in configurationSettings.Elements(XName.Get("Setting", ns)))
                        {
                            var settingName = element.Attribute("name").Value;
                            var settingValue = element.Attribute("value").Value;
                            Console.WriteLine(string.Format("{0} = {1}", settingName, settingValue));
                        }
                        Console.WriteLine("==========================================");
                    }
                }
                Console.ReadLine();
            }
        }
    }