Skip to content
This repository was archived by the owner on Jan 24, 2021. It is now read-only.

Commit 2b26073

Browse files
dwonischkhellang
authored andcommitted
Replaced an unintended NullReferenceException when a partial view could not be located and introduced a ViewNotFoundException instead
Conflicts: src/Nancy.Tests.Functional/Tests/PartialViewTests.cs src/Nancy.ViewEngines.Razor/HtmlHelpers.cs
1 parent 0b0f632 commit 2b26073

File tree

6 files changed

+53
-4
lines changed

6 files changed

+53
-4
lines changed

src/Nancy.Tests.Functional/Modules/RazorTestModule.cs

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,13 @@ public RazorTestModule()
2424

2525
return serialized;
2626
};
27+
28+
Get["/razor-partialnotfound"] = _ =>
29+
{
30+
this.ViewBag.Name = "Bob";
31+
32+
return View["RazorPageWithUnknownPartial"];
33+
};
2734
}
2835
}
2936
}

src/Nancy.Tests.Functional/Nancy.Tests.Functional.csproj

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -155,6 +155,9 @@
155155
</ItemGroup>
156156
<ItemGroup>
157157
<None Include="packages.config" />
158+
<None Include="Views\RazorPageWithUnknownPartial.cshtml">
159+
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
160+
</None>
158161
<None Include="Views\_PartialTest.cshtml">
159162
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
160163
</None>

src/Nancy.Tests.Functional/Tests/PartialViewTests.cs

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
11
namespace Nancy.Tests.Functional.Tests
22
{
33
using System;
4-
using Bootstrapper;
5-
using Modules;
6-
using Testing;
4+
using Nancy.Bootstrapper;
5+
using Nancy.Testing;
6+
using Nancy.Tests.Functional.Modules;
7+
using Nancy.ViewEngines;
78
using Xunit;
89

910
public class PartialViewTests
@@ -41,5 +42,16 @@ public void When_Using_Partial_View_Then_First_Index_Of_ViewStart_Should_Equal_L
4142
// If the index is not the same then the string occurs twice...
4243
Assert.Equal(firstIndex, lastIndex);
4344
}
45+
46+
[Fact]
47+
public void When_Partial_View_Could_Not_Be_Found_An_Meaningful_Exception_Should_Be_Thrown()
48+
{
49+
Assert.Throws<ViewNotFoundException>(() =>
50+
{
51+
var response = this.browser.Get(@"/razor-partialnotfound");
52+
53+
response.Body.AsString();
54+
});
55+
}
4456
}
4557
}
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
@inherits Nancy.ViewEngines.Razor.NancyRazorViewBase<dynamic>
2+
3+
Hello @ViewBag.Name
4+
5+
@Html.Partial("_UnknownPartialTest.cshtml")

src/Nancy.ViewEngines.Razor/HtmlHelpers.cs

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,8 @@
22
{
33
using System;
44
using System.IO;
5-
using Nancy.Security;
5+
using System.Linq;
6+
using System.Security.Claims;
67

78
/// <summary>
89
/// Helpers to generate html content.
@@ -76,6 +77,10 @@ public IHtmlString Partial(string viewName, dynamic modelForPartial)
7677
{
7778
var view = this.RenderContext.LocateView(viewName, modelForPartial);
7879

80+
if (view == null) {
81+
throw new ViewNotFoundException(viewName, Engine.Extensions.ToArray());
82+
}
83+
7984
var response = this.Engine.RenderView(view, modelForPartial, this.RenderContext, true);
8085
Action<Stream> action = response.Contents;
8186
var mem = new MemoryStream();

src/Nancy/ViewEngines/ViewNotFoundException.cs

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,23 @@ public ViewNotFoundException(string viewName, string[] availableViewEngineExtens
3939
Environment.NewLine);
4040
}
4141

42+
/// <summary>
43+
/// Initializes a new instance of the <see cref="ViewNotFoundException"/>.
44+
/// </summary>
45+
/// <param name="viewName">The name of the view that was being located.</param>
46+
/// <param name="availableViewEngineExtensions">List of available view extensions that can be rendered by the available view engines.</param>
47+
public ViewNotFoundException(string viewName, string[] availableViewEngineExtensions)
48+
{
49+
this.ViewName = viewName;
50+
this.AvailableViewEngineExtensions = availableViewEngineExtensions;
51+
52+
this.message = String.Format(
53+
"Unable to locate view '{0}'{2}Currently available view engine extensions: {1}{2}",
54+
this.ViewName,
55+
string.Join(",", this.AvailableViewEngineExtensions),
56+
Environment.NewLine);
57+
}
58+
4259
/// <summary>
4360
/// Initializes a new instance of the <see cref="ViewNotFoundException"/>
4461
/// </summary>

0 commit comments

Comments
 (0)