2
2
using System . Text ;
3
3
using System . Threading . Tasks ;
4
4
using Microsoft . AspNetCore . Hosting ;
5
- using Microsoft . AspNetCore . Http ;
6
- using Microsoft . AspNetCore . Http . Extensions ;
5
+ using Microsoft . AspNetCore . Http . Features ;
7
6
using Microsoft . AspNetCore . Mvc . ViewFeatures ;
8
7
using Microsoft . AspNetCore . Mvc . Rendering ;
9
8
using Microsoft . AspNetCore . NodeServices ;
10
9
using Microsoft . AspNetCore . Razor . TagHelpers ;
11
- using Microsoft . Extensions . PlatformAbstractions ;
12
10
using Newtonsoft . Json ;
13
11
14
12
namespace Microsoft . AspNetCore . SpaServices . Prerendering
@@ -60,7 +58,19 @@ public PrerenderTagHelper(IServiceProvider serviceProvider)
60
58
61
59
public override async Task ProcessAsync ( TagHelperContext context , TagHelperOutput output )
62
60
{
61
+ // We want to pass the original, unencoded incoming URL data through to Node, so that
62
+ // server-side code has the same view of the URL as client-side code (on the client,
63
+ // location.pathname returns an unencoded string).
64
+ // The following logic handles special characters in URL paths in the same way that
65
+ // Node and client-side JS does. For example, the path "/a=b%20c" gets passed through
66
+ // unchanged (whereas other .NET APIs do change it - Path.Value will return it as
67
+ // "/a=b c" and Path.ToString() will return it as "/a%3db%20c")
68
+ var requestFeature = ViewContext . HttpContext . Features . Get < IHttpRequestFeature > ( ) ;
69
+ var unencodedPathAndQuery = requestFeature . RawTarget ;
70
+
63
71
var request = ViewContext . HttpContext . Request ;
72
+ var unencodedAbsoluteUrl = $ "{ request . Scheme } ://{ request . Host } { unencodedPathAndQuery } ";
73
+
64
74
var result = await Prerenderer . RenderToString (
65
75
_applicationBasePath ,
66
76
_nodeServices ,
@@ -69,8 +79,8 @@ public override async Task ProcessAsync(TagHelperContext context, TagHelperOutpu
69
79
ExportName = ExportName ,
70
80
WebpackConfig = WebpackConfigPath
71
81
} ,
72
- request . GetEncodedUrl ( ) ,
73
- request . Path + request . QueryString . Value ,
82
+ unencodedAbsoluteUrl ,
83
+ unencodedPathAndQuery ,
74
84
CustomDataParameter ) ;
75
85
output . Content . SetHtmlContent ( result . Html ) ;
76
86
0 commit comments