Skip to content

Commit 6f96c2b

Browse files
authored
Merge branch 'trunk' into should-not-select-hidden-options
2 parents ceb1063 + e639050 commit 6f96c2b

File tree

77 files changed

+706
-717
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

77 files changed

+706
-717
lines changed

dotnet/src/webdriver/BiDi/Communication/Broker.cs

Lines changed: 35 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -83,6 +83,7 @@ internal Broker(BiDi bidi, ITransport transport)
8383
new DateTimeOffsetConverter(),
8484
new PrintPageRangeConverter(),
8585
new InputOriginConverter(),
86+
new SubscriptionConverter(),
8687
new JsonStringEnumConverter(JsonNamingPolicy.CamelCase),
8788

8889
// https://github.com/dotnet/runtime/issues/72604
@@ -111,15 +112,17 @@ public async Task ConnectAsync(CancellationToken cancellationToken)
111112
await _transport.ConnectAsync(cancellationToken).ConfigureAwait(false);
112113

113114
_receiveMessagesCancellationTokenSource = new CancellationTokenSource();
114-
_receivingMessageTask = _myTaskFactory.StartNew(async () => await ReceiveMessagesAsync(_receiveMessagesCancellationTokenSource.Token), TaskCreationOptions.LongRunning).Unwrap();
115-
_eventEmitterTask = _myTaskFactory.StartNew(async () => await ProcessEventsAwaiterAsync(), TaskCreationOptions.LongRunning).Unwrap();
115+
_receivingMessageTask = _myTaskFactory.StartNew(async () => await ReceiveMessagesAsync(_receiveMessagesCancellationTokenSource.Token)).Unwrap();
116+
_eventEmitterTask = _myTaskFactory.StartNew(ProcessEventsAwaiterAsync).Unwrap();
116117
}
117118

118119
private async Task ReceiveMessagesAsync(CancellationToken cancellationToken)
119120
{
120121
while (!cancellationToken.IsCancellationRequested)
121122
{
122-
var message = await _transport.ReceiveAsJsonAsync<Message>(_jsonSerializerContext, cancellationToken);
123+
var data = await _transport.ReceiveAsync(cancellationToken).ConfigureAwait(false);
124+
125+
var message = JsonSerializer.Deserialize(new ReadOnlySpan<byte>(data), _jsonSerializerContext.Message);
123126

124127
switch (message)
125128
{
@@ -179,21 +182,21 @@ private async Task ProcessEventsAwaiterAsync()
179182
}
180183

181184
public async Task<TResult> ExecuteCommandAsync<TCommand, TResult>(TCommand command, CommandOptions? options)
182-
where TCommand: Command
185+
where TCommand : Command
183186
{
184187
var jsonElement = await ExecuteCommandCoreAsync(command, options).ConfigureAwait(false);
185188

186189
return (TResult)jsonElement.Deserialize(typeof(TResult), _jsonSerializerContext)!;
187190
}
188191

189192
public async Task ExecuteCommandAsync<TCommand>(TCommand command, CommandOptions? options)
190-
where TCommand: Command
193+
where TCommand : Command
191194
{
192195
await ExecuteCommandCoreAsync(command, options).ConfigureAwait(false);
193196
}
194197

195198
private async Task<JsonElement> ExecuteCommandCoreAsync<TCommand>(TCommand command, CommandOptions? options)
196-
where TCommand: Command
199+
where TCommand : Command
197200
{
198201
command.Id = Interlocked.Increment(ref _currentCommandId);
199202

@@ -207,7 +210,9 @@ private async Task<JsonElement> ExecuteCommandCoreAsync<TCommand>(TCommand comma
207210

208211
_pendingCommands[command.Id] = tcs;
209212

210-
await _transport.SendAsJsonAsync(command, _jsonSerializerContext, cts.Token).ConfigureAwait(false);
213+
var data = JsonSerializer.SerializeToUtf8Bytes(command, typeof(TCommand), _jsonSerializerContext);
214+
215+
await _transport.SendAsync(data, cts.Token).ConfigureAwait(false);
211216

212217
return await tcs.Task.ConfigureAwait(false);
213218
}
@@ -219,23 +224,23 @@ public async Task<Subscription> SubscribeAsync<TEventArgs>(string eventName, Act
219224

220225
if (options is BrowsingContextsSubscriptionOptions browsingContextsOptions)
221226
{
222-
await _bidi.SessionModule.SubscribeAsync([eventName], new() { Contexts = browsingContextsOptions.Contexts }).ConfigureAwait(false);
227+
var subscribeResult = await _bidi.SessionModule.SubscribeAsync([eventName], new() { Contexts = browsingContextsOptions.Contexts }).ConfigureAwait(false);
223228

224229
var eventHandler = new SyncEventHandler<TEventArgs>(eventName, action, browsingContextsOptions?.Contexts);
225230

226231
handlers.Add(eventHandler);
227232

228-
return new Subscription(this, eventHandler);
233+
return new Subscription(subscribeResult.Subscription, this, eventHandler);
229234
}
230235
else
231236
{
232-
await _bidi.SessionModule.SubscribeAsync([eventName]).ConfigureAwait(false);
237+
var subscribeResult = await _bidi.SessionModule.SubscribeAsync([eventName]).ConfigureAwait(false);
233238

234239
var eventHandler = new SyncEventHandler<TEventArgs>(eventName, action);
235240

236241
handlers.Add(eventHandler);
237242

238-
return new Subscription(this, eventHandler);
243+
return new Subscription(subscribeResult.Subscription, this, eventHandler);
239244
}
240245
}
241246

@@ -246,44 +251,51 @@ public async Task<Subscription> SubscribeAsync<TEventArgs>(string eventName, Fun
246251

247252
if (options is BrowsingContextsSubscriptionOptions browsingContextsOptions)
248253
{
249-
await _bidi.SessionModule.SubscribeAsync([eventName], new() { Contexts = browsingContextsOptions.Contexts }).ConfigureAwait(false);
254+
var subscribeResult = await _bidi.SessionModule.SubscribeAsync([eventName], new() { Contexts = browsingContextsOptions.Contexts }).ConfigureAwait(false);
250255

251256
var eventHandler = new AsyncEventHandler<TEventArgs>(eventName, func, browsingContextsOptions.Contexts);
252257

253258
handlers.Add(eventHandler);
254259

255-
return new Subscription(this, eventHandler);
260+
return new Subscription(subscribeResult.Subscription, this, eventHandler);
256261
}
257262
else
258263
{
259-
await _bidi.SessionModule.SubscribeAsync([eventName]).ConfigureAwait(false);
264+
var subscribeResult = await _bidi.SessionModule.SubscribeAsync([eventName]).ConfigureAwait(false);
260265

261266
var eventHandler = new AsyncEventHandler<TEventArgs>(eventName, func);
262267

263268
handlers.Add(eventHandler);
264269

265-
return new Subscription(this, eventHandler);
270+
return new Subscription(subscribeResult.Subscription, this, eventHandler);
266271
}
267272
}
268273

269-
public async Task UnsubscribeAsync(EventHandler eventHandler)
274+
public async Task UnsubscribeAsync(Modules.Session.Subscription subscription, EventHandler eventHandler)
270275
{
271276
var eventHandlers = _eventHandlers[eventHandler.EventName];
272277

273278
eventHandlers.Remove(eventHandler);
274279

275-
if (eventHandler.Contexts is not null)
280+
if (subscription is not null)
276281
{
277-
if (!eventHandlers.Any(h => eventHandler.Contexts.Equals(h.Contexts)) && !eventHandlers.Any(h => h.Contexts is null))
278-
{
279-
await _bidi.SessionModule.UnsubscribeAsync([eventHandler.EventName], new() { Contexts = eventHandler.Contexts }).ConfigureAwait(false);
280-
}
282+
await _bidi.SessionModule.UnsubscribeAsync([subscription]).ConfigureAwait(false);
281283
}
282284
else
283285
{
284-
if (!eventHandlers.Any(h => h.Contexts is not null) && !eventHandlers.Any(h => h.Contexts is null))
286+
if (eventHandler.Contexts is not null)
287+
{
288+
if (!eventHandlers.Any(h => eventHandler.Contexts.Equals(h.Contexts)) && !eventHandlers.Any(h => h.Contexts is null))
289+
{
290+
await _bidi.SessionModule.UnsubscribeAsync([eventHandler.EventName], new() { Contexts = eventHandler.Contexts }).ConfigureAwait(false);
291+
}
292+
}
293+
else
285294
{
286-
await _bidi.SessionModule.UnsubscribeAsync([eventHandler.EventName]).ConfigureAwait(false);
295+
if (!eventHandlers.Any(h => h.Contexts is not null) && !eventHandlers.Any(h => h.Contexts is null))
296+
{
297+
await _bidi.SessionModule.UnsubscribeAsync([eventHandler.EventName]).ConfigureAwait(false);
298+
}
287299
}
288300
}
289301
}

dotnet/src/webdriver/BiDi/Communication/Json/BiDiJsonSerializerContext.cs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,9 @@ namespace OpenQA.Selenium.BiDi.Communication.Json;
7979
[JsonSerializable(typeof(Modules.Session.NewResult))]
8080
[JsonSerializable(typeof(Modules.Session.EndCommand))]
8181
[JsonSerializable(typeof(Modules.Session.SubscribeCommand))]
82-
[JsonSerializable(typeof(Modules.Session.UnsubscribeCommand))]
82+
[JsonSerializable(typeof(Modules.Session.SubscribeResult))]
83+
[JsonSerializable(typeof(Modules.Session.UnsubscribeByIdCommand))]
84+
[JsonSerializable(typeof(Modules.Session.UnsubscribeByAttributesCommand))]
8385

8486
[JsonSerializable(typeof(Modules.Browser.CloseCommand), TypeInfoPropertyName = "Browser_CloseCommand")]
8587
[JsonSerializable(typeof(Modules.Browser.CreateUserContextCommand))]
Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
// <copyright file="SubscriptionConverter.cs" company="Selenium Committers">
2+
// Licensed to the Software Freedom Conservancy (SFC) under one
3+
// or more contributor license agreements. See the NOTICE file
4+
// distributed with this work for additional information
5+
// regarding copyright ownership. The SFC licenses this file
6+
// to you under the Apache License, Version 2.0 (the
7+
// "License"); you may not use this file except in compliance
8+
// with the License. You may obtain a copy of the License at
9+
//
10+
// http://www.apache.org/licenses/LICENSE-2.0
11+
//
12+
// Unless required by applicable law or agreed to in writing,
13+
// software distributed under the License is distributed on an
14+
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
// KIND, either express or implied. See the License for the
16+
// specific language governing permissions and limitations
17+
// under the License.
18+
// </copyright>
19+
20+
using System;
21+
using System.Text.Json;
22+
using System.Text.Json.Serialization;
23+
24+
#nullable enable
25+
26+
namespace OpenQA.Selenium.BiDi.Communication.Json.Converters;
27+
28+
internal class SubscriptionConverter : JsonConverter<Modules.Session.Subscription>
29+
{
30+
public override Modules.Session.Subscription? Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
31+
{
32+
var id = reader.GetString();
33+
34+
return new Modules.Session.Subscription(id!);
35+
}
36+
37+
public override void Write(Utf8JsonWriter writer, Modules.Session.Subscription value, JsonSerializerOptions options)
38+
{
39+
writer.WriteStringValue(value.Id);
40+
}
41+
}

dotnet/src/webdriver/BiDi/Communication/Transport/ITransport.cs

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,6 @@
2020
using System.Threading.Tasks;
2121
using System.Threading;
2222
using System;
23-
using System.Text.Json.Serialization;
2423

2524
#nullable enable
2625

@@ -30,8 +29,7 @@ interface ITransport : IDisposable
3029
{
3130
Task ConnectAsync(CancellationToken cancellationToken);
3231

33-
Task<T> ReceiveAsJsonAsync<T>(JsonSerializerContext jsonSerializerContext, CancellationToken cancellationToken);
32+
Task<byte[]> ReceiveAsync(CancellationToken cancellationToken);
3433

35-
Task SendAsJsonAsync<TCommand>(TCommand command, JsonSerializerContext jsonSerializerContext, CancellationToken cancellationToken)
36-
where TCommand : Command;
34+
Task SendAsync(byte[] data, CancellationToken cancellationToken);
3735
}

dotnet/src/webdriver/BiDi/Communication/Transport/WebSocketTransport.cs

Lines changed: 8 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -22,10 +22,8 @@
2222
using System.Net.WebSockets;
2323
using System.Threading.Tasks;
2424
using System.Threading;
25-
using System.Text.Json;
2625
using System.Text;
2726
using OpenQA.Selenium.Internal.Logging;
28-
using System.Text.Json.Serialization;
2927

3028
#nullable enable
3129

@@ -45,7 +43,7 @@ public async Task ConnectAsync(CancellationToken cancellationToken)
4543
await _webSocket.ConnectAsync(_uri, cancellationToken).ConfigureAwait(false);
4644
}
4745

48-
public async Task<T> ReceiveAsJsonAsync<T>(JsonSerializerContext jsonSerializerContext, CancellationToken cancellationToken)
46+
public async Task<byte[]> ReceiveAsync(CancellationToken cancellationToken)
4947
{
5048
using var ms = new MemoryStream();
5149

@@ -61,31 +59,28 @@ public async Task<T> ReceiveAsJsonAsync<T>(JsonSerializerContext jsonSerializerC
6159

6260
ms.Seek(0, SeekOrigin.Begin);
6361

62+
byte[] data = ms.ToArray();
63+
6464
if (_logger.IsEnabled(LogEventLevel.Trace))
6565
{
66-
_logger.Trace($"BiDi RCV <-- {Encoding.UTF8.GetString(ms.ToArray())}");
66+
_logger.Trace($"BiDi RCV <-- {Encoding.UTF8.GetString(data)}");
6767
}
6868

69-
var res = await JsonSerializer.DeserializeAsync(ms, typeof(T), jsonSerializerContext, cancellationToken).ConfigureAwait(false);
70-
71-
return (T)res!;
69+
return data;
7270
}
7371

74-
public async Task SendAsJsonAsync<TCommand>(TCommand command, JsonSerializerContext jsonSerializerContext, CancellationToken cancellationToken)
75-
where TCommand : Command
72+
public async Task SendAsync(byte[] data, CancellationToken cancellationToken)
7673
{
77-
var buffer = JsonSerializer.SerializeToUtf8Bytes(command, typeof(TCommand), jsonSerializerContext);
78-
7974
await _socketSendSemaphoreSlim.WaitAsync(cancellationToken);
8075

8176
try
8277
{
8378
if (_logger.IsEnabled(LogEventLevel.Trace))
8479
{
85-
_logger.Trace($"BiDi SND --> {Encoding.UTF8.GetString(buffer)}");
80+
_logger.Trace($"BiDi SND --> {Encoding.UTF8.GetString(data)}");
8681
}
8782

88-
await _webSocket.SendAsync(new ArraySegment<byte>(buffer), WebSocketMessageType.Text, true, cancellationToken).ConfigureAwait(false);
83+
await _webSocket.SendAsync(new ArraySegment<byte>(data), WebSocketMessageType.Text, true, cancellationToken).ConfigureAwait(false);
8984
}
9085
finally
9186
{

dotnet/src/webdriver/BiDi/Modules/BrowsingContext/BrowsingContext.cs

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -154,6 +154,11 @@ public Task<Subscription> OnDomContentLoadedAsync(Func<NavigationInfo, Task> han
154154
return BiDi.BrowsingContext.OnDomContentLoadedAsync(handler, new BrowsingContextsSubscriptionOptions(options) { Contexts = [this] });
155155
}
156156

157+
public Task<Subscription> OnDomContentLoadedAsync(Action<NavigationInfo> handler, SubscriptionOptions? options = null)
158+
{
159+
return BiDi.BrowsingContext.OnDomContentLoadedAsync(handler, new BrowsingContextsSubscriptionOptions(options) { Contexts = [this] });
160+
}
161+
157162
public Task<Subscription> OnLoadAsync(Action<NavigationInfo> handler, SubscriptionOptions? options = null)
158163
{
159164
return BiDi.BrowsingContext.OnLoadAsync(handler, new BrowsingContextsSubscriptionOptions(options) { Contexts = [this] });
@@ -194,9 +199,14 @@ public Task<Subscription> OnNavigationFailedAsync(Func<NavigationInfo, Task> han
194199
return BiDi.BrowsingContext.OnNavigationFailedAsync(handler, new BrowsingContextsSubscriptionOptions(options) { Contexts = [this] });
195200
}
196201

197-
public Task<Subscription> OnDomContentLoadedAsync(Action<NavigationInfo> handler, SubscriptionOptions? options = null)
202+
public Task<Subscription> OnNavigationCommittedAsync(Action<NavigationInfo> handler, SubscriptionOptions? options = null)
198203
{
199-
return BiDi.BrowsingContext.OnDomContentLoadedAsync(handler, new BrowsingContextsSubscriptionOptions(options) { Contexts = [this] });
204+
return BiDi.BrowsingContext.OnNavigationCommittedAsync(handler, new BrowsingContextsSubscriptionOptions(options) { Contexts = [this] });
205+
}
206+
207+
public Task<Subscription> OnNavigationCommittedAsync(Func<NavigationInfo, Task> handler, SubscriptionOptions? options = null)
208+
{
209+
return BiDi.BrowsingContext.OnNavigationCommittedAsync(handler, new BrowsingContextsSubscriptionOptions(options) { Contexts = [this] });
200210
}
201211

202212
public override bool Equals(object? obj)

0 commit comments

Comments
 (0)