Skip to content
This repository has been archived by the owner on Nov 1, 2023. It is now read-only.

Migrating notification templates #2486

Merged
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
6 changes: 6 additions & 0 deletions src/ApiService/ApiService/OneFuzzTypes/Enums.cs
Original file line number Diff line number Diff line change
Expand Up @@ -331,8 +331,14 @@ private static readonly IReadOnlySet<NodeState> _readyForReset
}


/// Select how nodes should be disposed of after they complete a WorkSet
public enum NodeDisposalStrategy {
/// Re-images the node (which resets its state), then either it can pick up more work
tevoinea marked this conversation as resolved.
Show resolved Hide resolved
/// or auto scale will reap it if no work is queued
ScaleIn,

/// Skips re-imaging the node, the node will no longer pick up new work. It will only be
/// scaled in by auto scale.
Decommission
}

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
namespace Microsoft.OneFuzz.Service;

public class JinjaTemplateAdapter {
tevoinea marked this conversation as resolved.
Show resolved Hide resolved
public static bool IsJinjaTemplate(string jinjaTemplate) {
return jinjaTemplate.Contains("{% endfor %}")
|| jinjaTemplate.Contains("{% endif %}");
}
public static string AdaptForScriban(string jinjaTemplate) {
return jinjaTemplate.Replace("endfor", "end")
.Replace("endif", "end")
.Replace("{%", "{{")
.Replace("%}", "}}");
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -97,6 +97,7 @@ public Renderer(
// implementation doesn't have that so I'm trying to match it.
// We should probably propagate any errors up
public async Async.Task<string> Render(string templateString, Uri instanceUrl) {
templateString = JinjaTemplateAdapter.IsJinjaTemplate(templateString) ? JinjaTemplateAdapter.AdaptForScriban(templateString) : templateString;
var template = Template.Parse(templateString);
if (template != null) {
return await template.RenderAsync(new {
Expand Down
38 changes: 35 additions & 3 deletions src/ApiService/Tests/TemplateTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ public class TemplateTests {
private static readonly string _defaultTemplate = "<a href='{{ input_url }}'>This input</a> caused the <a href='{{ target_url }}'>fuzz target</a> {{ report.executable }} to crash. The faulting input SHA256 hash is {{ report.input_sha256 }} <br>";

// Original python template: "This is the call stack as determined by heuristics. You may wish to confirm this stack trace with a debugger via repro: <ul> {% for item in report.call_stack %} <li> {{ item }} </li> {% endfor %} </ul>"
private static readonly string _jinjaForLoop = "This is the call stack as determined by heuristics. You may wish to confirm this stack trace with a debugger via repro: <ul> {% for item in report.call_stack %} <li> {{ item }} </li> {% endfor %} </ul>";
// Changes for dotnet:
// * Change "endfor" in python to "end"
// * Change "{% ... %}" in python to "{{ ... }}"
Expand All @@ -24,12 +25,14 @@ public class TemplateTests {
private static readonly string _testString2 = "The OneFuzz job {{ task.job_id }} found a crash in <a href='{{ target_url }}'>{{ report.executable }}</a> with input <a href='{{ input_url }}'>{{ report.input_sha256 }}</a>. ASan log:<br><br>{{ report.asan_log }}";

// Original python template: "The fuzzing target ({{ job.project }} {{ job.name }} {{ job.build }}) reported a crash. <br> {%if report.asan_log %} AddressSanitizer reported the following details: <br> <pre> {{ report.asan_log }} </pre> {% else %} Faulting call stack: <ul> {% for item in report.call_stack %} <li> {{ item }} </li> {% endfor %} </ul> <br> {% endif %} You can reproduce the issue remotely in OneFuzz by running the following command: <pre> {{ repro_cmd }} </pre>"
private static readonly string _jinjaComplex = "The fuzzing target ({{ job.project }} {{ job.name }} {{ job.build }}) reported a crash. <br> {% if report.asan_log %} AddressSanitizer reported the following details: <br> <pre> {{ report.asan_log }} </pre> {% else %} Faulting call stack: <ul> {% for item in report.call_stack %} <li> {{ item }} </li> {% endfor %} </ul> <br> {% endif %} You can reproduce the issue remotely in OneFuzz by running the following command: <pre> {{ repro_cmd }} </pre>";
// Changes for dotnet:
// * Change "endfor" in python to "end"
// * Change "endif" in python for "end"
// * Change "{% ... %}" in python to "{{ ... }}"
// * Change job.project -> job.config.project (same for job.name, job.build). This is actually a bug, it shouldn't work in python either
private static readonly string _testString3 = "The fuzzing target ({{ job.config.project }} {{ job.config.name }} {{ job.config.build }}) reported a crash. <br> {{ if report.asan_log }} AddressSanitizer reported the following details: <br> <pre> {{ report.asan_log }} </pre> {{ else }} Faulting call stack: <ul> {{ for item in report.call_stack }} <li> {{ item }} </li> {{ end }} </ul> <br> {{ end }} You can reproduce the issue remotely in OneFuzz by running the following command: <pre> {{ repro_cmd }} </pre>";
private static readonly string _testString3 = "The fuzzing target ({{ job.project }} {{ job.name }} {{ job.build }}) reported a crash. <br> {{ if report.asan_log }} AddressSanitizer reported the following details: <br> <pre> {{ report.asan_log }} </pre> {{ else }} Faulting call stack: <ul> {{ for item in report.call_stack }} <li> {{ item }} </li> {{ end }} </ul> <br> {{ end }} You can reproduce the issue remotely in OneFuzz by running the following command: <pre> {{ repro_cmd }} </pre>";

private static readonly string _jinjaIfStatement = "{% if report.asan_log %} AddressSanitizer reported the following details: <br> <pre> {{ report.asan_log }} </pre> {% else %} Faulting call stack: <ul> {% endif %}";

[Fact]
public void CanFormatDefaultTemplate() {
Expand Down Expand Up @@ -104,7 +107,7 @@ public void CanFormatWithIfStatement() {
var output = template.Render(new {
ReproCmd = reproCmd,
Report = report,
Job = job
Job = job.Config
});

output.Should().Contain(job.Config.Project);
Expand All @@ -130,6 +133,35 @@ public void TemplatesShouldDeserializeAppropriately() {
g.Should().BeFalse();
}

[Fact]
public void CanConvertJinjaForLoop() {
_testString1.Should().BeEquivalentTo(
JinjaTemplateAdapter.AdaptForScriban(_jinjaForLoop)
);
}

[Fact]
public void CanConvertJinjaIfStatement() {
var migrated = JinjaTemplateAdapter.AdaptForScriban(_jinjaIfStatement);

migrated.Should().Contain("{{ if report.asan_log }}");
migrated.Should().Contain("{{ end }}");
}

[Fact]
public void CanConvertJinjaComplex() {
_testString3.Should().BeEquivalentTo(
JinjaTemplateAdapter.AdaptForScriban(_jinjaComplex)
);
}

[Fact]
public void CanDetectJinja() {
JinjaTemplateAdapter.IsJinjaTemplate(_jinjaIfStatement).Should().BeTrue();
JinjaTemplateAdapter.IsJinjaTemplate(_jinjaComplex).Should().BeTrue();
JinjaTemplateAdapter.IsJinjaTemplate(_jinjaForLoop).Should().BeTrue();
}

private static Report GetReport() {
return new Report(
"https://example.com",
Expand Down