Last active
April 8, 2020 01:05
-
-
Save justinyoo/840f71acbc16a767c23e90b16c06a323 to your computer and use it in GitHub Desktop.
Identifying Faces through Azure Functions Using Face API
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
var sasToken = Environment.GetEnvironmentVariable("Blob__SasToken"); | |
var containerName = Environment.GetEnvironmentVariable("Blob__Container"); | |
var personGroup = Environment.GetEnvironmentVariable("Blob__PersonGroup"); | |
var numberOfPhotos = Convert.ToInt32(Environment.GetEnvironmentVariable("Blob__NumberOfPhotos")); | |
var tableName = Environment.GetEnvironmentVariable("Table__Name"); | |
var authKey = Environment.GetEnvironmentVariable("Face__AuthKey"); | |
var endpoint = Environment.GetEnvironmentVariable("Face__Endpoint"); | |
var confidence = Convert.ToDouble(Environment.GetEnvironmentVariable("Face__Confidence")); |
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
var client = new CloudBlobClient(); | |
var container = client.GetContainerReference(containerName); | |
await container.CreateIfNotExistsAsync().ConfigureAwait(false); | |
var segment = await container.ListBlobsSegmentedAsync($"{personGroup}/", true, BlobListingDetails.Metadata, numberOfPhotos, null, null, null) | |
.ConfigureAwait(false); | |
var images = segment.Results.Select(p => (CloudBlockBlob)p).ToList(); | |
if (images.Count < numberOfPhotos) | |
{ | |
var uploaded = DO_IMAGE_UPLOAD(); | |
return new CreatedResult(uploaded.Uri, $"Need {numberOfPhotos - blobs.Count} more photo(s)."); | |
} |
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
var credentials = new ApiKeyServiceClientCredentials(authKey); | |
var client = new FaceClient(credentials) { Endpoint = endpoint }; | |
var url = $"{face.Uri.AbsoluteUri}{sasToken}"; | |
var faces = await client.Face | |
.DetectWithUrlAsync(url, recognitionModel: RecognitionModel.Recognition01) | |
.ConfigureAwait(false); | |
if (faces.Count != 1) | |
{ | |
return new BadRequestObjectResult("Too many faces or no face detected"); | |
} |
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
var personGroupId = Guid.NewGuid().ToString(); | |
var client = new CloudTableClient(); | |
var table = client.GetTableReference(tableName); | |
await table.CreateIfNotExistsAsync().ConfigureAwait(false); | |
var entity = new FaceEntity(personGroup, personGroupId); | |
var operation = TableOperation.InsertOrReplace(entity); | |
await table.ExecuteAsync(operation).ConfigureAwait(false); |
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
var credentials = new ApiKeyServiceClientCredentials(authKey); | |
var client = new FaceClient(credentials) { Endpoint = endpoint }; | |
await client.PersonGroup | |
.CreateAsync(entity.PersonGroupId, entity.PersonGroup, recognitionModel: RecognitionModel.Recognition01) | |
.ConfigureAwait(false); | |
var person = await client.PersonGroupPerson | |
.CreateAsync(entity.PersonGroupId, entity.PersonGroup) | |
.ConfigureAwait(false); | |
entity.PersonId = person.PersonId.ToString(); |
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
var credentials = new ApiKeyServiceClientCredentials(authKey); | |
var client = new FaceClient(credentials) { Endpoint = endpoint }; | |
var faceIds = new List<string>(); | |
foreach (var face in faces) | |
{ | |
var url = $"{face.Uri.AbsoluteUri}{sasToken}"; | |
var added = await client.PersonGroupPerson | |
.AddFaceFromUrlAsync(entity.PersonGroupId, person.PersonId, url, face.Name) | |
.ConfigureAwait(false); | |
var filename = face.Name | |
.Replace($"{personGroup}/", string.Empty) | |
.Replace(".png", string.Empty); | |
faceIds.Add(filename); | |
} | |
entity.FaceIds = string.Join(",", faceIds); |
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
var credentials = new ApiKeyServiceClientCredentials(authKey); | |
var client = new FaceClient(credentials) { Endpoint = endpoint }; | |
await client.PersonGroup | |
.TrainAsync(entity.PersonGroupId) | |
.ConfigureAwait(false); | |
while (true) | |
{ | |
await Task.Delay(1000); | |
var trainingStatus = await client.PersonGroup | |
.GetTrainingStatusAsync(entity.PersonGroupId) | |
.ConfigureAwait(false); | |
if (trainingStatus.Status == TrainingStatusType.Succeeded) | |
{ | |
break; | |
} | |
} |
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
var credentials = new ApiKeyServiceClientCredentials(authKey); | |
var client = new FaceClient(credentials) { Endpoint = endpoint }; | |
var faces = DO_FACE_DETECTION(); | |
var detected = faces.Select(p => p.FaceId.Value).ToList(); | |
var identified = await client.Face | |
.IdentifyAsync(detected, entity.PersonGroupId) | |
.ConfigureAwait(false); | |
entity.Confidence = identified.First().Candidates.First().Confidence; |
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
// var confidence = Convert.ToDouble(Environment.GetEnvironmentVariable("Face__Confidence")); | |
if (entity.Confidence < confidence) | |
{ | |
return new BadRequestObjectResult($"Face not identified: {entity.Confidence:0.00}"); | |
} | |
return new OkObjectResult($"Face identified: {entity.Confidence:0.00}"); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment