diff --git a/doc/mgmt_preview_quickstart.md b/doc/mgmt_preview_quickstart.md index 52a8ac6690f9b..1742684184b5f 100644 --- a/doc/mgmt_preview_quickstart.md +++ b/doc/mgmt_preview_quickstart.md @@ -1,6 +1,5 @@ -Quickstart Tutorial - Resource Management (Preview Libraries) -============================================================= +# Quickstart Tutorial - Resource Management (Preview Libraries) We are excited to announce that a new set of management libraries are now in Public Preview. Those packages share a number of new features @@ -14,314 +13,249 @@ You can find the details of those new libraries In this basic quickstart guide, we will walk you through how to authenticate to Azure using the preview libraries and start interacting with Azure resources. There are several possible approaches to -authentication. This document illustrates the most common scenario +authentication. This document illustrates the most common scenario. -Prerequisites -------------- +## Getting started -You will need the following values to authenticate to Azure +### Install the package -- **Subscription ID** -- **Client ID** -- **Client Secret** -- **Tenant ID** +Install the Azure Compute management library for .NET with [NuGet](https://www.nuget.org/): -These values can be obtained from the portal, here's the instructions: +```PowerShell +Install-Package Azure.ResourceManager.Compute -Version 1.0.0-beta.1 +``` -### Get Subscription ID +### Prerequisites -1. Login into your Azure account -2. Select Subscriptions in the left sidebar -3. Select whichever subscription is needed -4. Click on Overview -5. Copy the Subscription ID +Set up a way to authenticate to Azure with Azure Identity. -### Get Client ID / Client Secret / Tenant ID +Some options are: -For information on how to get Client ID, Client Secret, and Tenant ID, -please refer to [this -document](https://docs.microsoft.com/azure/active-directory/develop/howto-create-service-principal-portal) +- Through the [Azure CLI Login](https://docs.microsoft.com/cli/azure/authenticate-azure-cli). +- Via [Visual Studio](https://docs.microsoft.com/dotnet/api/overview/azure/identity-readme?view=azure-dotnet#authenticating-via-visual-studio). +- Setting [Environment Variables](https://github.com/Azure/azure-sdk-for-net/blob/main/sdk/resourcemanager/Azure.ResourceManager/docs/AuthUsingEnvironmentVariables.md). -### Setting Environment Variables +More information and different authentication approaches using Azure Identity can be found in [this document](https://docs.microsoft.com/dotnet/api/overview/azure/identity-readme?view=azure-dotnet). -After you obtained the values, you need to set the following values as -your environment variables +### Authenticate the Client -- `AZURE_CLIENT_ID` -- `AZURE_CLIENT_SECRET` -- `AZURE_TENANT_ID` -- `AZURE_SUBSCRIPTION_ID` +The default option to create an authenticated client is to use `DefaultAzureCredential`. Since all management APIs go through the same endpoint, in order to interact with resources, only one top-level `ArmClient` has to be created. -To set the following environment variables on your development system: +To authenticate to Azure and create an `ArmClient`, do the following: -Windows (Note: Administrator access is required) +```C# Snippet:Readme_AuthClient +using Azure.Identity; +using Azure.ResourceManager; -1. Open the Control Panel -2. Click System Security, then System -3. Click Advanced system settings on the left -4. Inside the System Properties window, click the Environment - Variables… button. -5. Click on the property you would like to change, then click the Edit… - button. If the property name is not listed, then click the New… - button. +// Code omitted for brevity -Linux-based OS : +ArmClient armClient = new ArmClient(new DefaultAzureCredential()); +``` - export AZURE_CLIENT_ID="__CLIENT_ID__" - export AZURE_CLIENT_SECRET="__CLIENT_SECRET__" - export AZURE_TENANT_ID="__TENANT_ID__" - export AZURE_SUBSCRIPTION_ID="__SUBSCRIPTION_ID__" +Additional documentation for the `Azure.Identity.DefaultAzureCredential` class can be found in [this document](https://docs.microsoft.com/dotnet/api/azure.identity.defaultazurecredential). -Authentication and Creating Resource Management Client ------------------------------------------------------- +### Understanding Azure Resource Hierarchy -Now that the environment is setup, all you need to do is to create an -authenticated client. Our default option is to use -**DefaultAzureCredential** and in this guide we have picked -**Resources** as our target service, but you can set it up similarly for -any other service that you are using. **For example, in order to manage Compute or Network resources, you would create a ``ComputeManagementClient`` or ``NetworkManagementClient``** +In new management libraries, we no longer provide various clients like `ResourceManagementClient` or `ComputeMangementClient`. Instead, we adopt a hierarchical resource model. **Before you continue, make sure you go through the concepts of the Azure .NET SDK [here](https://github.com/Azure/azure-sdk-for-net/blob/main/sdk/resourcemanager/Azure.ResourceManager/README.md#key-concepts).** -To authenticate to Azure and create a management client, simply do the -following: -```csharp - using Azure.Identity; - using Azure.ResourceManager.Resources; - using Azure.ResourceManager.Resources.Models; - using System; - ... - var subscriptionId = Environment.GetEnvironmentVariable("AZURE_SUBSCRIPTION_ID"); - var resourceClient = new ResourcesManagementClient(subscriptionId, new DefaultAzureCredential()); - var resourceGroupsClient = resourceClient.ResourceGroups; -``` -From this code snippet, we showed that in order to interact with Resources, we need to create a top-level client first (**ResourcesManagementClient**), then get the corresponding sub-resource client we are interested in, in this case we called **.ResourceGroups** to get a ResourceGroupsOperations +---- -For more information and different authentication approaches using Azure -Identity can be found in [this document](https://docs.microsoft.com/dotnet/api/overview/azure/identity-readme?view=azure-dotnet) +## Interacting with Azure Resources -Interacting with Azure Resources --------------------------------- +Now that we are authenticated, we can use our `ArmClient` to make API calls. Let's demonstrate the hierarchical APIs by concrete examples. -Now that we are authenticated, we can use our management client to make API calls. Let's demonstrate management client's usage by showing concrete examples +For the examples below, you need the following namespaces: -Example: Managing Resource Groups ---------------------------------- -We can use the Resource client (``Azure.ResourceManager.Resources.ResourcesManagementClient``) we have created to perform operations on Resource Group. In this example, we will show to manage Resource Groups. +```csharp +using System; +using System.Threading.Tasks; +using Azure.Identity; +using Azure.ResourceManager.Compute.Models; +using Azure.ResourceManager.Resources; +``` -***Create a resource group*** +### Example: Managing Resource Groups + +We can use the `ResourceGroupContainer` to perform operations on Resource Group. In the following code snippets, we will demonstrate how to manage Resource Groups. + +#### Create a resource group ```csharp - var location = "westus2"; - var resourceGroupName = "myResourceGroupName"; - var resourceGroup = new ResourceGroup(location); - resourceGroup = await resourceGroupsClient.CreateOrUpdateAsync(resourceGroupName, resourceGroup); +// First, initialize the ArmClient and get the default subscription +ArmClient armClient = new ArmClient(new DefaultAzureCredential()); +// Now we get a ResourceGroup container for that subscription +Subscription subscription = armClient.DefaultSubscription; +ResourceGroupContainer rgContainer = subscription.GetResourceGroups(); + +// With the container, we can create a new resource group with an specific name +string rgName = "myRgName"; +Location location = Location.WestUS2; +ResourceGroupData rgData = new ResourceGroupData(location); +ResourceGroup resourceGroup = await rgContainer.CreateOrUpdateAsync(rgName, rgData); ``` -***Update a resource group*** +#### Update a resource group ```csharp - ... - var newResourceGroup = new ResourceGroup(location); - var resourceGroupName = "myResourceGroupName"; - var tags = new Dictionary(); - tags.Add("environment","test"); - tags.Add("department","tech"); - newResourceGroup.Tags = tags; - // Use existing resource group name and new resource group object - newResourceGroup = await resourceGroupsClient.CreateOrUpdateAsync(resourceGroupName, newResourceGroup); +// Note: Resource group named 'myRgName' should exist for this example to work. +ArmClient armClient = new ArmClient(new DefaultAzureCredential()); +Subscription subscription = armClient.DefaultSubscription; +string rgName = "myRgName"; +ResourceGroup resourceGroup = await subscription.GetResourceGroups().GetAsync(rgName); +resourceGroup = await resourceGroup.AddTagAsync("key", "value"); ``` - -***List all resource groups*** +#### List all resource groups ```csharp - AsyncPageable response = resourceGroupsClient.ListAsync(); - await foreach (ResourceGroup rg in response) - { - Console.WriteLine(rg.Name); - } +// First, initialize the ArmClient and get the default subscription +ArmClient armClient = new ArmClient(new DefaultAzureCredential()); +Subscription subscription = armClient.DefaultSubscription; +// Now we get a ResourceGroup container for that subscription +ResourceGroupContainer rgContainer = subscription.GetResourceGroups(); +// With GetAllAsync(), we can get a list of the resources in the container +await foreach (ResourceGroup rg in rgContainer.GetAllAsync()) +{ + Console.WriteLine(rg.Data.Name); +} ``` -***Delete a resource group*** +#### Delete a resource group ```csharp - await resourceGroupsClient.StartDeleteAsync(groupName); +// Note: Resource group named 'myRgName' should exist for this example to work. +ArmClient armClient = new ArmClient(new DefaultAzureCredential()); +Subscription subscription = armClient.DefaultSubscription; +string rgName = "myRgName"; +ResourceGroup resourceGroup = await subscription.GetResourceGroups().GetAsync(rgName); +await resourceGroup.DeleteAsync(); ``` -Example: Creating a Virtual Machine ------------------------------------ -Let's show a concrete example of how you would create a virtual machine using .NET SDK -```csharp -using System.Collections.Generic; -using System.Linq; -using System.Threading.Tasks; +### Example: Managing Virtual Machines -using Azure.Identity; -using Azure.ResourceManager.Compute; -using Azure.ResourceManager.Compute.Models; -using Azure.ResourceManager.Network; -using Azure.ResourceManager.Network.Models; -using Azure.ResourceManager.Resources; -using Azure.ResourceManager.Resources.Models; +We can use `VirtualMachineContainer` to perform operations on Virtual Machine. In the following code snippets, we will demonstrate how to manage Virtual Machine. + +#### Create a virtual machine -namespace AzureCreateVMSample +```csharp +ArmClient armClient = new ArmClient(new DefaultAzureCredential()); +Subscription subscription = armClient.DefaultSubscription; +// first we need to get the resource group +string rgName = "myRgName"; +ResourceGroup resourceGroup = await subscription.GetResourceGroups().GetAsync(rgName); +// Now we get the virtual machine container from the resource group +VirtualMachineContainer vmContainer = resourceGroup.GetVirtualMachines(); +// Use the same location as the resource group +string vmName = "myVM"; +VirtualMachineData input = new VirtualMachineData(resourceGroup.Data.Location) { - /// - /// Create a Virtual Machine - /// - public class CreateVMSample + HardwareProfile = new HardwareProfile() + { + VmSize = VirtualMachineSizeTypes.StandardF2 + }, + OsProfile = new OSProfile() { - public static async Task CreateVmAsync( - string subscriptionId, - string resourceGroupName, - string location, - string vmName) + AdminUsername = "adminUser", + ComputerName = "myVM", + LinuxConfiguration = new LinuxConfiguration() { - var computeClient = new ComputeManagementClient(subscriptionId, new DefaultAzureCredential()); - var networkClient = new NetworkManagementClient(subscriptionId, new DefaultAzureCredential()); - var resourcesClient = new ResourcesManagementClient(subscriptionId, new DefaultAzureCredential()); - - var virtualNetworksClient = networkClient.VirtualNetworks; - var networkInterfaceClient = networkClient.NetworkInterfaces; - var publicIpAddressClient = networkClient.PublicIPAddressses; - var availabilitySetsClient = computeClient.AvailabilitySets; - var virtualMachinesClient = computeClient.VirtualMachines; - var resourceGroupClient = resourcesClient.ResourceGroups; - - // Create Resource Group - var resourceGroup = new ResourceGroup(location); - resourceGroup = await resourceGroupClient.CreateOrUpdateAsync(resourceGroupName, resourceGroup); - - // Create AvailabilitySet - var availabilitySet = new AvailabilitySet(location) - { - PlatformUpdateDomainCount = 5, - PlatformFaultDomainCount = 2, - Sku = new Sku() { Name = "Aligned" } // TODO. Verify new codegen on AvailabilitySetSkuTypes.Aligned - }; - - availabilitySet = await availabilitySetsClient.CreateOrUpdateAsync(resourceGroupName, vmName + "_aSet", availabilitySet); - - // Create IP Address - var ipAddress = new PublicIPAddress() + DisablePasswordAuthentication = true, + Ssh = new SshConfiguration() { - PublicIPAddressVersion = IPVersion.IPv4, - PublicIPAllocationMethod = IPAllocationMethod.Dynamic, - Location = location, - }; - - ipAddress = await publicIpAddressClient.StartCreateOrUpdate(resourceGroupName, vmName + "_ip", ipAddress) - .WaitForCompletionAsync(); - - // Create VNet - var vnet = new VirtualNetwork() - { - Location = location, - AddressSpace = new AddressSpace() { AddressPrefixes = new List() { "10.0.0.0/16" } }, - Subnets = new List() - { - new Subnet() - { - Name = "mySubnet", - AddressPrefix = "10.0.0.0/24", - } - }, - }; - - vnet = await virtualNetworksClient - .StartCreateOrUpdate(resourceGroupName, vmName + "_vent", vnet) - .WaitForCompletionAsync(); - - // Create Network interface - var nic = new NetworkInterface() + PublicKeys = { + new SshPublicKeyInfo() + { + Path = $"/home/adminUser/.ssh/authorized_keys", + KeyData = "", + } + } + } + } + }, + NetworkProfile = new NetworkProfile() + { + NetworkInterfaces = + { + new NetworkInterfaceReference() { - Location = location, - IpConfigurations = new List() - { - new NetworkInterfaceIPConfiguration() - { - Name = "Primary", - Primary = true, - Subnet = new Subnet() { Id = vnet.Subnets.First().Id }, - PrivateIPAllocationMethod = IPAllocationMethod.Dynamic, - PublicIPAddress = new PublicIPAddress() { Id = ipAddress.Id } - } - } - }; - - nic = await networkInterfaceClient - .StartCreateOrUpdate(resourceGroupName, vmName + "_nic", nic) - .WaitForCompletionAsync(); - - var vm = new VirtualMachine(location) + Id = "/subscriptions//resourceGroups//providers/Microsoft.Network/networkInterfaces/", + Primary = true, + } + } + }, + StorageProfile = new StorageProfile() + { + OsDisk = new OSDisk(DiskCreateOptionTypes.FromImage) + { + OsType = OperatingSystemTypes.Linux, + Caching = CachingTypes.ReadWrite, + ManagedDisk = new ManagedDiskParameters() { - NetworkProfile = new Compute.Models.NetworkProfile { NetworkInterfaces = new[] { new NetworkInterfaceReference() { Id = nic.Id } } }, - OsProfile = new OSProfile - { - ComputerName = "testVM", - AdminUsername = "username", - AdminPassword = "(YourPassword)", - LinuxConfiguration = new LinuxConfiguration { DisablePasswordAuthentication = false, ProvisionVMAgent = true } - }, - StorageProfile = new StorageProfile() - { - ImageReference = new ImageReference() - { - Offer = "UbuntuServer", - Publisher = "Canonical", - Sku = "18.04-LTS", - Version = "latest" - }, - DataDisks = new List() - }, - HardwareProfile = new HardwareProfile() { VmSize = VirtualMachineSizeTypes.StandardB1Ms }, - }; - vm.AvailabilitySet.Id = availabilitySet.Id; - - var operaiontion = await virtualMachinesClient.StartCreateOrUpdateAsync(resourceGroupName, vmName, vm); - var vm = (await operaiontion.WaitForCompletionAsync()).Value; + StorageAccountType = StorageAccountTypes.StandardLRS + } + }, + ImageReference = new ImageReference() + { + Publisher = "Canonical", + Offer = "UbuntuServer", + Sku = "16.04-LTS", + Version = "latest", } } -} - +}; +VirtualMachineCreateOrUpdateOperation lro = await vmContainer.CreateOrUpdateAsync(vmName, input); +VirtualMachine vm = lro.Value; ``` -Driver program +#### List all virtual machines ```csharp -using System; -using System.Threading.Tasks; - -namespace AzureCreateVMSample +ArmClient armClient = new ArmClient(new DefaultAzureCredential()); +Subscription subscription = armClient.DefaultSubscription; +// first we need to get the resource group +string rgName = "myRgName"; +ResourceGroup resourceGroup = await subscription.GetResourceGroups().GetAsync(rgName); +// Now we get the virtual machine container from the resource group +VirtualMachineContainer vmContainer = resourceGroup.GetVirtualMachines(); +// With ListAsync(), we can get a list of the virtual machines in the container +AsyncPageable response = vmContainer.GetAllAsync(); +await foreach (VirtualMachine vm in response) { - class Program - { - static async Task Main(string[] args) - { - var subscriptionId = Environment.GetEnvironmentVariable("AZURE_SUBSCRIPTION_ID"); - var location = "westus2"; - - await CreateVMSample.CreateVmAsync(subscriptionId, "myResourceGroupName", location, "myVirtualMachine"); - } - } + Console.WriteLine(vm.Data.Name); } ``` + +#### Delete a virtual machine + +```csharp +ArmClient armClient = new ArmClient(new DefaultAzureCredential()); +Subscription subscription = armClient.DefaultSubscription; +// first we need to get the resource group +string rgName = "myRgName"; +ResourceGroup resourceGroup = await subscription.GetResourceGroups().GetAsync(rgName); +// Now we get the virtual machine container from the resource group +VirtualMachineContainer vmContainer = resourceGroup.GetVirtualMachines(); +string vmName = "myVM"; +VirtualMachine vm = await vmContainer.GetAsync(vmName); +await vm.DeleteAsync(); +``` + ## Code Samples More code samples for using the management library for .NET can be found in the following locations + - [.NET Management Library Code Samples](https://docs.microsoft.com/samples/browse/?branch=master&languages=csharp&term=managing%20using%20Azure%20.NET%20SDK&terms=managing%20using%20Azure%20.NET%20SDK) -Need help? ----------- +## Need help? -- File an issue via [Github - Issues](https://github.com/Azure/azure-sdk-for-net/issues) and - make sure you add the "Preview" label to the issue -- Check [previous - questions](https://stackoverflow.com/questions/tagged/azure+.net) - or ask new ones on StackOverflow using azure and .NET tags. +- File an issue via [Github + Issues](https://github.com/Azure/azure-sdk-for-net/issues) and + make sure you add the "Preview" label to the issue +- Check [previous + questions](https://stackoverflow.com/questions/tagged/azure+.net) + or ask new ones on StackOverflow using azure and .NET tags. -Contributing ------------- +## Contributing For details on contributing to this repository, see the contributing guide.