Bug 204078 - [Clipboard API] Add support for Clipboard.write()
Summary: [Clipboard API] Add support for Clipboard.write()
Status: RESOLVED FIXED
Alias: None
Product: WebKit
Classification: Unclassified
Component: HTML Editing (show other bugs)
Version: WebKit Nightly Build
Hardware: Unspecified Unspecified
: P2 Normal
Assignee: Wenson Hsieh
URL:
Keywords: InRadar
Depends on:
Blocks:
 
Reported: 2019-11-11 12:06 PST by Wenson Hsieh
Modified: 2019-11-13 22:44 PST (History)
8 users (show)

See Also:


Attachments
Patch (43.98 KB, patch)
2019-11-11 17:02 PST, Wenson Hsieh
no flags Details | Formatted Diff | Diff
Fix GTK/WPE (41.69 KB, patch)
2019-11-11 17:07 PST, Wenson Hsieh
no flags Details | Formatted Diff | Diff
Fix macOS 10.13 build (41.77 KB, patch)
2019-11-11 17:25 PST, Wenson Hsieh
rniwa: review+
ews-watchlist: commit-queue-
Details | Formatted Diff | Diff
Archive of layout-test-results from ews215 for win-future (14.41 MB, application/zip)
2019-11-12 14:38 PST, EWS Watchlist
no flags Details
Patch for EWS (41.67 KB, patch)
2019-11-13 17:16 PST, Wenson Hsieh
no flags Details | Formatted Diff | Diff

Note You need to log in before you can comment on or make changes to this bug.
Description Wenson Hsieh 2019-11-11 12:06:25 PST
Implement basic support for Clipboard.write().
Comment 1 Radar WebKit Bug Importer 2019-11-11 12:06:52 PST
<rdar://problem/57087756>
Comment 2 Wenson Hsieh 2019-11-11 17:02:48 PST Comment hidden (obsolete)
Comment 3 Wenson Hsieh 2019-11-11 17:07:03 PST Comment hidden (obsolete)
Comment 4 Wenson Hsieh 2019-11-11 17:25:18 PST
Created attachment 383324 [details]
Fix macOS 10.13 build
Comment 5 EWS Watchlist 2019-11-12 14:38:03 PST Comment hidden (obsolete)
Comment 6 EWS Watchlist 2019-11-12 14:38:05 PST Comment hidden (obsolete)
Comment 7 Ryosuke Niwa 2019-11-13 14:01:24 PST
Comment on attachment 383324 [details]
Fix macOS 10.13 build

View in context: https://bugs.webkit.org/attachment.cgi?id=383324&action=review

> Source/WebCore/Modules/async-clipboard/Clipboard.cpp:191
> +    auto shouldProceedWithClipboardWrite = [&] {

It seems like this can just be a static function which takes frame as an argument instead of a lambda?

> Source/WebCore/Modules/async-clipboard/Clipboard.cpp:225
> +    for (size_t index = 0; index < items.size(); ++index) {
> +        items[index]->collectDataForWriting(*this, [index, collector = makeRef(*m_activeItemWriter)] (auto data) {
> +            collector->setData(WTFMove(data), index);
> +        });
> +    }

Why isn't this code in ItemWriter?
Also, it's weird to call ItemWriter a collector. Let's use a consistent name (writer) here.

> Source/WebCore/Modules/async-clipboard/Clipboard.cpp:246
> +void Clipboard::ItemWriter::setData(Optional<PasteboardCustomData>&& data, size_t index)

Please put these code below the constructor in the order they are declared.

> Source/WebCore/Modules/async-clipboard/Clipboard.cpp:255
> +    if (!--m_pendingItemCount)

Like the other code I reviewed, I really don't want to see a decrement statement on its own like this. This will lead to bugs.

> Source/WebCore/Modules/async-clipboard/Clipboard.cpp:265
> +Clipboard::ItemWriter::ItemWriter(Clipboard& clipboard, Ref<DeferredPromise>&& promise, size_t numberOfItems)

It's very awkward that this constructor the number of items an argument.
I think this should just take Vector<RefPtr<ClipboardItem>> as an argument instead.

> Source/WebCore/Modules/async-clipboard/Clipboard.cpp:309
> +void Clipboard::ItemWriter::resolveOrReject(ResolveOrReject resolveOrReject)

This is an awkward helper function. Why don't we have resolve & reject helper functions instead?
Then there is only one place where we resolve so we don't even need resolve.

> LayoutTests/editing/async-clipboard/clipboard-change-data-while-writing.html:50
> +            await UIHelper.activateElement(copyButton);
> +            await new Promise(resolve => shouldBecomeEqual("finishedWriting", "true", resolve));
> +
> +            copyButton.remove();

What is trigging a change to the pasteboard content while we're writing?
Comment 8 Wenson Hsieh 2019-11-13 17:03:54 PST
Comment on attachment 383324 [details]
Fix macOS 10.13 build

View in context: https://bugs.webkit.org/attachment.cgi?id=383324&action=review

>> Source/WebCore/Modules/async-clipboard/Clipboard.cpp:191
>> +    auto shouldProceedWithClipboardWrite = [&] {
> 
> It seems like this can just be a static function which takes frame as an argument instead of a lambda?

Turned this into a static function.

>> Source/WebCore/Modules/async-clipboard/Clipboard.cpp:225
>> +    }
> 
> Why isn't this code in ItemWriter?
> Also, it's weird to call ItemWriter a collector. Let's use a consistent name (writer) here.

Good catch — it looks like I forgot to rename this local variable when I renamed ClipboardItemDataCollector to Clipboard::ItemWriter.

I also moved this logic into a new helper method on ItemWriter, called write, that takes a Vector of ClipboardItems; this also allows us to make setData() private instead of public.

>> Source/WebCore/Modules/async-clipboard/Clipboard.cpp:246
>> +void Clipboard::ItemWriter::setData(Optional<PasteboardCustomData>&& data, size_t index)
> 
> Please put these code below the constructor in the order they are declared.

Fixed!

>> Source/WebCore/Modules/async-clipboard/Clipboard.cpp:255
>> +    if (!--m_pendingItemCount)
> 
> Like the other code I reviewed, I really don't want to see a decrement statement on its own like this. This will lead to bugs.

I refactored this so the code to initialize m_pendingItemCount and decrement it is all in the same method, next to each other.

>> Source/WebCore/Modules/async-clipboard/Clipboard.cpp:265
>> +Clipboard::ItemWriter::ItemWriter(Clipboard& clipboard, Ref<DeferredPromise>&& promise, size_t numberOfItems)
> 
> It's very awkward that this constructor the number of items an argument.
> I think this should just take Vector<RefPtr<ClipboardItem>> as an argument instead.

I’ve removed the `numberOfItems` parameter.

>> Source/WebCore/Modules/async-clipboard/Clipboard.cpp:309
>> +void Clipboard::ItemWriter::resolveOrReject(ResolveOrReject resolveOrReject)
> 
> This is an awkward helper function. Why don't we have resolve & reject helper functions instead?
> Then there is only one place where we resolve so we don't even need resolve.

Good call — I refactored this so that we only have a reject() helper.

I also renamed `finish()` to `didSetAllData()`, to better reflect its purpose.

>> LayoutTests/editing/async-clipboard/clipboard-change-data-while-writing.html:50
>> +            copyButton.remove();
> 
> What is trigging a change to the pasteboard content while we're writing?

The call to copyText("foo”) above changes the system pasteboard.
Comment 9 Wenson Hsieh 2019-11-13 17:16:53 PST
Created attachment 383523 [details]
Patch for EWS
Comment 10 WebKit Commit Bot 2019-11-13 22:39:15 PST
Comment on attachment 383523 [details]
Patch for EWS

Clearing flags on attachment: 383523

Committed r252450: <https://trac.webkit.org/changeset/252450>