Created
April 23, 2019 06:34
-
-
Save buchizo/ad58de5d9b0c304b8ca2e4f673c4cb63 to your computer and use it in GitHub Desktop.
get role assignments and userinfo using ARM and Graph API on Functions
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using System.Threading.Tasks; | |
using Microsoft.AspNetCore.Mvc; | |
using Microsoft.Azure.WebJobs; | |
using Microsoft.Azure.WebJobs.Extensions.Http; | |
using Microsoft.AspNetCore.Http; | |
using Microsoft.Extensions.Logging; | |
using Microsoft.Extensions.Configuration; | |
using Microsoft.IdentityModel.Clients.ActiveDirectory; | |
using System.Net.Http; | |
using System.Collections.Generic; | |
using System.Linq; | |
namespace FunctionApp7 | |
{ | |
public static class Function1 | |
{ | |
static Function1() | |
{ | |
var builder = new ConfigurationBuilder() | |
.AddJsonFile("local.settings.json", true, false) | |
.AddJsonFile("secret.settings.json", true, false) | |
.AddEnvironmentVariables(); | |
Configuration = builder.Build(); | |
} | |
private static async Task<AuthenticationResult> GetS2SAccessToken(string authority, string resource, string clientId, string clientSecret) | |
{ | |
var clientCredential = new ClientCredential(clientId, clientSecret); | |
AuthenticationContext context = new AuthenticationContext(authority, false); | |
AuthenticationResult authenticationResult = await context.AcquireTokenAsync( | |
resource, | |
clientCredential); | |
return authenticationResult; | |
} | |
private static IConfigurationRoot Configuration { get; } | |
private static HttpClient Client = new HttpClient(); | |
[FunctionName("Function1")] | |
public static async Task<IActionResult> Run( | |
[HttpTrigger(AuthorizationLevel.Function, "get", Route = null)] HttpRequest req, | |
ILogger log) | |
{ | |
try | |
{ | |
// トークンの期限は考慮してないので注意 | |
var token = await GetS2SAccessToken( | |
string.Format("https://login.microsoftonline.com/{0}/", Configuration["Tenant"]), | |
"https://management.azure.com/", | |
Configuration["AppId"], | |
Configuration["AppSecret"] | |
); | |
var tokengraph = await GetS2SAccessToken( | |
string.Format("https://login.microsoftonline.com/{0}/", Configuration["Tenant"]), | |
"https://graph.microsoft.com/", | |
Configuration["AppId"], | |
Configuration["AppSecret"] | |
); | |
var subscriptionId = req.Query["subscriptionid"]; | |
// ロール割り当ての取得 | |
var roleassignments = Utf8Json.JsonSerializer.Deserialize<dynamic>(await GetRoleAssignment(subscriptionId, token.CreateAuthorizationHeader())); | |
var results = await Task.WhenAll( | |
(roleassignments["value"] as List<dynamic>)?.AsParallel() | |
.Select(async val => | |
{ | |
var assigninfo = new { id = val["id"], principalId = val["properties"]["principalId"], roleid = val["properties"]["roleDefinitionId"] }; | |
// 割り当てられているユーザーの情報を取得 | |
string ui = await GetUserInformation(assigninfo.principalId, tokengraph.CreateAuthorizationHeader()); | |
if (string.IsNullOrWhiteSpace(ui)) return null; // 取れない場合ユーザーじゃない可能性もあり(App/Group他 ※手抜き) | |
var user = Utf8Json.JsonSerializer.Deserialize<dynamic>(ui); | |
var roledef = Utf8Json.JsonSerializer.Deserialize<dynamic>(await GetRoleDefine(assigninfo.roleid, token.CreateAuthorizationHeader())); | |
return new | |
{ | |
id = assigninfo.principalId, | |
name = user["displayName"], | |
upn = user["userPrincipalName"], | |
mail = user["mail"], | |
roleid = assigninfo.roleid, | |
rolename = roledef["properties"]["roleName"] | |
}; | |
} | |
) | |
); | |
return new JsonResult(results.Where(x => x != null)); | |
} | |
catch (Exception ex) | |
{ | |
log.LogError(ex.Message); | |
throw; | |
} | |
} | |
static async Task<string> InvokeApi(string requesturi, string authheader) | |
{ | |
var request = new HttpRequestMessage() | |
{ | |
Method = HttpMethod.Get, | |
RequestUri = new Uri(requesturi), | |
}; | |
request.Headers.Add("Authorization", authheader); | |
var res = await Client.SendAsync(request); | |
if (res.StatusCode != System.Net.HttpStatusCode.OK) return null; | |
return await res.Content.ReadAsStringAsync(); | |
} | |
static async Task<string> GetRoleAssignment(string subscriptionId, string authheader) | |
{ | |
return await InvokeApi( | |
$"https://management.azure.com/subscriptions/{subscriptionId}/providers/Microsoft.Authorization/roleAssignments?api-version=2015-07-01", | |
authheader | |
); | |
} | |
static async Task<string> GetRoleDefine(string roleId, string authheader) | |
{ | |
return await InvokeApi( | |
$"https://management.azure.com/{roleId}?api-version=2015-07-01", | |
authheader | |
); | |
} | |
static async Task<string> GetUserInformation(string userid, string authheader) | |
{ | |
return await InvokeApi( | |
$"https://graph.microsoft.com/v1.0/users/{userid}", | |
authheader | |
); | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment