Skip to content

Commit 5e4fa1c

Browse files
Adopt spector/parameters/path (#7237)
fixes: #7053
1 parent c38096e commit 5e4fa1c

File tree

3 files changed

+62
-5
lines changed

3 files changed

+62
-5
lines changed

packages/http-client-csharp/generator/Microsoft.TypeSpec.Generator.ClientModel/src/Providers/RestClientProvider.cs

Lines changed: 22 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -234,7 +234,7 @@ private IEnumerable<MethodBodyStatement> AppendHeaderParameters(HttpRequestApi r
234234
if (!TryGetSpecialHeaderParam(inputParameter, out _) && (!inputParameter.IsRequired || type?.IsNullable == true ||
235235
(type is { IsValueType: false, IsFrameworkType: true } && type.FrameworkType != typeof(string))))
236236
{
237-
statement = BuildQueryOrHeaderParameterNullCheck(type, valueExpression, statement);
237+
statement = BuildQueryOrHeaderOrPathParameterNullCheck(type, valueExpression, statement);
238238
}
239239

240240
statements.Add(statement);
@@ -309,7 +309,7 @@ private static List<MethodBodyStatement> AppendQueryParameters(ScopedApi uri, In
309309
if (!inputParameter.IsRequired || paramType?.IsNullable == true ||
310310
(paramType is { IsValueType: false, IsFrameworkType: true } && paramType.FrameworkType != typeof(string)))
311311
{
312-
statement = BuildQueryOrHeaderParameterNullCheck(paramType, valueExpression, statement);
312+
statement = BuildQueryOrHeaderOrPathParameterNullCheck(paramType, valueExpression, statement);
313313
}
314314

315315
statements.Add(statement);
@@ -318,7 +318,7 @@ private static List<MethodBodyStatement> AppendQueryParameters(ScopedApi uri, In
318318
return statements;
319319
}
320320

321-
private static IfStatement BuildQueryOrHeaderParameterNullCheck(
321+
private static IfStatement BuildQueryOrHeaderOrPathParameterNullCheck(
322322
CSharpType? parameterType,
323323
ValueExpression valueExpression,
324324
MethodBodyStatement originalStatement)
@@ -384,7 +384,8 @@ private void AddUriSegments(
384384
break;
385385
}
386386

387-
statements.Add(uri.AppendPath(Literal(pathSpan.Slice(0, paramIndex).ToString()), false).Terminate());
387+
var path = pathSpan.Slice(0, paramIndex);
388+
statements.Add(uri.AppendPath(Literal(path.ToString()), false).Terminate());
388389
pathSpan = pathSpan.Slice(paramIndex + 1);
389390
var paramEndIndex = pathSpan.IndexOf('}');
390391
var paramName = pathSpan.Slice(0, paramEndIndex).ToString();
@@ -424,7 +425,23 @@ private void AddUriSegments(
424425
valueExpression = type?.Equals(typeof(string)) == true
425426
? valueExpression
426427
: valueExpression.Invoke(nameof(ToString), toStringParams);
427-
statements.Add(uri.AppendPath(valueExpression, escape).Terminate());
428+
MethodBodyStatement statement;
429+
if (inputParam?.IsRequired == false)
430+
{
431+
bool shouldPrependWithPathSeparator = path.Length > 0 && path[^1] != '/';
432+
List<MethodBodyStatement> appendPathStatements = shouldPrependWithPathSeparator
433+
? [uri.AppendPath(Literal("/"), false).Terminate(), uri.AppendPath(valueExpression, escape).Terminate()]
434+
: [uri.AppendPath(valueExpression, escape).Terminate()];
435+
statement = BuildQueryOrHeaderOrPathParameterNullCheck(
436+
type,
437+
valueExpression,
438+
appendPathStatements);
439+
}
440+
else
441+
{
442+
statement = uri.AppendPath(valueExpression, escape).Terminate();
443+
}
444+
statements.Add(statement);
428445
}
429446

430447
pathSpan = pathSpan.Slice(paramEndIndex + 1);
Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
// Copyright (c) Microsoft Corporation. All rights reserved.
2+
// Licensed under the MIT License.
3+
4+
using System;
5+
using System.ClientModel;
6+
using System.ClientModel.Primitives;
7+
using System.Collections.Generic;
8+
using System.Linq;
9+
using System.Reflection;
10+
using System.Threading;
11+
using System.Threading.Tasks;
12+
using NUnit.Framework;
13+
using Parameters.Path;
14+
15+
namespace TestProjects.Spector.Tests.Http.Parameters.Path
16+
{
17+
public class PathTests : SpectorTestBase
18+
{
19+
[SpectorTest]
20+
public Task Normal() => Test(async (host) =>
21+
{
22+
var client = new PathClient(host, null);
23+
var name = "foo";
24+
ClientResult response = await client.NormalAsync(name);
25+
Assert.AreEqual(204, response.GetRawResponse().Status);
26+
});
27+
28+
[SpectorTest]
29+
[TestCase(true)]
30+
[TestCase(false)]
31+
public Task OptionalPathParamIncluded(bool isOptional) => Test(async (host) =>
32+
{
33+
var client = new PathClient(host, null);
34+
string? name = isOptional ? null : "foo";
35+
ClientResult response = await client.OptionalAsync(name);
36+
Assert.AreEqual(204, response.GetRawResponse().Status);
37+
});
38+
}
39+
}

packages/http-client-csharp/generator/TestProjects/Spector.Tests/TestProjects.Spector.Tests.csproj

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@
4040
<ProjectReference Include="$(RepoRoot)\TestProjects\Spector\http\parameters\body-optionality\src\Parameters.BodyOptionality.csproj" />
4141
<ProjectReference Include="$(RepoRoot)\TestProjects\Spector\http\parameters\collection-format\src\Parameters.CollectionFormat.csproj" />
4242
<ProjectReference Include="$(RepoRoot)\TestProjects\Spector\http\parameters\spread\src\Parameters.Spread.csproj" />
43+
<ProjectReference Include="$(RepoRoot)\TestProjects\Spector\http\parameters\path\src\Parameters.Path.csproj" />
4344
<ProjectReference Include="$(RepoRoot)\TestProjects\Spector\http\payload\content-negotiation\src\Payload.ContentNegotiation.csproj" />
4445
<ProjectReference Include="$(RepoRoot)\TestProjects\Spector\http\payload\json-merge-patch\src\Payload.JsonMergePatch.csproj" />
4546
<ProjectReference Include="$(RepoRoot)\TestProjects\Spector\http\payload\media-type\src\Payload.MediaType.csproj" />

0 commit comments

Comments
 (0)