Skip to content

Instantly share code, notes, and snippets.

@SpicySyntax
Last active April 30, 2019 14:30
Show Gist options
  • Save SpicySyntax/df6fd2b1b6f56a4e0058c2f35790dd31 to your computer and use it in GitHub Desktop.
Save SpicySyntax/df6fd2b1b6f56a4e0058c2f35790dd31 to your computer and use it in GitHub Desktop.
Azure Function Dependency Injection
using System.Collections.Generic;
using System.Threading.Tasks;
using MongoDB.Bson;
using MongoDB.Driver;
namespace CrackDetection
{
public interface ICosmosDbClient
{
Task<string> CreateImageRecord(ImageRecord image);
Task<bool> UpdateImageRecord(ObjectId id, IDictionary<string, string> keyVals);
}
public class CosmosDbClient: ICosmosDbClient
{
private readonly IMongoDatabase _mongoDatabase;
public CosmosDbClient()
{
var settings = MongoClientSettings.FromUrl(new MongoUrl(Config.GetEnvironmentVariable("CosmosDbConnectionString")));
var mongoClient = new MongoClient(settings);
_mongoDatabase = mongoClient.GetDatabase("imageProcessor");
}
public async Task<bool> UpdateImageRecord(ObjectId id, IDictionary<string, string> keyVals)
{
var collection = _mongoDatabase.GetCollection<ImageRecord>("images");
var filter = Builders<ImageRecord>.Filter.Eq("_id", id);
var updateBuilder = Builders<ImageRecord>.Update;
var updates = new List<UpdateDefinition<ImageRecord>>();
foreach (var key in keyVals.Keys)
{
string stringVal = null;
var val = keyVals.TryGetValue(key, out stringVal);
if (!val) continue;
updates.Add(updateBuilder.Set(key, stringVal));
}
var update = updateBuilder.Combine((updates));
var result = await collection.UpdateOneAsync(filter, update);
return result.ModifiedCount != 0;
}
public async Task<string> CreateImageRecord(ImageRecord image)
{
var collection = _mongoDatabase.GetCollection<ImageRecord>("images");
await collection.InsertOneAsync(image);
return image._Id.ToString();
}
public async Task<IEnumerable<ImageRecord>> GetImageRecordByField(string fieldName, string fieldValue)
{
var collection = _mongoDatabase.GetCollection<ImageRecord>("images");
var filter = Builders<ImageRecord>.Filter.Eq(fieldName, fieldValue);
var result = await collection.Find(filter).ToListAsync();
return result;
}
}
}
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>netcoreapp2.2</TargetFramework>
<AzureFunctionsVersion>v2</AzureFunctionsVersion>
<Platforms>x64</Platforms>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="IdentityModel" Version="3.10.7" />
<PackageReference Include="Microsoft.Azure.WebJobs.Extensions.Storage" Version="3.0.0" />
<PackageReference Include="Microsoft.NET.Sdk.Functions" Version="1.0.26" />
<PackageReference Include="MongoDB.Driver" Version="2.7.3" />
<PackageReference Include="Newtonsoft.Json" Version="11.0.2" />
<PackageReference Include="WindowsAzure.Storage" Version="9.3.3" />
<PackageReference Include="Willezone.Azure.WebJobs.Extensions.DependencyInjection" Version="1.0.1" />
<PackageReference Include="Autofac.Extensions.DependencyInjection" Version="4.4.0" />
</ItemGroup>
<ItemGroup>
<None Update="host.json">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
<None Update="local.settings.json">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
<CopyToPublishDirectory>Never</CopyToPublishDirectory>
</None>
</ItemGroup>
</Project>
using System;
using System.Net.Http;
using System.Net;
using System.Threading.Tasks;
using Microsoft.Azure.WebJobs;
using Microsoft.Azure.WebJobs.Extensions.Http;
using Microsoft.Extensions.Logging;
using Willezone.Azure.WebJobs.Extensions.DependencyInjection;
namespace CrackDetection
{
public static class UploadImage
{
[FunctionName("UploadImage")]
public static async Task<HttpResponseMessage> Run(
[HttpTrigger(AuthorizationLevel.Anonymous, "post", Route = "upload")] HttpRequestMessage req,
[Inject] ICosmosDbClient cosmosDbClient,
IAzureStorageClient azureStorageClient,
ILogger log)
{
//ICosmosDbClient cosmosDbClient = new CosmosDbClient();
IAzureStorageClient azureStorageClient = new AzureStorageClient();
log.LogInformation("Upload Image HTTP trigger function processed a request.");
var provider = new MultipartMemoryStreamProvider();
try
{
await req.Content.ReadAsMultipartAsync(provider);
}
catch (Exception e)
{
log.LogWarning(new EventId(), e, "Unable to read multipart content");
}
if (provider.Contents.Count != 1)
return new HttpResponseMessage(HttpStatusCode.BadRequest);
var file = provider.Contents[0];
var fileInfo = file.Headers.ContentDisposition;
var fileType = file.Headers.ContentType.ToString().ToLower();
if (fileType != "image/png" && fileType != "image/jpeg" && fileType != "image/bmp")
return new HttpResponseMessage(HttpStatusCode.BadRequest);
var fileData = await file.ReadAsByteArrayAsync();
var newImage = new ImageRecord()
{
FileName = fileInfo.FileName,
Size = fileData.LongLength,
Status = ImageStatus.Recieved.Value
};
var imageName = await cosmosDbClient.CreateImageRecord(newImage);
if (!(await azureStorageClient.SaveToBlobStorage(imageName, fileData)))
return new HttpResponseMessage(HttpStatusCode.InternalServerError);
return new HttpResponseMessage(HttpStatusCode.Created)
{
Content = new StringContent(imageName)
};
}
}
}
using ObjectDetection;
using Microsoft.Azure.WebJobs.Hosting;
using Microsoft.Azure.WebJobs;
using Willezone.Azure.WebJobs.Extensions.DependencyInjection;
using Autofac;
using Microsoft.Extensions.Configuration;
using System;
using Microsoft.Extensions.DependencyInjection;
using Autofac.Extensions.DependencyInjection;
using ObjectDetection.Services;
[assembly: WebJobsStartup(typeof(Startup))]
namespace ObjectDetection
{
public class Startup : IWebJobsStartup
{
public void Configure(IWebJobsBuilder builder)
{
builder.AddDependencyInjection<AutofacServiceProviderBuilder>();
}
}
internal class AutofacServiceProviderBuilder : IServiceProviderBuilder
{
protected IConfiguration Configuration { get; }
public AutofacServiceProviderBuilder(IConfiguration configuration) => Configuration = configuration;
public IServiceProvider Build()
{
var services = new ServiceCollection();
services.Configure<IConfiguration>(Configuration);
var builder = new ContainerBuilder();
builder.Populate(services);
Configure(builder);
return new AutofacServiceProvider(builder.Build());
}
protected void Configure(ContainerBuilder builder)
{
builder.RegisterType<CosmosDbClient>().As<ICosmosDbClient>().InstancePerDependency();
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment