Skip to content

Commit

Permalink
Bidi: Element handle
Browse files Browse the repository at this point in the history
  • Loading branch information
kblok committed Dec 27, 2024
1 parent 8472613 commit deaae6b
Show file tree
Hide file tree
Showing 7 changed files with 142 additions and 25 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -945,21 +945,6 @@
"FAIL"
]
},
{
"comment": "This is part of organizing the webdriver bidi implementation, We will remove it one by one",
"testIdPattern": "[jshandle.spec] *JSHandle.toString*",
"platforms": [
"darwin",
"linux",
"win32"
],
"parameters": [
"webDriverBiDi"
],
"expectations": [
"FAIL"
]
},
{
"comment": "This is part of organizing the webdriver bidi implementation, We will remove it one by one",
"testIdPattern": "[keyboard.spec] *",
Expand Down
14 changes: 9 additions & 5 deletions lib/PuppeteerSharp.Tests/JSHandleTests/ToStringTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,6 @@ namespace PuppeteerSharp.Tests.JSHandleTests
{
public class ToStringTests : PuppeteerPageBaseTest
{
public ToStringTests() : base()
{
}

[Test, Retry(2), PuppeteerTest("jshandle.spec", "JSHandle JSHandle.toString", "should work for primitives")]
public async Task ShouldWorkForPrimitives()
{
Expand All @@ -23,7 +19,15 @@ public async Task ShouldWorkForPrimitives()
public async Task ShouldWorkForComplicatedObjects()
{
var aHandle = await Page.EvaluateExpressionHandleAsync("window");
Assert.That(aHandle.ToString(), Is.EqualTo("JSHandle@object"));

if (PuppeteerTestAttribute.IsCdp)
{
Assert.That(aHandle.ToString(), Is.EqualTo("JSHandle@object"));
}
else
{
Assert.That(aHandle.ToString(), Is.EqualTo("JSHandle@window"));
}
}

[Test, Retry(2), PuppeteerTest("jshandle.spec", "JSHandle JSHandle.toString", "should work with different subtypes")]
Expand Down
97 changes: 97 additions & 0 deletions lib/PuppeteerSharp/Bidi/BidiDeserializer.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
// * 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.

using System;
using System.Collections.Generic;
using System.Globalization;
using WebDriverBiDi.Script;

namespace PuppeteerSharp.Bidi;

internal static class BidiDeserializer
{
public static object ToPrettyPrint(this RemoteValue value)
{
if (value is null)
{
return null;
}

switch (value.Type)
{
case "array":
case "set":
if (value.Value is IEnumerable<RemoteValue> enumerable)
{
var list = new List<object>();

foreach (var item in enumerable)
{
list.Add(item.ToPrettyPrint());
}

return list.ToArray();
}

return Array.Empty<object>();
case "object":
case "map":
// TODO
return value.Value;
case "regexp":
case "date":
// TODO
return value.Value;
case "promise":
return "{}";
case "undefined":
return "undefined";
case "null":
return "null";
case "number":
return DeserializeNumber(value.Value);
case "bigint":
return Convert.ToInt64(value.Value, CultureInfo.InvariantCulture);
case "boolean":
return Convert.ToBoolean(value.Value, CultureInfo.InvariantCulture);
default:
return value.Value;
}
}

private static object DeserializeNumber(object value)
{
switch (value)
{
case "-0":
return -0;
case "NaN":
return double.NaN;
case "Infinity":
return double.PositiveInfinity;
case "-Infinity":
return double.NegativeInfinity;
default:
return value;
}
}
}
4 changes: 3 additions & 1 deletion lib/PuppeteerSharp/Bidi/BidiElementHandle.cs
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,9 @@

namespace PuppeteerSharp.Bidi;

internal class BidiElementHandle(RemoteValue value, BidiRealm realm) : ElementHandle
#pragma warning disable CA2000
internal class BidiElementHandle(RemoteValue value, BidiRealm realm) : ElementHandle(BidiJSHandle.From(value, realm))
#pragma warning restore CA2000
{
/// <summary>
/// Bidi Remote value.
Expand Down
23 changes: 23 additions & 0 deletions lib/PuppeteerSharp/Bidi/BidiJSHandle.cs
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,18 @@ internal class BidiJSHandle(RemoteValue value, BidiRealm realm) : JSHandle
{
public RemoteValue RemoteValue { get; } = value;

public bool IsPrimitiveValue
{
get
{
return RemoteValue.Type switch
{
"string" or "number" or "bigint" or "boolean" or "undefined" or "null" => true,
_ => false,
};
}
}

internal override Realm Realm { get; } = realm;

public static BidiJSHandle From(RemoteValue value, BidiRealm realm)
Expand All @@ -40,4 +52,15 @@ public static BidiJSHandle From(RemoteValue value, BidiRealm realm)
public override Task<T> JsonValueAsync<T>() => throw new System.NotImplementedException();

public override ValueTask DisposeAsync() => throw new System.NotImplementedException();

/// <inheritdoc/>
public override string ToString()
{
if (IsPrimitiveValue)
{
return "JSHandle:" + RemoteValue.ToPrettyPrint();
}

return "JSHandle@" + RemoteValue.Type;
}
}
5 changes: 3 additions & 2 deletions lib/PuppeteerSharp/Cdp/CdpElementHandle.cs
Original file line number Diff line number Diff line change
Expand Up @@ -39,9 +39,10 @@ public class CdpElementHandle : ElementHandle

internal CdpElementHandle(
IsolatedWorld world,
RemoteObject remoteObject)
#pragma warning disable CA2000
RemoteObject remoteObject) : base(new CdpJSHandle(world, remoteObject))
#pragma warning restore CA2000
{
Handle = new CdpJSHandle(world, remoteObject);
Logger = Realm.Environment.Client.Connection.LoggerFactory.CreateLogger(GetType());
_cdpFrame = IsolatedWorld.Frame as CdpFrame;
}
Expand Down
9 changes: 7 additions & 2 deletions lib/PuppeteerSharp/ElementHandle.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
using System.Linq;
using System.Text.Json;
using System.Threading.Tasks;
using PuppeteerSharp.Cdp;
using PuppeteerSharp.Helpers;
using PuppeteerSharp.Input;
using PuppeteerSharp.QueryHandlers;
Expand All @@ -16,8 +17,9 @@ public abstract class ElementHandle : JSHandle, IElementHandle
{
private ElementHandle _isolatedHandle;

internal ElementHandle()
internal ElementHandle(JSHandle handle)
{
Handle = handle;
}

/// <inheritdoc/>
Expand All @@ -28,13 +30,16 @@ internal ElementHandle()
/// <summary>
/// Base handle.
/// </summary>
protected JSHandle Handle { get; init; }
protected JSHandle Handle { get; }

/// <summary>
/// Element's page.
/// </summary>
protected abstract Page Page { get; }

/// <inheritdoc/>
public override string ToString() => Handle.ToString();

/// <inheritdoc/>
public Task ScreenshotAsync(string file) => ScreenshotAsync(file, new ElementScreenshotOptions());

Expand Down

0 comments on commit deaae6b

Please sign in to comment.