How to remotely update azure SQL firewall with loc

2019-04-13 16:19发布

问题:

How can I remotely update my azure SQL firewall with my local PCs IP address for administration either via powershell or C#.

I have had a look over the documentation but I can only find out how to do it from the actual server itself, not remotely.

I can get visual studio to pop up and ask me if I want to add my IP address to the firewall randomly, but most the time it simply fails and does not ask me so I am looking for a solution other than manually logging into the azure portal whenever my IP address changes.

Looking for either an example or a link to documentation that shows which libraries to use.

回答1:

From C# you can access all Azure resources via Microsoft.Azure.Management.Fluent like this

// Create an authentication context to Azure and acquire a login token
var context = new AuthenticationContext("https://login.microsoftonline.com/tenantId");
var auth = await context.AcquireTokenAsync("https://management.core.windows.net/",
                    "yourClientId", new Uri("urn:ietf:wg:oauth:2.0:oob"),
                    new PlatformParameters(PromptBehavior.Always));
var tokenCredentials = new TokenCredentials(token);
var azureCredentials = new AzureCredentials(tokenCredentials, tokenCredentials, 
                           AzureParts.Tenant, AzureEnvironment.AzureGlobalCloud);

// Build the client with the acquired token as a credential.
RestClient client = RestClient.Configure()
                .WithEnvironment(AzureEnvironment.AzureGlobalCloud)
                .WithLogLevel(HttpLoggingDelegatingHandler.Level.Basic)
                .WithCredentials(azureCredentials)
                .Build();

// Authenticate against azure with the correct subscription to access.
var azure = Azure.Authenticate(client, AzureParts.Tenant)
                .WithSubscription("subscriptionId");

// Search for the sql server and add a firewall rule.
var sqlServer = azure.SqlServers.GetByResourceGroup("ResourceGroup", "servername");
sqlServer.FirewallRules.Define("LetMeIn").WithIPAddress("yourIp").Create();

Note that acquiring the login token via AcquireTokenAsync will open a login window and thus can not be used in an automated fashion. You could provide a token-cache with an already stored token if you want to only login once.



回答2:

We can do that with Microsoft.Azure.Management.Fluent and Microsoft.Azure.Management.ResourceManager.Fluent,more detail info about library, please refer to the packages.config. We also could get more demo code from the github. Before coding we need to registry an Azure AD Application and assign corresponding role for it, more details please refer to the document. Then we can get the clientId, key(secret key) and tenant from the Azure AD App. After that we could create the Auth file with following format

subscription=########-####-####-####-############
client=########-####-####-####-############
tenant=########-####-####-####-############
key=XXXXXXXXXXXXXXXX
managementURI=https\://management.core.windows.net/
baseURL=https\://management.azure.com/
authURL=https\://login.windows.net/
graphURL=https\://graph.windows.net/

Demo code:

 var credFile = @"File Path"; // example: c:\tom\auth.txt
            var resourceGroup = "resource group";
            var azureSQLServer = "Azure sql server name"; //just name of the Azure sql server such as tomdemo
            var firewallRull = "firewall rull name";//such as myFirewallRull
            var firewallRuleIPAddress = "x.x.x.x";//your Ip address
            var credentials = SdkContext.AzureCredentialsFactory.FromFile(credFile);
            var azure = Azure
                .Configure()
                .WithLogLevel(HttpLoggingDelegatingHandler.Level.Basic)
                .Authenticate(credentials)
                .WithDefaultSubscription();

            var sqlServer = azure.SqlServers.GetByResourceGroup(resourceGroup, azureSQLServer);
            var newFirewallRule = sqlServer.FirewallRules.Define(firewallRull)
                .WithIPAddress(firewallRuleIPAddress)
                .Create();

packages.config

<?xml version="1.0" encoding="utf-8"?>
<packages>
  <package id="Microsoft.Azure.KeyVault.Core" version="1.0.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.AppService.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.Batch.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.Cdn.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.Compute.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.ContainerInstance.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.ContainerRegistry.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.CosmosDB.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.Dns.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.Graph.RBAC.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.KeyVault.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.Network.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.Redis.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.ResourceManager.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.Search.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.ServiceBus.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.Sql.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.Storage.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Azure.Management.TrafficManager.Fluent" version="1.3.0" targetFramework="net461" />
  <package id="Microsoft.Data.Edm" version="5.8.2" targetFramework="net461" />
  <package id="Microsoft.Data.OData" version="5.8.2" targetFramework="net461" />
  <package id="Microsoft.Data.Services.Client" version="5.8.2" targetFramework="net461" />
  <package id="Microsoft.IdentityModel.Clients.ActiveDirectory" version="2.28.3" targetFramework="net461" />
  <package id="Microsoft.Rest.ClientRuntime" version="2.3.9" targetFramework="net461" />
  <package id="Microsoft.Rest.ClientRuntime.Azure" version="3.3.10" targetFramework="net461" />
  <package id="Microsoft.Rest.ClientRuntime.Azure.Authentication" version="2.3.1" targetFramework="net461" />
  <package id="Newtonsoft.Json" version="6.0.8" targetFramework="net461" />
  <package id="System.ComponentModel.EventBasedAsync" version="4.0.11" targetFramework="net461" />
  <package id="System.Dynamic.Runtime" version="4.0.0" targetFramework="net461" />
  <package id="System.Linq.Queryable" version="4.0.0" targetFramework="net461" />
  <package id="System.Net.Requests" version="4.0.11" targetFramework="net461" />
  <package id="System.Spatial" version="5.8.2" targetFramework="net461" />
  <package id="WindowsAzure.Storage" version="8.1.4" targetFramework="net461" />
</packages>


回答3:

For PowerShell, you would need to use New-AzureRmSqlServerFirewallRule.

From this link:

New-AzureRmSqlServerFirewallRule -ResourceGroupName "myResourceGroup" -ServerName $servername -FirewallRuleName "AllowSome" -StartIpAddress "0.0.0.0" -EndIpAddress "0.0.0.0"