Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
using System.Threading.Tasks;
using Ahk.GitHub.Monitor.Config;
using Ahk.GitHub.Monitor.Services.EventDispatch;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Logging.Abstractions;
using Microsoft.Extensions.Options;
Expand All @@ -18,7 +20,8 @@ public async Task NoAppConfigsReturnsError()
{
var log = new Mock<ILogger<GitHubMonitorFunction>>();
var eds = new Mock<IEventDispatchService>();
var func = new GitHubMonitorFunction(eds.Object, Options.Create(new GitHubMonitorConfig()), log.Object);
var mockConfiguration = new Mock<IConfiguration>();
var func = new GitHubMonitorFunction(eds.Object, log.Object, mockConfiguration.Object);

ObjectResult resp = await func.InvokeAndGetResponseAs<ObjectResult>(req => { });

Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
using Ahk.GitHub.Monitor.Config;
using Ahk.GitHub.Monitor.Services.EventDispatch;
using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Options;
Expand All @@ -13,7 +14,5 @@ internal static class FunctionBuilder
};

public static GitHubMonitorFunction Create(IEventDispatchService dispatchService = null)
=> new(dispatchService ?? new Mock<IEventDispatchService>().Object,
Options.Create(AppConfig),
new Mock<ILogger<GitHubMonitorFunction>>().Object);
=> new(dispatchService ?? new Mock<IEventDispatchService>().Object, Options.Create(AppConfig), new Mock<ILogger<GitHubMonitorFunction>>().Object);
}
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
using Ahk.GitHub.Monitor.EventHandlers;
using Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;
using Microsoft.VisualStudio.TestTools.UnitTesting;

namespace Ahk.GitHub.Monitor.Tests.UnitTests;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
using System.Threading.Tasks;
using Ahk.GitHub.Monitor.EventHandlers;
using Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;
using Ahk.GitHub.Monitor.Services;
using Ahk.GitHub.Monitor.Services.EventDispatch;
using Ahk.GitHub.Monitor.Tests.UnitTests.EventHandlersTests.Helpers;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
using System.Threading.Tasks;
using Ahk.GitHub.Monitor.EventHandlers;
using Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;
using Ahk.GitHub.Monitor.Services;
using Ahk.GitHub.Monitor.Tests.UnitTests.EventHandlersTests.Helpers;
using Microsoft.Extensions.DependencyInjection;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
using System.Threading.Tasks;
using Ahk.GitHub.Monitor.EventHandlers;
using Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;
using Ahk.GitHub.Monitor.Tests.UnitTests.EventHandlersTests.Helpers;
using Microsoft.Extensions.Logging.Abstractions;
using Microsoft.VisualStudio.TestTools.UnitTesting;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
using System.Collections.Generic;
using System.Threading.Tasks;
using Ahk.GitHub.Monitor.EventHandlers;
using Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;
using Ahk.GitHub.Monitor.EventHandlers.GradeComment;
using Ahk.GitHub.Monitor.EventHandlers.StatusTracking;
using Ahk.GitHub.Monitor.Services;
using Ahk.GitHub.Monitor.Services.GradeStore;
using Ahk.GitHub.Monitor.Services.StatusTrackingStore;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ public static GitHubClientMockFactory CreateDefault()
public IGitHubClientFactory CreateFactory()
{
var factoryMock = new Mock<IGitHubClientFactory>();
factoryMock.Setup(f => f.CreateGitHubClient(It.IsAny<long>(), NullLogger<GitHubMonitorFunction>.Instance))
factoryMock.Setup(f => f.CreateGitHubClient(It.IsAny<string>(), It.IsAny<long>(), NullLogger<GitHubMonitorFunction>.Instance))
.ReturnsAsync(this.GitHubClientMock.Object);
return factoryMock.Object;
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
using System.Threading.Tasks;
using Ahk.GitHub.Monitor.EventHandlers;
using Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;
using Ahk.GitHub.Monitor.Tests.UnitTests.EventHandlersTests.Helpers;
using Microsoft.Extensions.Logging.Abstractions;
using Microsoft.VisualStudio.TestTools.UnitTesting;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
using System.Threading.Tasks;
using Ahk.GitHub.Monitor.EventHandlers;
using Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;
using Ahk.GitHub.Monitor.Tests.UnitTests.EventHandlersTests.Helpers;
using Microsoft.Extensions.Logging.Abstractions;
using Microsoft.VisualStudio.TestTools.UnitTesting;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
using System.Threading.Tasks;
using Ahk.GitHub.Monitor.EventHandlers;
using Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;
using Ahk.GitHub.Monitor.Tests.UnitTests.EventHandlersTests.Helpers;
using Microsoft.Extensions.Logging.Abstractions;
using Microsoft.VisualStudio.TestTools.UnitTesting;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -53,3 +53,4 @@ public async Task PullRequestStatusEventIssued(string actualEventName)
*/



Original file line number Diff line number Diff line change
@@ -1,11 +1,10 @@
using System;
using System.Threading.Tasks;
using Ahk.GitHub.Monitor.EventHandlers;
using Ahk.GitHub.Monitor.EventHandlers.StatusTracking;
using Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;
using Ahk.GitHub.Monitor.Services.StatusTrackingStore;
using Ahk.GitHub.Monitor.Services.StatusTrackingStore.Dto;
using Ahk.GitHub.Monitor.Tests.UnitTests.EventHandlersTests.Helpers;
using Microsoft.Extensions.Logging.Abstractions;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using Moq;

Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,14 @@
using System;
using System.Net;
using System.Threading.Tasks;
using Ahk.GitHub.Monitor.EventHandlers;
using Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;
using Ahk.GitHub.Monitor.Services;
using Ahk.GitHub.Monitor.Tests.UnitTests.EventHandlersTests.Helpers;
using Microsoft.Extensions.Logging.Abstractions;
using Microsoft.Extensions.Caching.Memory;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using Moq;
using Octokit;

namespace Ahk.GitHub.Monitor.Tests.UnitTests.EventHandlersTests;

Expand All @@ -17,7 +22,7 @@ public async Task NonJsonPayloadReturnsError()
MemoryCacheMockFactory.Instance);
EventHandlerResult result = await eh.Execute("invalid payload");

Assert.IsTrue(result.Result.Contains("payload error", System.StringComparison.InvariantCultureIgnoreCase));
Assert.IsTrue(result.Result.Contains("payload error", StringComparison.InvariantCultureIgnoreCase));
}

[TestMethod]
Expand All @@ -27,7 +32,7 @@ public async Task EmptyPayloadReturnsError()
MemoryCacheMockFactory.Instance);
EventHandlerResult result = await eh.Execute(string.Empty);

Assert.IsTrue(result.Result.Contains("payload error", System.StringComparison.InvariantCultureIgnoreCase));
Assert.IsTrue(result.Result.Contains("payload error", StringComparison.InvariantCultureIgnoreCase));
}

[TestMethod]
Expand All @@ -37,21 +42,21 @@ public async Task InvalidPayloadReturnsError()
MemoryCacheMockFactory.Instance);
EventHandlerResult result = await eh.Execute("{a:1}");

Assert.IsTrue(result.Result.Contains("payload error", System.StringComparison.InvariantCultureIgnoreCase));
Assert.IsTrue(result.Result.Contains("payload error", StringComparison.InvariantCultureIgnoreCase));
}

[TestMethod]
public async Task NoAhkMonitorConfigYaml1()
{
GitHubClientMockFactory gitHubMock = GitHubClientMockFactory.CreateCustom()
.WithAhkMonitorConfigYamlContent(c =>
c.ThrowsAsync(new Octokit.NotFoundException(string.Empty, System.Net.HttpStatusCode.NotFound)));
c.ThrowsAsync(new NotFoundException(string.Empty, HttpStatusCode.NotFound)));

var eh = new TestHandler(gitHubMock.CreateFactory(), MemoryCacheMockFactory.Instance);
EventHandlerResult result = await eh.Execute(SampleData.BranchCreate.Body);

Assert.IsTrue(result.Result.Contains("no ahk-monitor.yml or disabled",
System.StringComparison.InvariantCultureIgnoreCase));
StringComparison.InvariantCultureIgnoreCase));
gitHubMock.GitHubClientMock.Verify(c =>
c.Repository.Content.GetAllContentsByRef(It.IsAny<long>(), ".github/ahk-monitor.yml",
It.IsAny<string>()),
Expand All @@ -62,13 +67,13 @@ public async Task NoAhkMonitorConfigYaml1()
public async Task NoAhkMonitorConfigYaml2()
{
GitHubClientMockFactory gitHubMock = GitHubClientMockFactory.CreateCustom()
.WithAhkMonitorConfigYamlContent(c => c.ReturnsAsync(new Octokit.RepositoryContent[0]));
.WithAhkMonitorConfigYamlContent(c => c.ReturnsAsync(new RepositoryContent[0]));

var eh = new TestHandler(gitHubMock.CreateFactory(), MemoryCacheMockFactory.Instance);
EventHandlerResult result = await eh.Execute(SampleData.BranchCreate.Body);

Assert.IsTrue(result.Result.Contains("no ahk-monitor.yml or disabled",
System.StringComparison.InvariantCultureIgnoreCase));
StringComparison.InvariantCultureIgnoreCase));
gitHubMock.GitHubClientMock.Verify(c =>
c.Repository.Content.GetAllContentsByRef(It.IsAny<long>(), ".github/ahk-monitor.yml",
It.IsAny<string>()),
Expand All @@ -86,7 +91,7 @@ public async Task AhkMonitorConfigYamlInvalid()
EventHandlerResult result = await eh.Execute(SampleData.BranchCreate.Body);

Assert.IsTrue(result.Result.Contains("no ahk-monitor.yml or disabled",
System.StringComparison.InvariantCultureIgnoreCase));
StringComparison.InvariantCultureIgnoreCase));
gitHubMock.GitHubClientMock.Verify(c =>
c.Repository.Content.GetAllContentsByRef(It.IsAny<long>(), ".github/ahk-monitor.yml",
It.IsAny<string>()),
Expand Down Expand Up @@ -141,22 +146,22 @@ public async Task EnabledAndHandlerCalled()
var eh = new TestHandler(gitHubMock.CreateFactory(), MemoryCacheMockFactory.Instance);
EventHandlerResult result = await eh.Execute(SampleData.BranchCreate.Body);

Assert.IsTrue(result.Result.Contains("TestHandler ok", System.StringComparison.InvariantCultureIgnoreCase));
Assert.IsTrue(result.Result.Contains("TestHandler ok", StringComparison.InvariantCultureIgnoreCase));
gitHubMock.GitHubClientMock.Verify(c =>
c.Repository.Content.GetAllContentsByRef(It.IsAny<long>(), ".github/ahk-monitor.yml",
It.IsAny<string>()),
Times.Once());
}

private class TestHandler : RepositoryEventBase<Octokit.ActivityPayload>
private class TestHandler : RepositoryEventBase<ActivityPayload>
{
public TestHandler(Services.IGitHubClientFactory gitHubClientFactory,
Microsoft.Extensions.Caching.Memory.IMemoryCache cache)
public TestHandler(IGitHubClientFactory gitHubClientFactory,
IMemoryCache cache)
: base(gitHubClientFactory, cache, ServiceProviderMock.GetMockedObject())
{
}

protected override Task<EventHandlerResult> executeCore(Octokit.ActivityPayload webhookPayload) =>
protected override Task<EventHandlerResult> executeCore(ActivityPayload webhookPayload) =>
Task.FromResult(EventHandlerResult.ActionPerformed("TestHandler ok"));
}
}
25 changes: 14 additions & 11 deletions github-monitor/Ahk.GitHub.Monitor/Ahk.GitHub.Monitor.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -26,24 +26,27 @@
</ItemGroup>

<ItemGroup>
<PackageReference Include="Azure.Extensions.AspNetCore.Configuration.Secrets" Version="1.4.0" />
<PackageReference Include="Azure.Identity" Version="1.13.2"/>
<PackageReference Include="Azure.Security.KeyVault.Secrets" Version="4.7.0"/>
<PackageReference Include="Microsoft.Azure.Core.NewtonsoftJson" Version="2.0.0"/>
<PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Http" Version="3.2.0"/>
<PackageReference Include="Polly" Version="8.4.1"/>
<PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Http" Version="3.3.0"/>
<PackageReference Include="Polly" Version="8.5.2"/>
<PackageReference Include="StyleCop.Analyzers" Version="1.2.0-beta.354">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers</IncludeAssets>
</PackageReference>
<PackageReference Include="Azure.Storage.Queues" Version="12.19.1"/>
<PackageReference Include="Microsoft.Extensions.Azure" Version="1.7.4"/>
<PackageReference Include="System.IdentityModel.Tokens.Jwt" Version="8.0.1"/>
<PackageReference Include="Microsoft.Extensions.Caching.Memory" Version="8.0.0"/>
<PackageReference Include="Azure.Storage.Queues" Version="12.21.0"/>
<PackageReference Include="Microsoft.Extensions.Azure" Version="1.10.0"/>
<PackageReference Include="System.IdentityModel.Tokens.Jwt" Version="8.5.0"/>
<PackageReference Include="Microsoft.Extensions.Caching.Memory" Version="9.0.2"/>
<FrameworkReference Include="Microsoft.AspNetCore.App"/>
<PackageReference Include="Microsoft.Azure.Functions.Worker" Version="1.23.0"/>
<PackageReference Include="Microsoft.Azure.Functions.Worker.Sdk" Version="1.17.4"/>
<PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Http.AspNetCore" Version="1.3.2"/>
<PackageReference Include="Microsoft.Azure.Functions.Worker" Version="2.0.0"/>
<PackageReference Include="Microsoft.Azure.Functions.Worker.Sdk" Version="2.0.0"/>
<PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Http.AspNetCore" Version="2.0.1"/>
<PackageReference Include="Microsoft.ApplicationInsights.WorkerService" Version="2.22.0"/>
<PackageReference Include="Microsoft.Azure.Functions.Worker.ApplicationInsights" Version="1.3.0"/>
<PackageReference Include="Octokit" Version="13.0.1"/>
<PackageReference Include="Microsoft.Azure.Functions.Worker.ApplicationInsights" Version="2.0.0"/>
<PackageReference Include="Octokit" Version="14.0.0"/>
</ItemGroup>

<ItemGroup>
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
using System;
using Azure.Identity;
using Microsoft.Extensions.Configuration;

namespace Ahk.GitHub.Monitor.Config;

public static class ConfigurationBuilderExtensions
{
public static IConfigurationBuilder AddAzureKeyVaultIfConfigured(this IConfigurationBuilder builder)
{
var keyVaultUri = Environment.GetEnvironmentVariable("KEY_VAULT_URI");

if (!string.IsNullOrEmpty(keyVaultUri))
{
var credential = new DefaultAzureCredential();
builder.AddAzureKeyVault(new Uri(keyVaultUri), credential);
}

return builder;
}
}
12 changes: 12 additions & 0 deletions github-monitor/Ahk.GitHub.Monitor/Config/GitHubMonitorConfig.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
namespace Ahk.GitHub.Monitor.Config;

public class GitHubMonitorConfig
{
private static string name = "GitHubMonitorConfig";

public string GitHubAppId { get; set; }
public string GitHubAppPrivateKey { get; set; }
public string GitHubWebhookSecret { get; set; }

public static string GetSectionName(string gitHubOrganisationName) => name + ":" + gitHubOrganisationName;
}
6 changes: 6 additions & 0 deletions github-monitor/Ahk.GitHub.Monitor/Config/QueueConfig.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
namespace Ahk.GitHub.Monitor.Config;

public class QueueConfig
{
public string EventsQueueConnectionString { get; set; }
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;
using Ahk.GitHub.Monitor.Services;
using Microsoft.Extensions.Caching.Memory;
using Octokit;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
using System;
using System.Text.RegularExpressions;

namespace Ahk.GitHub.Monitor.EventHandlers;
namespace Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;

internal static class ConfigYamlParser
{
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
namespace Ahk.GitHub.Monitor.EventHandlers;
namespace Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;

public class EventHandlerResult(string result)
{
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
using System.Threading.Tasks;

namespace Ahk.GitHub.Monitor.EventHandlers;
namespace Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;

[System.Diagnostics.CodeAnalysis.SuppressMessage("Naming", "CA1711:Identifiers should not have incorrect suffix",
Justification = "Event is a GitHub terminology in this context.")]
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
using System;
using Microsoft.Extensions.Logging;
using Octokit;
using Octokit.Internal;

namespace Ahk.GitHub.Monitor.EventHandlers.BaseAndUtils;

public class PayloadParser<TPayload>
where TPayload : ActivityPayload
{
public static bool TryParsePayload(string requestBody, out TPayload payload, out EventHandlerResult errorResult, ILogger logger)
{
payload = null;
if (string.IsNullOrEmpty(requestBody))
{
errorResult = EventHandlerResult.PayloadError("request body was empty");
logger.LogError("request body was empty");
return false;
}

try
{
payload = new SimpleJsonSerializer().Deserialize<TPayload>(requestBody);
}
catch (Exception ex)
{
errorResult = EventHandlerResult.PayloadError($"request body deserialization failed: {ex.Message}");
logger.LogError(ex, "request body deserialization failed");
return false;
}

if (payload == null)
{
errorResult = EventHandlerResult.PayloadError("parsed payload was null or empty");
logger.LogError("parsed payload was null or empty");
return false;
}

if (payload.Repository == null)
{
errorResult = EventHandlerResult.PayloadError("no repository information in webhook payload");
logger.LogError("no repository information in webhook payload");
return false;
}

errorResult = null;
return true;
}
}
Loading
Loading