From 35674542d7c5d3fb8f2026c86ad33542e51e0a7c Mon Sep 17 00:00:00 2001 From: Sebastian Stehle Date: Fri, 14 Sep 2018 10:10:29 +0200 Subject: [PATCH] Prerender action. --- .../Actions/Medium/MediumActionHandler.cs | 16 +++-- .../Actions/Prerender/PrerenderAction.cs | 30 ++++++++++ .../Prerender/PrerenderActionHandler.cs | 59 +++++++++++++++++++ .../HandleRules/RuleServiceTests.cs | 19 +++--- 4 files changed, 104 insertions(+), 20 deletions(-) create mode 100644 extensions/Squidex.Extensions/Actions/Prerender/PrerenderAction.cs create mode 100644 extensions/Squidex.Extensions/Actions/Prerender/PrerenderActionHandler.cs diff --git a/extensions/Squidex.Extensions/Actions/Medium/MediumActionHandler.cs b/extensions/Squidex.Extensions/Actions/Medium/MediumActionHandler.cs index a397ed05c..631e74e13 100644 --- a/extensions/Squidex.Extensions/Actions/Medium/MediumActionHandler.cs +++ b/extensions/Squidex.Extensions/Actions/Medium/MediumActionHandler.cs @@ -16,17 +16,8 @@ using Squidex.Domain.Apps.Core.HandleRules.Actions.Utils; using Squidex.Domain.Apps.Core.HandleRules.EnrichedEvents; using Squidex.Infrastructure.Http; -#pragma warning disable SA1649 // File name must match first type name - namespace Squidex.Extensions.Actions.Medium { - public sealed class MediumJob - { - public string RequestBody { get; set; } - - public string AccessToken { get; set; } - } - public sealed class MediumActionHandler : RuleActionHandler { private const string Description = "Post to medium"; @@ -131,4 +122,11 @@ namespace Squidex.Extensions.Actions.Medium return request; } } + + public sealed class MediumJob + { + public string RequestBody { get; set; } + + public string AccessToken { get; set; } + } } diff --git a/extensions/Squidex.Extensions/Actions/Prerender/PrerenderAction.cs b/extensions/Squidex.Extensions/Actions/Prerender/PrerenderAction.cs new file mode 100644 index 000000000..74c7de4c7 --- /dev/null +++ b/extensions/Squidex.Extensions/Actions/Prerender/PrerenderAction.cs @@ -0,0 +1,30 @@ +// ========================================================================== +// Squidex Headless CMS +// ========================================================================== +// Copyright (c) Squidex UG (haftungsbeschränkt) +// All rights reserved. Licensed under the MIT license. +// ========================================================================== + +using System.ComponentModel.DataAnnotations; +using Squidex.Domain.Apps.Core.Rules; + +namespace Squidex.Extensions.Actions.Prerender +{ + [RuleActionHandler(typeof(PrerenderActionHandler))] + [RuleAction( + IconImage = "", + IconColor = "#2c3e50", + Display = "Recache URL", + Description = "Create a status update at Tweet to a your user account.", + ReadMore = "https://prerender.io")] + public sealed class PrerenderAction : RuleAction + { + [Required] + [Display(Name = "Token", Description = "The prerender token from your account.")] + public string Token { get; set; } + + [Required] + [Display(Name = "Url", Description = "The url to recache.")] + public string Url { get; set; } + } +} diff --git a/extensions/Squidex.Extensions/Actions/Prerender/PrerenderActionHandler.cs b/extensions/Squidex.Extensions/Actions/Prerender/PrerenderActionHandler.cs new file mode 100644 index 000000000..e569fc25b --- /dev/null +++ b/extensions/Squidex.Extensions/Actions/Prerender/PrerenderActionHandler.cs @@ -0,0 +1,59 @@ +// ========================================================================== +// Squidex Headless CMS +// ========================================================================== +// Copyright (c) Squidex UG (haftungsbeschraenkt) +// All rights reserved. Licensed under the MIT license. +// ========================================================================== + +using System; +using System.Net.Http; +using System.Text; +using System.Threading.Tasks; +using Newtonsoft.Json.Linq; +using Squidex.Domain.Apps.Core.HandleRules; +using Squidex.Domain.Apps.Core.HandleRules.Actions.Utils; +using Squidex.Domain.Apps.Core.HandleRules.EnrichedEvents; + +namespace Squidex.Extensions.Actions.Prerender +{ + public sealed class PrerenderActionHandler : RuleActionHandler + { + private readonly IHttpClientFactory httpClientFactory; + + public PrerenderActionHandler(RuleEventFormatter formatter, IHttpClientFactory httpClientFactory) + : base(formatter) + { + this.httpClientFactory = httpClientFactory; + } + + protected override (string Description, PrerenderJob Data) CreateJob(EnrichedEvent @event, PrerenderAction action) + { + var url = Format(action.Url, @event); + + var request = + new JObject( + new JProperty("prerenderToken", action.Token), + new JProperty("url", url)); + + return ($"Recache {url}", new PrerenderJob { RequestBody = request.ToString() }); + } + + protected override async Task<(string Dump, Exception Exception)> ExecuteJobAsync(PrerenderJob job) + { + using (var httpClient = httpClientFactory.CreateClient()) + { + var request = new HttpRequestMessage(HttpMethod.Post, "https://api.prerender.io/recache") + { + Content = new StringContent(job.RequestBody, Encoding.UTF8, "application/json") + }; + + return await httpClient.OneWayRequestAsync(request, job.RequestBody); + } + } + } + + public sealed class PrerenderJob + { + public string RequestBody { get; set; } + } +} diff --git a/tests/Squidex.Domain.Apps.Core.Tests/Operations/HandleRules/RuleServiceTests.cs b/tests/Squidex.Domain.Apps.Core.Tests/Operations/HandleRules/RuleServiceTests.cs index 7f1e8a9cb..b9811bf86 100644 --- a/tests/Squidex.Domain.Apps.Core.Tests/Operations/HandleRules/RuleServiceTests.cs +++ b/tests/Squidex.Domain.Apps.Core.Tests/Operations/HandleRules/RuleServiceTests.cs @@ -120,12 +120,12 @@ namespace Squidex.Domain.Apps.Core.Operations.HandleRules [Fact] public async Task Should_not_create_job_if_too_old() { - var e = new ContentCreated { SchemaId = NamedId.Of(Guid.NewGuid(), "my-schema"), AppId = NamedId.Of(Guid.NewGuid(), "my-event") }; + var @event = new ContentCreated { SchemaId = NamedId.Of(Guid.NewGuid(), "my-schema"), AppId = NamedId.Of(Guid.NewGuid(), "my-event") }; var now = SystemClock.Instance.GetCurrentInstant(); var ruleConfig = new Rule(new ContentChangedTrigger(), new ValidAction()); - var ruleEnvelope = Envelope.Create(e); + var ruleEnvelope = Envelope.Create(@event); ruleEnvelope.SetTimestamp(now.Minus(Duration.FromDays(3))); @@ -149,12 +149,12 @@ namespace Squidex.Domain.Apps.Core.Operations.HandleRules [Fact] public async Task Should_create_job_if_triggered() { - var e = new ContentCreated { SchemaId = NamedId.Of(Guid.NewGuid(), "my-schema"), AppId = NamedId.Of(Guid.NewGuid(), "my-event") }; + var @event = new ContentCreated { SchemaId = NamedId.Of(Guid.NewGuid(), "my-schema"), AppId = NamedId.Of(Guid.NewGuid(), "my-event") }; var now = SystemClock.Instance.GetCurrentInstant(); var ruleConfig = new Rule(new ContentChangedTrigger(), new ValidAction()); - var ruleEnvelope = Envelope.Create(e); + var ruleEnvelope = Envelope.Create(@event); ruleEnvelope.SetTimestamp(now); @@ -180,7 +180,7 @@ namespace Squidex.Domain.Apps.Core.Operations.HandleRules Assert.Equal(now, job.Created); Assert.Equal(now.Plus(Duration.FromDays(2)), job.Expires); - Assert.Equal(e.AppId.Id, job.AppId); + Assert.Equal(@event.AppId.Id, job.AppId); Assert.NotEqual(Guid.Empty, job.JobId); } @@ -189,7 +189,6 @@ namespace Squidex.Domain.Apps.Core.Operations.HandleRules public async Task Should_return_succeeded_job_with_full_dump_when_handler_returns_no_exception() { var ruleJob = new JObject(); - var ruleEx = new InvalidOperationException(); var actionDump = "MyDump"; @@ -208,7 +207,6 @@ namespace Squidex.Domain.Apps.Core.Operations.HandleRules public async Task Should_return_failed_job_with_full_dump_when_handler_returns_exception() { var ruleJob = new JObject(); - var ruleEx = new InvalidOperationException(); var actionDump = "MyDump"; @@ -227,7 +225,6 @@ namespace Squidex.Domain.Apps.Core.Operations.HandleRules public async Task Should_return_timedout_job_with_full_dump_when_exception_from_handler_indicates_timeout() { var ruleJob = new JObject(); - var ruleEx = new InvalidOperationException(); var actionDump = "MyDump"; @@ -247,14 +244,14 @@ namespace Squidex.Domain.Apps.Core.Operations.HandleRules public async Task Should_create_exception_details_when_job_to_execute_failed() { var ruleJob = new JObject(); - var ruleEx = new InvalidOperationException(); + var ruleError = new InvalidOperationException(); A.CallTo(() => ruleActionHandler.ExecuteJobAsync(ruleJob)) - .Throws(ruleEx); + .Throws(ruleError); var result = await sut.InvokeAsync("ValidAction", ruleJob); - Assert.Equal((ruleEx.ToString(), RuleResult.Failed, TimeSpan.Zero), result); + Assert.Equal((ruleError.ToString(), RuleResult.Failed, TimeSpan.Zero), result); } } } \ No newline at end of file