mirror of
https://github.com/JustArchiNET/ArchiSteamFarm
synced 2024-11-10 07:04:27 +00:00
Unify WebBrowser API in regards to nullable bodies (#2593)
* Unify logic for nullable bodies * Update ArchiWebHandler.cs * Misc
This commit is contained in:
parent
d82df0074f
commit
715ed034df
9 changed files with 56 additions and 165 deletions
|
@ -41,7 +41,7 @@ internal static class CatAPI {
|
|||
|
||||
ObjectResponse<MeowResponse>? response = await webBrowser.UrlGetToJsonObject<MeowResponse>(request).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
|
|
|
@ -530,7 +530,7 @@ internal sealed class SteamTokenDumperPlugin : OfficialPlugin, IASF, IBot, IBotC
|
|||
|
||||
ASF.ArchiLogger.LogGenericInfo(string.Format(CultureInfo.CurrentCulture, Strings.SubmissionInProgress, appTokens.Count, packageTokens.Count, depotKeys.Count));
|
||||
|
||||
OptionalObjectResponse<ResponseData>? response = await ASF.WebBrowser.UrlPostToOptionalJsonObject<ResponseData, RequestData>(request, data: requestData, requestOptions: WebBrowser.ERequestOptions.ReturnClientErrors | WebBrowser.ERequestOptions.AllowInvalidBodyOnErrors).ConfigureAwait(false);
|
||||
ObjectResponse<ResponseData>? response = await ASF.WebBrowser.UrlPostToJsonObject<ResponseData, RequestData>(request, data: requestData, requestOptions: WebBrowser.ERequestOptions.ReturnClientErrors | WebBrowser.ERequestOptions.AllowInvalidBodyOnErrors).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
ASF.ArchiLogger.LogGenericWarning(ArchiSteamFarm.Localization.Strings.WarningFailed);
|
||||
|
|
|
@ -93,7 +93,7 @@ internal static class ArchiNet {
|
|||
|
||||
ObjectResponse<ChecksumResponse>? response = await ASF.WebBrowser.UrlGetToJsonObject<ChecksumResponse>(request).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
|
|
|
@ -181,7 +181,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
|
||||
response = await UrlGetToJsonObjectWithSession<InventoryResponse>(request, requestOptions: WebBrowser.ERequestOptions.ReturnServerErrors, rateLimitingDelay: rateLimitingDelay).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
throw new HttpRequestException(string.Format(CultureInfo.CurrentCulture, Strings.ErrorObjectIsNull, nameof(response)));
|
||||
}
|
||||
|
||||
|
@ -210,7 +210,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
}
|
||||
}
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
throw new HttpRequestException(string.Format(CultureInfo.CurrentCulture, Strings.ErrorObjectIsNull, nameof(response)));
|
||||
}
|
||||
|
||||
|
@ -434,7 +434,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
for (byte i = 0; (i < WebBrowser.MaxTries) && (response == null); i++) {
|
||||
response = await UrlPostToJsonObjectWithSession<TradeOfferSendResponse>(request, data: data, referer: referer, requestOptions: WebBrowser.ERequestOptions.ReturnServerErrors).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
return (false, mobileTradeOfferIDs);
|
||||
}
|
||||
|
||||
|
@ -453,7 +453,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
}
|
||||
}
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
return (false, mobileTradeOfferIDs);
|
||||
}
|
||||
|
||||
|
@ -1231,7 +1231,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
|
||||
ObjectResponse<ResultResponse>? response = await UrlPostToJsonObjectWithSession<ResultResponse>(request, data: data).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -1263,7 +1263,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
for (byte i = 0; (i < WebBrowser.MaxTries) && (response == null); i++) {
|
||||
response = await UrlPostToJsonObjectWithSession<TradeOfferAcceptResponse>(request, data: data, referer: referer, requestOptions: WebBrowser.ERequestOptions.ReturnServerErrors).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
return (false, false);
|
||||
}
|
||||
|
||||
|
@ -1282,7 +1282,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
}
|
||||
}
|
||||
|
||||
return response != null ? (true, response.Content.RequiresMobileConfirmation) : (false, false);
|
||||
return response?.Content != null ? (true, response.Content.RequiresMobileConfirmation) : (false, false);
|
||||
}
|
||||
|
||||
internal async Task<(EResult Result, EPurchaseResultDetail PurchaseResult)> AddFreeLicense(uint subID) {
|
||||
|
@ -1354,7 +1354,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
|
||||
ObjectResponse<ResultResponse>? response = await UrlPostToJsonObjectWithSession<ResultResponse>(request, data: data).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -1400,7 +1400,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
|
||||
ObjectResponse<NewDiscoveryQueueResponse>? response = await UrlPostToJsonObjectWithSession<NewDiscoveryQueueResponse>(request, data: data).ConfigureAwait(false);
|
||||
|
||||
return response?.Content.Queue;
|
||||
return response?.Content?.Queue;
|
||||
}
|
||||
|
||||
internal async Task<HashSet<TradeOffer>?> GetActiveTradeOffers() {
|
||||
|
@ -1717,7 +1717,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
|
||||
using HtmlDocumentResponse? response = await UrlGetToHtmlDocumentWithSession(request, checkSessionPreemptively: false).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
|
@ -1763,7 +1763,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
|
||||
using HtmlDocumentResponse? response = await UrlGetToHtmlDocumentWithSession(request, checkSessionPreemptively: false).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
|
@ -1855,7 +1855,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
|
||||
using HtmlDocumentResponse? response = await UrlGetToHtmlDocumentWithSession(request, checkSessionPreemptively: false).ConfigureAwait(false);
|
||||
|
||||
IElement? htmlNode = response?.Content.SelectSingleNode("//div[@class='pagecontent']/script");
|
||||
IElement? htmlNode = response?.Content?.SelectSingleNode("//div[@class='pagecontent']/script");
|
||||
|
||||
if (htmlNode == null) {
|
||||
// Trade can be no longer valid
|
||||
|
@ -2005,7 +2005,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
|
||||
ObjectResponse<BooleanResponse>? response = await UrlGetToJsonObjectWithSession<BooleanResponse>(request).ConfigureAwait(false);
|
||||
|
||||
return response?.Content.Success;
|
||||
return response?.Content?.Success;
|
||||
}
|
||||
|
||||
internal async Task<bool?> HandleConfirmations(string deviceID, string confirmationHash, uint time, IReadOnlyCollection<Confirmation> confirmations, bool accept) {
|
||||
|
@ -2059,7 +2059,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
|
||||
ObjectResponse<BooleanResponse>? response = await UrlPostToJsonObjectWithSession<BooleanResponse>(request, data: data).ConfigureAwait(false);
|
||||
|
||||
return response?.Content.Success;
|
||||
return response?.Content?.Success;
|
||||
}
|
||||
|
||||
internal async Task<bool> Init(ulong steamID, EUniverse universe, string webAPIUserNonce, string? parentalCode = null) {
|
||||
|
@ -2253,7 +2253,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
|
||||
ObjectResponse<RedeemWalletResponse>? response = await UrlPostToJsonObjectWithSession<RedeemWalletResponse>(request, data: data).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
|
@ -2292,7 +2292,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
|
||||
ObjectResponse<ResultResponse>? response = await UrlPostToJsonObjectWithSession<ResultResponse>(request, data: data).ConfigureAwait(false);
|
||||
|
||||
return response?.Content.Result == EResult.OK;
|
||||
return response?.Content?.Result == EResult.OK;
|
||||
}
|
||||
|
||||
private async Task<(ESteamApiKeyState State, string? Key)> GetApiKeyState() {
|
||||
|
@ -2300,7 +2300,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
|
||||
using HtmlDocumentResponse? response = await UrlGetToHtmlDocumentWithSession(request, checkSessionPreemptively: false).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
return (ESteamApiKeyState.Timeout, null);
|
||||
}
|
||||
|
||||
|
@ -2570,7 +2570,7 @@ public sealed class ArchiWebHandler : IDisposable {
|
|||
ObjectResponse<AccessTokenResponse>? response = await UrlGetToJsonObjectWithSession<AccessTokenResponse>(request).ConfigureAwait(false);
|
||||
|
||||
// ReSharper disable once RedundantSuppressNullableWarningExpression - required for .NET Framework
|
||||
return !string.IsNullOrEmpty(response?.Content.Data.WebAPIToken) ? (true, response!.Content.Data.WebAPIToken) : (false, null);
|
||||
return !string.IsNullOrEmpty(response?.Content?.Data.WebAPIToken) ? (true, response!.Content!.Data.WebAPIToken) : (false, null);
|
||||
}
|
||||
|
||||
private async Task<(bool Success, string? Result)> ResolveApiKey() {
|
||||
|
|
|
@ -73,19 +73,19 @@ internal static class GitHub {
|
|||
|
||||
Uri request = new($"{SharedInfo.ProjectURL}/wiki/{page}/_history");
|
||||
|
||||
using HtmlDocumentResponse? response = await ASF.WebBrowser.UrlGetToHtmlDocument(request, requestOptions: WebBrowser.ERequestOptions.ReturnClientErrors).ConfigureAwait(false);
|
||||
using HtmlDocumentResponse? response = await ASF.WebBrowser.UrlGetToHtmlDocument(request, requestOptions: WebBrowser.ERequestOptions.ReturnClientErrors | WebBrowser.ERequestOptions.AllowInvalidBodyOnErrors).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
if (response.StatusCode.IsClientErrorCode()) {
|
||||
if (response?.StatusCode.IsClientErrorCode() == true) {
|
||||
return response.StatusCode switch {
|
||||
HttpStatusCode.NotFound => new Dictionary<string, DateTime>(0),
|
||||
_ => null
|
||||
};
|
||||
}
|
||||
|
||||
if (response?.Content == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
IEnumerable<IElement> revisionNodes = response.Content.SelectNodes("//li[contains(@class, 'wiki-history-revision')]");
|
||||
|
||||
Dictionary<string, DateTime> result = new();
|
||||
|
@ -148,7 +148,7 @@ internal static class GitHub {
|
|||
|
||||
using HtmlDocumentResponse? response = await ASF.WebBrowser.UrlGetToHtmlDocument(request).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
if (response?.Content == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
|
|
|
@ -23,22 +23,19 @@ using System;
|
|||
using System.Threading.Tasks;
|
||||
using AngleSharp;
|
||||
using AngleSharp.Dom;
|
||||
using ArchiSteamFarm.Core;
|
||||
using JetBrains.Annotations;
|
||||
|
||||
namespace ArchiSteamFarm.Web.Responses;
|
||||
|
||||
public sealed class HtmlDocumentResponse : BasicResponse, IDisposable {
|
||||
[PublicAPI]
|
||||
public IDocument Content { get; }
|
||||
public IDocument? Content { get; }
|
||||
|
||||
private HtmlDocumentResponse(BasicResponse basicResponse, IDocument content) : base(basicResponse) {
|
||||
ArgumentNullException.ThrowIfNull(basicResponse);
|
||||
public HtmlDocumentResponse(BasicResponse basicResponse) : base(basicResponse) => ArgumentNullException.ThrowIfNull(basicResponse);
|
||||
|
||||
Content = content ?? throw new ArgumentNullException(nameof(content));
|
||||
}
|
||||
private HtmlDocumentResponse(BasicResponse basicResponse, IDocument content) : this(basicResponse) => Content = content ?? throw new ArgumentNullException(nameof(content));
|
||||
|
||||
public void Dispose() => Content.Dispose();
|
||||
public void Dispose() => Content?.Dispose();
|
||||
|
||||
[PublicAPI]
|
||||
public static async Task<HtmlDocumentResponse?> Create(StreamResponse streamResponse) {
|
||||
|
@ -46,14 +43,8 @@ public sealed class HtmlDocumentResponse : BasicResponse, IDisposable {
|
|||
|
||||
IBrowsingContext context = BrowsingContext.New();
|
||||
|
||||
try {
|
||||
IDocument document = await context.OpenAsync(req => req.Content(streamResponse.Content, true)).ConfigureAwait(false);
|
||||
IDocument document = await context.OpenAsync(request => request.Content(streamResponse.Content, true)).ConfigureAwait(false);
|
||||
|
||||
return new HtmlDocumentResponse(streamResponse, document);
|
||||
} catch (Exception e) {
|
||||
ASF.ArchiLogger.LogGenericWarningException(e);
|
||||
|
||||
return null;
|
||||
}
|
||||
return new HtmlDocumentResponse(streamResponse, document);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -26,11 +26,9 @@ namespace ArchiSteamFarm.Web.Responses;
|
|||
|
||||
public sealed class ObjectResponse<T> : BasicResponse {
|
||||
[PublicAPI]
|
||||
public T Content { get; }
|
||||
public T? Content { get; }
|
||||
|
||||
public ObjectResponse(BasicResponse basicResponse, T content) : base(basicResponse) {
|
||||
ArgumentNullException.ThrowIfNull(basicResponse);
|
||||
public ObjectResponse(BasicResponse basicResponse, T? content) : this(basicResponse) => Content = content;
|
||||
|
||||
Content = content ?? throw new ArgumentNullException(nameof(content));
|
||||
}
|
||||
public ObjectResponse(BasicResponse basicResponse) : base(basicResponse) => ArgumentNullException.ThrowIfNull(basicResponse);
|
||||
}
|
||||
|
|
|
@ -1,38 +0,0 @@
|
|||
// _ _ _ ____ _ _____
|
||||
// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___
|
||||
// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \
|
||||
// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | |
|
||||
// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_|
|
||||
// |
|
||||
// Copyright 2015-2022 Łukasz "JustArchi" Domeradzki
|
||||
// Contact: JustArchi@JustArchi.net
|
||||
// |
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
// |
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
// |
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
using System;
|
||||
using JetBrains.Annotations;
|
||||
|
||||
namespace ArchiSteamFarm.Web.Responses;
|
||||
|
||||
public sealed class OptionalObjectResponse<T> : BasicResponse {
|
||||
[PublicAPI]
|
||||
public T? Content { get; }
|
||||
|
||||
public OptionalObjectResponse(BasicResponse basicResponse, T? content) : base(basicResponse) {
|
||||
ArgumentNullException.ThrowIfNull(basicResponse);
|
||||
|
||||
Content = content;
|
||||
}
|
||||
|
||||
public OptionalObjectResponse(BasicResponse basicResponse) : base(basicResponse) => ArgumentNullException.ThrowIfNull(basicResponse);
|
||||
}
|
|
@ -266,6 +266,10 @@ public sealed class WebBrowser : IDisposable {
|
|||
try {
|
||||
return await HtmlDocumentResponse.Create(response).ConfigureAwait(false);
|
||||
} catch (Exception e) {
|
||||
if ((requestOptions.HasFlag(ERequestOptions.AllowInvalidBodyOnSuccess) && response.StatusCode.IsSuccessCode()) || (requestOptions.HasFlag(ERequestOptions.AllowInvalidBodyOnErrors) && !response.StatusCode.IsSuccessCode())) {
|
||||
return new HtmlDocumentResponse(response);
|
||||
}
|
||||
|
||||
ArchiLogger.LogGenericWarningException(e);
|
||||
ArchiLogger.LogGenericDebug(string.Format(CultureInfo.CurrentCulture, Strings.ErrorFailingRequest, request));
|
||||
}
|
||||
|
@ -332,6 +336,10 @@ public sealed class WebBrowser : IDisposable {
|
|||
|
||||
obj = serializer.Deserialize<T>(jsonReader);
|
||||
} catch (Exception e) {
|
||||
if ((requestOptions.HasFlag(ERequestOptions.AllowInvalidBodyOnSuccess) && response.StatusCode.IsSuccessCode()) || (requestOptions.HasFlag(ERequestOptions.AllowInvalidBodyOnErrors) && !response.StatusCode.IsSuccessCode())) {
|
||||
return new ObjectResponse<T>(response);
|
||||
}
|
||||
|
||||
ArchiLogger.LogGenericWarningException(e);
|
||||
ArchiLogger.LogGenericDebug(string.Format(CultureInfo.CurrentCulture, Strings.ErrorFailingRequest, request));
|
||||
|
||||
|
@ -339,6 +347,10 @@ public sealed class WebBrowser : IDisposable {
|
|||
}
|
||||
|
||||
if (obj is null) {
|
||||
if ((requestOptions.HasFlag(ERequestOptions.AllowInvalidBodyOnSuccess) && response.StatusCode.IsSuccessCode()) || (requestOptions.HasFlag(ERequestOptions.AllowInvalidBodyOnErrors) && !response.StatusCode.IsSuccessCode())) {
|
||||
return new ObjectResponse<T>(response);
|
||||
}
|
||||
|
||||
ArchiLogger.LogGenericWarning(string.Format(CultureInfo.CurrentCulture, Strings.ErrorIsEmpty, nameof(obj)));
|
||||
|
||||
continue;
|
||||
|
@ -573,6 +585,10 @@ public sealed class WebBrowser : IDisposable {
|
|||
try {
|
||||
return await HtmlDocumentResponse.Create(response).ConfigureAwait(false);
|
||||
} catch (Exception e) {
|
||||
if ((requestOptions.HasFlag(ERequestOptions.AllowInvalidBodyOnSuccess) && response.StatusCode.IsSuccessCode()) || (requestOptions.HasFlag(ERequestOptions.AllowInvalidBodyOnErrors) && !response.StatusCode.IsSuccessCode())) {
|
||||
return new HtmlDocumentResponse(response);
|
||||
}
|
||||
|
||||
ArchiLogger.LogGenericWarningException(e);
|
||||
ArchiLogger.LogGenericDebug(string.Format(CultureInfo.CurrentCulture, Strings.ErrorFailingRequest, request));
|
||||
}
|
||||
|
@ -599,82 +615,6 @@ public sealed class WebBrowser : IDisposable {
|
|||
throw new ArgumentOutOfRangeException(nameof(rateLimitingDelay));
|
||||
}
|
||||
|
||||
for (byte i = 0; i < maxTries; i++) {
|
||||
if ((i > 0) && (rateLimitingDelay > 0)) {
|
||||
await Task.Delay(rateLimitingDelay).ConfigureAwait(false);
|
||||
}
|
||||
|
||||
StreamResponse? response = await UrlPostToStream(request, headers, data, referer, requestOptions | ERequestOptions.ReturnClientErrors, 1, rateLimitingDelay).ConfigureAwait(false);
|
||||
|
||||
if (response == null) {
|
||||
// Request timed out, try again
|
||||
continue;
|
||||
}
|
||||
|
||||
await using (response.ConfigureAwait(false)) {
|
||||
if (response.StatusCode.IsRedirectionCode()) {
|
||||
if (!requestOptions.HasFlag(ERequestOptions.ReturnRedirections)) {
|
||||
// We're not handling this error, do not try again
|
||||
break;
|
||||
}
|
||||
} else if (response.StatusCode.IsClientErrorCode()) {
|
||||
if (!requestOptions.HasFlag(ERequestOptions.ReturnClientErrors)) {
|
||||
// We're not handling this error, do not try again
|
||||
break;
|
||||
}
|
||||
} else if (response.StatusCode.IsServerErrorCode()) {
|
||||
if (!requestOptions.HasFlag(ERequestOptions.ReturnServerErrors)) {
|
||||
// We're not handling this error, try again
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
TResult? obj;
|
||||
|
||||
try {
|
||||
using StreamReader steamReader = new(response.Content);
|
||||
using JsonReader jsonReader = new JsonTextReader(steamReader);
|
||||
|
||||
JsonSerializer serializer = new();
|
||||
|
||||
obj = serializer.Deserialize<TResult>(jsonReader);
|
||||
} catch (Exception e) {
|
||||
ArchiLogger.LogGenericWarningException(e);
|
||||
ArchiLogger.LogGenericDebug(string.Format(CultureInfo.CurrentCulture, Strings.ErrorFailingRequest, request));
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
if (obj is null) {
|
||||
ArchiLogger.LogGenericWarning(string.Format(CultureInfo.CurrentCulture, Strings.ErrorIsEmpty, nameof(obj)));
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
return new ObjectResponse<TResult>(response, obj);
|
||||
}
|
||||
}
|
||||
|
||||
if (maxTries > 1) {
|
||||
ArchiLogger.LogGenericWarning(string.Format(CultureInfo.CurrentCulture, Strings.ErrorRequestFailedTooManyTimes, maxTries));
|
||||
ArchiLogger.LogGenericDebug(string.Format(CultureInfo.CurrentCulture, Strings.ErrorFailingRequest, request));
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
[PublicAPI]
|
||||
public async Task<OptionalObjectResponse<TResult>?> UrlPostToOptionalJsonObject<TResult, TData>(Uri request, IReadOnlyCollection<KeyValuePair<string, string>>? headers = null, TData? data = null, Uri? referer = null, ERequestOptions requestOptions = ERequestOptions.None, byte maxTries = MaxTries, int rateLimitingDelay = 0) where TData : class {
|
||||
ArgumentNullException.ThrowIfNull(request);
|
||||
|
||||
if (maxTries == 0) {
|
||||
throw new ArgumentOutOfRangeException(nameof(maxTries));
|
||||
}
|
||||
|
||||
if (rateLimitingDelay < 0) {
|
||||
throw new ArgumentOutOfRangeException(nameof(rateLimitingDelay));
|
||||
}
|
||||
|
||||
for (byte i = 0; i < maxTries; i++) {
|
||||
if ((i > 0) && (rateLimitingDelay > 0)) {
|
||||
await Task.Delay(rateLimitingDelay).ConfigureAwait(false);
|
||||
|
@ -716,7 +656,7 @@ public sealed class WebBrowser : IDisposable {
|
|||
obj = serializer.Deserialize<TResult>(jsonReader);
|
||||
} catch (Exception e) {
|
||||
if ((requestOptions.HasFlag(ERequestOptions.AllowInvalidBodyOnSuccess) && response.StatusCode.IsSuccessCode()) || (requestOptions.HasFlag(ERequestOptions.AllowInvalidBodyOnErrors) && !response.StatusCode.IsSuccessCode())) {
|
||||
return new OptionalObjectResponse<TResult>(response);
|
||||
return new ObjectResponse<TResult>(response);
|
||||
}
|
||||
|
||||
ArchiLogger.LogGenericWarningException(e);
|
||||
|
@ -727,7 +667,7 @@ public sealed class WebBrowser : IDisposable {
|
|||
|
||||
if (obj is null) {
|
||||
if ((requestOptions.HasFlag(ERequestOptions.AllowInvalidBodyOnSuccess) && response.StatusCode.IsSuccessCode()) || (requestOptions.HasFlag(ERequestOptions.AllowInvalidBodyOnErrors) && !response.StatusCode.IsSuccessCode())) {
|
||||
return new OptionalObjectResponse<TResult>(response);
|
||||
return new ObjectResponse<TResult>(response);
|
||||
}
|
||||
|
||||
ArchiLogger.LogGenericWarning(string.Format(CultureInfo.CurrentCulture, Strings.ErrorIsEmpty, nameof(obj)));
|
||||
|
@ -735,7 +675,7 @@ public sealed class WebBrowser : IDisposable {
|
|||
continue;
|
||||
}
|
||||
|
||||
return new OptionalObjectResponse<TResult>(response, obj);
|
||||
return new ObjectResponse<TResult>(response, obj);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue