Skip to content

Commit ace0dcb

Browse files
committed
Added more tests, Added new AllReqstars service to return pure collection, changed Route matching to use a score to pick the most relevant route.
1 parent 391b7c2 commit ace0dcb

9 files changed

Lines changed: 281 additions & 43 deletions

File tree

src/ServiceStack.ServiceInterface/Cors/CorsSupportAttribute.cs

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,13 @@
1-
using System;
2-
using System.Collections.Generic;
3-
using System.Linq;
4-
using System.Text;
1+
using System;
52
using ServiceStack.Common.Web;
63
using ServiceStack.ServiceHost;
74

85
namespace ServiceStack.ServiceInterface.Cors
96
{
107
/// <summary>
118
/// Attribute marks that specific response class has support for Cross-origin resource sharing (CORS, see http://www.w3.org/TR/access-control/). CORS allows to access resources from different domain which usually forbidden by origin policy.
12-
/// </summary>
13-
[AttributeUsage(AttributeTargets.Class, AllowMultiple = false, Inherited = true)]
9+
/// </summary>
10+
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, AllowMultiple = false, Inherited = true)]
1411
public class CorsSupportAttribute : Attribute, IHasResponseFilter
1512
{
1613
public int Priority { get { return 0; } }

src/ServiceStack.ServiceInterface/RequestFilterAttribute.cs

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,6 @@
11
using System;
2-
using System.Collections.Generic;
3-
using System.Linq;
4-
using System.Text;
52
using ServiceStack.ServiceHost;
63
using ServiceStack.Common;
7-
using ServiceStack.WebHost.Endpoints;
84

95
namespace ServiceStack.ServiceInterface
106
{

src/ServiceStack/ServiceHost/RestPath.cs

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -203,6 +203,19 @@ private void RegisterCaseInsenstivePropertyNameMappings()
203203

204204
private readonly Dictionary<string, string> propertyNamesMap = new Dictionary<string, string>();
205205

206+
public int MatchScore(string httpMethod, string[] withPathInfoParts)
207+
{
208+
var isMatch = IsMatch(httpMethod, withPathInfoParts);
209+
if (!isMatch) return -1;
210+
211+
var exactVerb = httpMethod == AllowedVerbs;
212+
var score = exactVerb ? 1 : 10;
213+
var varArgsCount = propertyNamesMap.Count;
214+
score += Math.Max((10 - varArgsCount), 1) * 100;
215+
216+
return score;
217+
}
218+
206219
/// <summary>
207220
/// For performance withPathInfoParts should already be a lower case string
208221
/// to minimize redundant matching operations.

src/ServiceStack/ServiceHost/ServiceController.cs

Lines changed: 30 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -221,22 +221,42 @@ public IRestPath GetRestPathForRequest(string httpMethod, string pathInfo)
221221
{
222222
if (!this.RestPathMap.TryGetValue(potentialHashMatch, out firstMatches)) continue;
223223

224-
foreach (var restPath in firstMatches)
225-
{
226-
if (restPath.IsMatch(httpMethod, matchUsingPathParts)) return restPath;
227-
}
228-
}
224+
var bestScore = -1;
225+
foreach (var restPath in firstMatches)
226+
{
227+
var score = restPath.MatchScore(httpMethod, matchUsingPathParts);
228+
if (score > bestScore) bestScore = score;
229+
}
230+
if (bestScore > 0)
231+
{
232+
foreach (var restPath in firstMatches)
233+
{
234+
if (bestScore == restPath.MatchScore(httpMethod, matchUsingPathParts))
235+
return restPath;
236+
}
237+
}
238+
}
229239

230240
var yieldedWildcardMatches = RestPath.GetFirstMatchWildCardHashKeys(matchUsingPathParts);
231241
foreach (var potentialHashMatch in yieldedWildcardMatches)
232242
{
233243
if (!this.RestPathMap.TryGetValue(potentialHashMatch, out firstMatches)) continue;
234244

235-
foreach (var restPath in firstMatches)
236-
{
237-
if (restPath.IsMatch(httpMethod, matchUsingPathParts)) return restPath;
238-
}
239-
}
245+
var bestScore = -1;
246+
foreach (var restPath in firstMatches)
247+
{
248+
var score = restPath.MatchScore(httpMethod, matchUsingPathParts);
249+
if (score > bestScore) bestScore = score;
250+
}
251+
if (bestScore > 0)
252+
{
253+
foreach (var restPath in firstMatches)
254+
{
255+
if (bestScore == restPath.MatchScore(httpMethod, matchUsingPathParts))
256+
return restPath;
257+
}
258+
}
259+
}
240260

241261
return null;
242262
}

tests/RazorRockstars.Console.Files/AppHost.cs

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,11 +15,14 @@ namespace RazorRockstars.Console.Files
1515
{
1616
public class AppHost : AppHostHttpListenerBase
1717
{
18-
public AppHost() : base("Test Razor", typeof(AppHost).Assembly) { }
18+
public AppHost() : base("Test Razor", typeof(AppHost).Assembly) { }
19+
20+
public bool EnableRazor = true;
1921

2022
public override void Configure(Container container)
2123
{
22-
Plugins.Add(new RazorFormat());
24+
if (EnableRazor)
25+
Plugins.Add(new RazorFormat());
2326

2427
container.Register<IDbConnectionFactory>(
2528
new OrmLiteConnectionFactory(":memory:", false, SqliteDialect.Provider));

tests/RazorRockstars.Console.Files/RazorRockstars.Console.Files.csproj

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,12 @@
7979
<None Include="NoModelNoController.cshtml">
8080
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
8181
</None>
82+
<None Include="Views\AllReqstars.cshtml">
83+
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
84+
</None>
85+
<None Include="Views\GetReqstar.cshtml">
86+
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
87+
</None>
8288
<None Include="Views\Rockstars.cshtml">
8389
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
8490
</None>

0 commit comments

Comments
 (0)