From 2fed2315dd1bf4d08b5e25c6beb00856de006666 Mon Sep 17 00:00:00 2001 From: Oren Novotny Date: Mon, 18 Nov 2019 12:20:59 -0500 Subject: [PATCH] Get rid of query shift parameter and rely on value from dictionary key --- Refit.Tests/Refit.Tests.csproj | 4 ++-- Refit.Tests/RequestBuilder.cs | 29 ++++++++++++++++++++++++++- Refit/RequestBuilderImplementation.cs | 11 ++++------ 3 files changed, 34 insertions(+), 10 deletions(-) diff --git a/Refit.Tests/Refit.Tests.csproj b/Refit.Tests/Refit.Tests.csproj index 22ada66c1..73d65a4a1 100644 --- a/Refit.Tests/Refit.Tests.csproj +++ b/Refit.Tests/Refit.Tests.csproj @@ -11,8 +11,7 @@ - - + @@ -24,6 +23,7 @@ + diff --git a/Refit.Tests/RequestBuilder.cs b/Refit.Tests/RequestBuilder.cs index 10d3090a9..3511ffa83 100644 --- a/Refit.Tests/RequestBuilder.cs +++ b/Refit.Tests/RequestBuilder.cs @@ -708,6 +708,10 @@ Task> UploadFile(int companyId, [Get("/api/{obj.someProperty}")] Task QueryWithOptionalParametersPathBoundObject(PathBoundObject obj, [Query]string text = null, [Query]int? optionalId = null, [Query(CollectionFormat = CollectionFormat.Multi)]string[] filters = null); + + [Headers("Accept:application/json", "X-API-V: 125")] + [Get("/api/someModule/deviceList?controlId={control_id}")] + Task QueryWithHeadersBeforeData([Header("Authorization")] string authorization, [Header("X-Lng")] string twoLetterLang, string search, [AliasAs("control_id")] string controlId, string secret); } interface ICancellableMethods @@ -1594,7 +1598,7 @@ public void MultipartPostWithAliasAndHeader() public void PostBlobByteWithAlias() { var fixture = new RequestBuilderImplementation(); - var factory = fixture.BuildRequestFactoryForMethod("Blob_Post_Byte"); + var factory = fixture.BuildRequestFactoryForMethod(nameof(IDummyHttpApi.Blob_Post_Byte)); var bytes = new byte[10] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10}; @@ -1607,6 +1611,29 @@ public void PostBlobByteWithAlias() Assert.Equal("/blobstorage/the/path", uri.PathAndQuery); } + [Fact] + public void QueryWithAliasAndHeadersWorks() + { + var fixture = new RequestBuilderImplementation(); + var factory = fixture.BuildRequestFactoryForMethod(nameof(IDummyHttpApi.QueryWithHeadersBeforeData)); + + var authHeader = "theAuth"; + var langHeader = "LnG"; + var searchParam = "theSearchParam"; + var controlIdParam = "theControlId"; + var secretValue = "theSecret"; + + + + var output = factory(new object[] { authHeader, langHeader, searchParam, controlIdParam, secretValue }); + + var uri = new Uri(new Uri("http://api"), output.RequestUri); + + Assert.Equal($"/api/someModule/deviceList?controlId={controlIdParam}&search={searchParam}&secret={secretValue}", uri.PathAndQuery); + Assert.Equal(langHeader, output.Headers.GetValues("X-LnG").FirstOrDefault()); + Assert.Equal(authHeader, output.Headers.Authorization?.Scheme); + } + class RequestBuilderMock : IRequestBuilder { public int CallCount { get; private set; } diff --git a/Refit/RequestBuilderImplementation.cs b/Refit/RequestBuilderImplementation.cs index cbe9ffa78..1e0f697e7 100644 --- a/Refit/RequestBuilderImplementation.cs +++ b/Refit/RequestBuilderImplementation.cs @@ -454,8 +454,7 @@ Func> BuildRequestFactoryForMethod(RestMethod var urlTarget = (basePath == "/" ? string.Empty : basePath) + restMethod.RelativePath; var queryParamsToAdd = new List>(); var headersToAdd = new Dictionary(restMethod.Headers); - RestMethodParameterInfo parameterInfo = null; - var queryParamShift = 0; + RestMethodParameterInfo parameterInfo = null; for (var i = 0; i < paramList.Length; i++) { @@ -477,7 +476,6 @@ Func> BuildRequestFactoryForMethod(RestMethod propertyInfo.PropertyInfo.PropertyType) ?? string.Empty), RegexOptions.IgnoreCase | RegexOptions.CultureInvariant); } - queryParamShift++; //don't continue here as we want it to fall through so any parameters on this object not bound here get passed as query parameters } else @@ -511,7 +509,6 @@ Func> BuildRequestFactoryForMethod(RestMethod replacement, RegexOptions.IgnoreCase | RegexOptions.CultureInvariant); - queryParamShift++; continue; } @@ -603,7 +600,7 @@ Func> BuildRequestFactoryForMethod(RestMethod foreach (var paramValue in paramValues) { queryParamsToAdd.Add(new KeyValuePair( - restMethod.QueryParameterMap.ElementAt(i - queryParamShift).Value, + restMethod.QueryParameterMap[i], settings.UrlParameterFormatter.Format(paramValue, restMethod.ParameterInfoMap[i], restMethod.ParameterInfoMap[i].ParameterType))); } continue; @@ -620,13 +617,13 @@ Func> BuildRequestFactoryForMethod(RestMethod .Select(v => settings.UrlParameterFormatter.Format(v, restMethod.ParameterInfoMap[i], restMethod.ParameterInfoMap[i].ParameterType)); queryParamsToAdd.Add(new KeyValuePair( - restMethod.QueryParameterMap.ElementAt(i - queryParamShift).Value, + restMethod.QueryParameterMap[i], string.Join(delimiter, formattedValues))); continue; } } - queryParamsToAdd.Add(new KeyValuePair(restMethod.QueryParameterMap.ElementAt(i - queryParamShift).Value, settings.UrlParameterFormatter.Format(param, restMethod.ParameterInfoMap[i], restMethod.ParameterInfoMap[i].ParameterType))); + queryParamsToAdd.Add(new KeyValuePair(restMethod.QueryParameterMap[i], settings.UrlParameterFormatter.Format(param, restMethod.ParameterInfoMap[i], restMethod.ParameterInfoMap[i].ParameterType))); } else {