Skip to content

Commit

Permalink
Fix request interception with complex PostData
Browse files Browse the repository at this point in the history
  • Loading branch information
kblok committed Sep 2, 2024
1 parent 174fe31 commit 0112e13
Show file tree
Hide file tree
Showing 14 changed files with 76 additions and 23 deletions.
2 changes: 1 addition & 1 deletion lib/PuppeteerSharp/BrowserData/JsonUtils.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@

namespace PuppeteerSharp.BrowserData
{
internal class JsonUtils
internal static class JsonUtils
{
public static async Task<T> GetAsync<T>(string url)
{
Expand Down
3 changes: 3 additions & 0 deletions lib/PuppeteerSharp/CDPSession.cs
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,9 @@ public abstract class CDPSession : ICDPSession
/// <inheritdoc/>
public string Id { get; init; }

/// <inheritdoc/>
public string CloseReason { get; protected set; }

/// <inheritdoc/>
public ILoggerFactory LoggerFactory => Connection.LoggerFactory;

Expand Down
7 changes: 3 additions & 4 deletions lib/PuppeteerSharp/Cdp/CdpCDPSession.cs
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,6 @@ public class CdpCDPSession : CDPSession
private readonly ConcurrentDictionary<int, MessageTask> _callbacks = new();
private readonly string _parentSessionId;
private readonly TargetType _targetType;
private string _closeReason;
private int _lastId;

internal CdpCDPSession(Connection connection, TargetType targetType, string sessionId, string parentSessionId)
Expand Down Expand Up @@ -79,8 +78,8 @@ public override Task DetachAsync()
throw new TargetClosedException(
$"Protocol error ({method}): Session closed. " +
$"Most likely the {_targetType} has been closed." +
$"Close reason: {_closeReason}",
_closeReason);
$"Close reason: {CloseReason}",
CloseReason);
}

var id = GetMessageId();
Expand Down Expand Up @@ -147,7 +146,7 @@ internal override void Close(string closeReason)
return;
}

_closeReason = closeReason;
CloseReason = closeReason;
IsClosed = true;

foreach (var callback in _callbacks.Values.ToArray())
Expand Down
2 changes: 1 addition & 1 deletion lib/PuppeteerSharp/Cdp/CdpHttpRequest.cs
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ internal CdpHttpRequest(
IFrame frame,
string interceptionId,
bool allowInterception,
RequestWillBeSentPayload data,
RequestWillBeSentResponse data,
List<IRequest> redirectChain,
ILoggerFactory loggerFactory)
{
Expand Down
9 changes: 8 additions & 1 deletion lib/PuppeteerSharp/Cdp/LifecycleWatcher.cs
Original file line number Diff line number Diff line change
Expand Up @@ -110,7 +110,14 @@ private void OnFrameDetached(object sender, EventArgs e)
var frame = sender as Frame;
if (_frame == frame)
{
Terminate(new PuppeteerException("Navigating frame was detached"));
var message = "Navigating frame was detached";

if (!string.IsNullOrEmpty(frame?.Client?.CloseReason))
{
message += $": {frame.Client.CloseReason}";
}

Terminate(new PuppeteerException(message));
return;
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
namespace PuppeteerSharp.Cdp.Messaging
{
internal class FetchRequestPausedResponse : RequestWillBeSentPayload
internal class FetchRequestPausedResponse : RequestWillBeSentResponse
{
public ResourceType? ResourceType { get; set; }
}
Expand Down
39 changes: 39 additions & 0 deletions lib/PuppeteerSharp/Cdp/Messaging/Request.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
// * MIT License
// *
// * Copyright (c) Darío Kondratiuk
// *
// * Permission is hereby granted, free of charge, to any person obtaining a copy
// * of this software and associated documentation files (the "Software"), to deal
// * in the Software without restriction, including without limitation the rights
// * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// * copies of the Software, and to permit persons to whom the Software is
// * furnished to do so, subject to the following conditions:
// *
// * The above copyright notice and this permission notice shall be included in all
// * copies or substantial portions of the Software.
// *
// * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// * SOFTWARE.

namespace PuppeteerSharp.Cdp.Messaging;

using System.Collections.Generic;
using System.Net.Http;

internal class Request
{
public HttpMethod Method { get; set; }

public object PostData { get; set; }

public Dictionary<string, string> Headers { get; set; } = [];

public string Url { get; set; }

public bool? HasPostData { get; set; }
}
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
namespace PuppeteerSharp.Cdp.Messaging
{
internal class RequestWillBeSentPayload
internal class RequestWillBeSentResponse
{
public string RequestId { get; set; }

public string LoaderId { get; set; }

public Payload Request { get; set; }
public Request Request { get; set; }

public ResponsePayload RedirectResponse { get; set; }

Expand Down
6 changes: 3 additions & 3 deletions lib/PuppeteerSharp/Cdp/NetworkEventManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ namespace PuppeteerSharp.Cdp
{
internal class NetworkEventManager
{
private readonly ConcurrentDictionary<string, RequestWillBeSentPayload> _requestWillBeSentMap = new();
private readonly ConcurrentDictionary<string, RequestWillBeSentResponse> _requestWillBeSentMap = new();
private readonly ConcurrentDictionary<string, FetchRequestPausedResponse> _requestPausedMap = new();
private readonly ConcurrentDictionary<string, CdpHttpRequest> _httpRequestsMap = new();
private readonly ConcurrentDictionary<string, QueuedEventGroup> _queuedEventGroupMap = new();
Expand Down Expand Up @@ -59,10 +59,10 @@ internal ResponseReceivedExtraInfoResponse ShiftResponseExtraInfo(string network
return result;
}

internal void StoreRequestWillBeSent(string networkRequestId, RequestWillBeSentPayload e)
internal void StoreRequestWillBeSent(string networkRequestId, RequestWillBeSentResponse e)
=> _requestWillBeSentMap.AddOrUpdate(networkRequestId, e, (_, _) => e);

internal RequestWillBeSentPayload GetRequestWillBeSent(string networkRequestId)
internal RequestWillBeSentResponse GetRequestWillBeSent(string networkRequestId)
{
_requestWillBeSentMap.TryGetValue(networkRequestId, out var result);
return result;
Expand Down
8 changes: 4 additions & 4 deletions lib/PuppeteerSharp/Cdp/NetworkManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -173,7 +173,7 @@ private async void Client_MessageReceived(object sender, MessageEventArgs e)
await OnAuthRequiredAsync(client, e.MessageData.ToObject<FetchAuthRequiredResponse>()).ConfigureAwait(false);
break;
case "Network.requestWillBeSent":
await OnRequestWillBeSentAsync(client, e.MessageData.ToObject<RequestWillBeSentPayload>()).ConfigureAwait(false);
await OnRequestWillBeSentAsync(client, e.MessageData.ToObject<RequestWillBeSentResponse>()).ConfigureAwait(false);
break;
case "Network.requestServedFromCache":
OnRequestServedFromCache(e.MessageData.ToObject<RequestServedFromCacheResponse>());
Expand Down Expand Up @@ -462,7 +462,7 @@ private async void OnRequestWithoutNetworkInstrumentationAsync(CDPSession client
_ = request.FinalizeInterceptionsAsync();
}

private async Task OnRequestAsync(CDPSession client, RequestWillBeSentPayload e, string fetchRequestId)
private async Task OnRequestAsync(CDPSession client, RequestWillBeSentResponse e, string fetchRequestId)
{
CdpHttpRequest request;
var redirectChain = new List<IRequest>();
Expand Down Expand Up @@ -549,7 +549,7 @@ private void HandleRequestRedirect(CDPSession client, CdpHttpRequest request, Re
RequestFinished?.Invoke(this, new RequestEventArgs(request));
}

private async Task OnRequestWillBeSentAsync(CDPSession client, RequestWillBeSentPayload e)
private async Task OnRequestWillBeSentAsync(CDPSession client, RequestWillBeSentResponse e)
{
// Request interception doesn't happen for data URLs with Network Service.
if (_userRequestInterceptionEnabled && !e.Request.Url.StartsWith("data:", StringComparison.InvariantCultureIgnoreCase))
Expand All @@ -571,7 +571,7 @@ private async Task OnRequestWillBeSentAsync(CDPSession client, RequestWillBeSent
await OnRequestAsync(client, e, null).ConfigureAwait(false);
}

private void PatchRequestEventHeaders(RequestWillBeSentPayload requestWillBeSentEvent, FetchRequestPausedResponse requestPausedEvent)
private void PatchRequestEventHeaders(RequestWillBeSentResponse requestWillBeSentEvent, FetchRequestPausedResponse requestPausedEvent)
{
foreach (var kv in requestPausedEvent.Request.Headers)
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -165,7 +165,7 @@ namespace PuppeteerSharp.Helpers.Json;
[JsonSerializable(typeof(RemoteObjectSubtype))]
[JsonSerializable(typeof(RemoteObjectType))]
[JsonSerializable(typeof(RequestServedFromCacheResponse))]
[JsonSerializable(typeof(RequestWillBeSentPayload))]
[JsonSerializable(typeof(RequestWillBeSentResponse))]
[JsonSerializable(typeof(ResponsePayload))]
[JsonSerializable(typeof(ResponseReceivedExtraInfoResponse))]
[JsonSerializable(typeof(ResponseReceivedResponse))]
Expand Down
5 changes: 5 additions & 0 deletions lib/PuppeteerSharp/ICDPSession.cs
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,11 @@ public interface ICDPSession : ICDPConnection
/// <value>The session identifier.</value>
string Id { get; }

/// <summary>
/// Close reason if the session has been closed.
/// </summary>
string CloseReason { get; }

/// <summary>
/// Detaches session from target. Once detached, session won't emit any events and can't be used to send messages.
/// </summary>
Expand Down
8 changes: 4 additions & 4 deletions lib/PuppeteerSharp/PuppeteerSharp.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -12,10 +12,10 @@
<Description>Headless Browser .NET API</Description>
<PackageId>PuppeteerSharp</PackageId>
<PackageReleaseNotes></PackageReleaseNotes>
<PackageVersion>19.0.2</PackageVersion>
<ReleaseVersion>19.0.2</ReleaseVersion>
<AssemblyVersion>19.0.2</AssemblyVersion>
<FileVersion>19.0.2</FileVersion>
<PackageVersion>19.0.3</PackageVersion>
<ReleaseVersion>19.0.3</ReleaseVersion>
<AssemblyVersion>19.0.3</AssemblyVersion>
<FileVersion>19.0.3</FileVersion>
<SynchReleaseVersion>false</SynchReleaseVersion>
<StyleCopTreatErrorsAsWarnings>false</StyleCopTreatErrorsAsWarnings>
<DebugType>embedded</DebugType>
Expand Down
2 changes: 1 addition & 1 deletion lib/PuppeteerSharp/RedirectInfo.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ namespace PuppeteerSharp
{
internal class RedirectInfo
{
public RequestWillBeSentPayload Event { get; set; }
public RequestWillBeSentResponse Event { get; set; }

public string FetchRequestId { get; set; }
}
Expand Down

0 comments on commit 0112e13

Please sign in to comment.