Configure a Virtual Network in Azure DevTest Labs - programmatically (c#) - c#

I'm trying to create a brand new network with two address spaces (10.0.0.0/20 and 10.0.16.0/20) and, most importantly, set useInVmCreationPermission and usePublicIpAddressPermission to Allow.
I have the lab already created and I'm able to create a network but I'm unable to relate them with each other. I'm not sure if it's possible through the REST API but if the portal does it, I'm pretty sure it can be achieved (even if I had to use HttpClient). The way it's done in the Azure Portal, is described here: https://learn.microsoft.com/en-us/azure/devtest-labs/devtest-lab-configure-vnet .
This is my code:
private async Task Create(IAzure azureClient, DbLab dbLab)
{
var virtualNetworkId = Guid.NewGuid().ToString();
var virtualNetwork = await azureClient
.Networks
.Define(virtualNetworkId)
.WithRegion(dbLab.Region.Value)
.WithExistingResourceGroup(dbLab.ResourceGroupName)
.WithAddressSpace(Consts.IPv4DynamicAddressSpace)
.WithAddressSpace(Consts.IPv4StaticAddressSpace)
.WithSubnet($"{virtualNetworkId}_dynamic", Consts.IPv4DynamicAddressSpace)
.WithSubnet($"{virtualNetworkId}_static", Consts.IPv4StaticAddressSpace)
.CreateAsync();
var fragment = new VirtualNetworkFragment(
subnetOverrides: virtualNetwork.Subnets.Select(s =>
new SubnetOverrideFragment(
resourceId: s.Value.Name,
useInVmCreationPermission: "Allow",
usePublicIpAddressPermission: "Allow")).ToList());
// fails because vnet is not related to that lab
var vnet = await BaseClientFactory.CreateDevTestLabClient(azureClient)
.VirtualNetworks
.UpdateAsync(dbLab.ResourceGroupName, dbLab.LabId.ToString(), virtualNetworkId, fragment);
}
How do I attach a lab to the vnet programmatically in c#?

Yes, you can configure your existing virtual network to a lab's Virtual Network settings via both the REST API and the SDK as well.
REST API: Virtual Networks - Create Or Update
PUT https://management.azure.com/subscriptions/{subscriptionId}/resourceGroups/{resourceGroupName}/providers/Microsoft.DevTestLab/labs/{labName}/virtualnetworks/{name}?api-version=2018-09-15
Note that resourceGroupName is the name of the resource group where the DevTest Lab exists, and not that of the VNet.
Here is the equivalent method in the .Net SDK: CreateOrUpdateWithHttpMessagesAsync

Related

How to get a MSAL access token for SharePoint Online in a federated environment the non-interactive way in a non-interactive .Net console app?

The task as simple as to have a scheduled .NET console app which will download a file from SharePoint Online on a regular basis using AD domain user account.
If I use recommended way
var token = publicApplication.AcquireTokenByIntegratedWindowsAuth(scopes).ExecuteAsync().Result;
I'm getting
UriFormatException: Invalid URI: The hostname could not be parsed.
What does it mean? Which URI, hostname? Should I override something somewhere or add some special parameter?
I've googled thru this stuff a lot, and I have no idea where to look further, any advice will be appreciated.
P.S. I have no permissions to do anything on SharePoint side, I'm not a SP admin. I just have access to specific folder on the site from which I'm downloading the file. And also I have a code which works interactively:
WebRequest.DefaultWebProxy = WebRequest.GetSystemWebProxy();
WebRequest.DefaultWebProxy.Credentials = CredentialCache.DefaultNetworkCredentials;
var scopes = new string[] { "https://tenant.sharepoint.com/.default" };
var options = new PublicClientApplicationOptions()
{
TenantId = "tenant.com",
ClientId = "{872cd9fa-d31f-45e0-9eab-6e460a02d1f1}",//known Visual Studio Id
};
var publicApplication = PublicClientApplicationBuilder.CreateWithApplicationOptions(options).Build();
var token = publicApplication.AcquireTokenInteractive(scopes).WithLoginHint("name.surname#tenant.com").ExecuteAsync().Result;
But it shows a browser window
No questions asked, pop-up disappear, and I get the token which is used further to download a file from SPOnline using /_api/web/GetFileByServerRelativeUrl(' stuff.
So just run the app, see the popup, get the file downloaded. No interaction needed.
But this approach doesn't work if I put this routine really non-interactive:
Showing a modal dialog box or form when the application is not running in UserInteractive mode is not a valid operation. Specify the ServiceNotification or DefaultDesktopOnly style to display a notification from a service application.
Turns out the non-interactive way is only possible using tenant-side registered application. Implemented using certificate authentication.
But surprisingly the token obtained by ConfidentialClientApplicationBuilder doesn't work the way I wanted/expected (scopes/user impersonation issues). So now we use Graph client approach.
This is the only way which works for me (.NetFramework 4.7.2):
using Azure.Identity;
using Microsoft.Graph;
//...
static async Task GetFile(GraphServiceClient graphClient, string fileName2get)
{
var fileitem = graphClient
.Sites["SiteGuidYouMayGetBy /sites/[your site name]/_api/site/id"]
.Drives["CrazyLongDriveIdYouMayGetByEnumeratingDrivesHere"]
.Root
.ItemWithPath($"/Path To The File starting from Drive Root/{fileName2get}")
.Content
.Request().GetResponseAsync();
var stream = fileitem.GetAwaiter().GetResult();
using (var fileStream = System.IO.File.Create($"C:/Temp/{fileName2get}"))
{
await stream.Content.CopyToAsync(fileStream);
}
}

C# AWS - How to determine AWS Region Endpoint dynamically in c#

I am connecting to AWS SecretManager, in which my code connects to specific region endpoint(below code)
AmazonSecretsManagerConfig config = new AmazonSecretsManagerConfig { RegionEndpoint = RegionEndpoint.USEast1 };
Now, I want to add one more new region RegionEndpoint.USEast2
I want this RegionEndpoint selection dynamically, based on the specific region request. Kindly help, How can I configure Multi Region in my C# Code?
Note: My app is running on Fargate and not on EC2 instance, so below solutions won't work:
client = Amazon.Util.EC2InstanceMetadata.Region.SystemName;
or
client = new Amazon&&&&Client(credentials, RegionEndpoint.GetBySystemName("us-east-1"));
You should be able to get the current region from reading the AWS_REGION environment variable as mentioned in this post: How can we determine the current region with AWS Fargate.

Get AWS caller Identity with C# SDK

When I execute this with the aws cli, i.ex. inside a fargate task, I can see the UserId that my application is going to use
aws sts get-caller-identity
with this output on the console
{
"Arn": "arn:aws:sts::643518765421:assumed-role/url_process_role/6ae81f92-66f3-30de-1eaa-3a7d1902bad9",
"UserId": "ARDYOAZLVOAQXTT5ZXTV4:4ea81f97-66f3-40de-beaa-3a7d1902bad9",
"Account": "692438514791"
}
I would like to get the same information but using the C# SDK. I tried with the methods exposed in this doc but I can see some account related details but not the UserId assigned.
So far I've tried with this but I cannot see any profile when running in a Fargate task.
var awsChain = new Amazon.Runtime.CredentialManagement.CredentialProfileStoreChain();
System.Console.WriteLine($"Found {awsChain.ListProfiles().Count} AWS profiles.");
My final goal is to get it and add to some task processed with Fargate to save a correlation Id in the database when something fails and easily find the Fargate log stream.
IAmazonSecurityTokenService will provide the same information when executed with .netcore. Notice that the above example will only work inside the AWS domain as the endpoint is not publicly available if testing from a development machine.
var getSessionTokenRequest = new GetSessionTokenRequest
{
DurationSeconds = 7200
};
var stsClient = hostContext.Configuration.GetAWSOptions().CreateServiceClient<IAmazonSecurityTokenService>();
var iden = stsClient.GetCallerIdentityAsync(new GetCallerIdentityRequest { }).Result;
System.Console.WriteLine($"A={iden.Account} ARN={iden.Arn} U={iden.UserId}");

Using the Azure API, how do I list and add virtual directories to a website?

I am trying to add a Virtual Directory to an Azure Web Site from a WinForms Application using the Azure API. I can enumerate the WebSites on in my webspace, but I cannot find a method that allows me access to the Virtual Directories in the WebSite.
Here is my code:
string certPath = Properties.Settings.Default.AzureCertificatePath;
string certPassword = Properties.Settings.Default.AzureCertificatePassword;
string subscriptionId = Properties.Settings.Default.AzureSubscriptionId;
var cert = new X509Certificate2(certPath, certPassword, X509KeyStorageFlags.MachineKeySet);
var cred = new CertificateCloudCredentials(subscriptionId, cert);
using (var client = new WebSiteManagementClient(cred))
{
var spaces = client.WebSpaces.List();
foreach (var space in spaces)
{
Console.WriteLine("Space: {0}", space.Name);
var sites = client.WebSpaces.ListWebSites(space.Name, new WebSiteListParameters {PropertiesToInclude = { "Name" } }); ***// Where do I find out what properties can be included in this array?***
foreach (var site in sites)
{
***// What goes here to show the virtual directories in this specific website??????***
}
}
}
I found that the Azure web services API does not offer access to the virtual directories/applications on a web app, although the underlying REST API's that it uses does.
Luckily, the management API is open source (I wanted to get the v3.0.0.0 of the website management API, matching what I had NuGet'd, which I found here: https://github.com/Azure/azure-sdk-for-net/commits/master?page=79) so with a little perseverance and messing about with .targets files and NuGet references, you can get the source code of the WebSiteManagement project into your solution instead of the referenced DLL that you likely downloaded from NuGet.
From there, if you go into your client.WebSites.GetConfiguration method, stick a breakpoint in and capture the HTTP response returned - you'll see that in the JSON the VirtualApplications on your website are indeed there.
From there, you can edit your copy of the source code to expose those object structures out, much the same way that other object structures are mapped out of the JSON (e.g. HandlerMappings).
Likewise for updating them, you need to add the VirtualApplications (in the ewact same format) into the Microsoft.WindowsAzure.Management.WebSites.Models.WebSiteUpdateConfigurationParameters, and pass that into client.WebSites.UpdateConfiguration (which you will also need to amend to map your VirtualApplications object structure back into JSON in the same format).
Works great for me doing it this way.
Note/Disclaimer: The GitHub site documentation does mention that much of the source code was autogenerated, and that you shouldn't really go editing that code, instead raise an issue on the project about getting it sorted. I didn't have the time to do this and needed an immediate way of getting it working with my local copy of the code only, so my solution does, as you'll note when you look a the source, involve adding to that auto-gen'd code. It works great, but I should in good conscience point you to the project owner's warnings about tinkering with the auto-gen'd code.

Google Admin Audit api - how do I get the CustomerID in C#

I am new to the Google API and web based programming so excuse my general ignorance. I am trying to use the Google Admin Audit APIs and have not found an example of how to make the call to get the ClientID to be able to make one of the Google API calls that require the CustomerID - like Admin Auditing. I have run other simple examples like retrieving Tasks list etc but the issue is that these types of calls do not require you to use a Customer ID.
I have all the right includes as per other Google API examples plus Google.Apis.Audit.v1 required for auditing. I have enabled the provisioning API in my admin console and I have created a new client based project in the API console and also enabled the Audit API service for the project.
Here is generally what I am doing:
public IAuthenticator GetServiceInterface()
{
ClientProvider = new NativeApplicationClient(GoogleAuthenticationServer.Description);
ClientProvider.ClientIdentifier = "MY_CLIENT_ID";
ClientProvider.ClientSecret = "MY_CLIENT_SECRET";
IAuthenticator IAuth = new OAuth2Authenticator<NativeApplicationClient>(ClientProvider, GetAuthorization);
return IAuth;
}
private IAuthorizationState GetAuthorization(NativeApplicationClient client)
{
string[] ScopeList = new string[2] { "https://apps-apis.google.com/a/feeds/policies/", "https://www.googleapis.com/auth/apps/reporting/audit.readonly" };
IAuthorizationState IAuthState = new AuthorizationState(ScopeList);
IAuthState = AuthorizationMgr.RequestNativeAuthorization(client, ScopeList);
return IAuthState;
}
public void GoogleAuditTest()
{
//Get a Audit Service Interface
AuditService AuService = new AuditService( GetServiceInterface() );
????????????????????????????
...How do I get the CustomerID required by the audit service calls to list activities, etc
}
Am I missing something?
There is an easy way to get the customerId through the API's explorer (no coding needed).
Log onto the domain
Go to:
https://developers.google.com/apis-explorer/#s/reports/v1/reports.customerUsageReports.get?date=2013-05-18&_h=1&
Authorize OAuth
When you run the report, you'll see the customerId in the response.

Categories