Changeset 238471 in webkit


Ignore:
Timestamp:
Nov 24, 2018 1:06:09 PM (5 years ago)
Author:
Wenson Hsieh
Message:

[Cocoa] Add WKWebView SPI to trigger and remove data detection
https://bugs.webkit.org/show_bug.cgi?id=191918
<rdar://problem/36185051>

Reviewed by Tim Horton.

Source/WebCore:

Add a helper method on DataDetection to remove all data detected links in the given document. See WebKit changes
for more detail.

  • editing/cocoa/DataDetection.h:
  • editing/cocoa/DataDetection.mm:

(WebCore::DataDetection::removeDataDetectedLinksInDocument):

Source/WebKit:

Adds support for two new WKWebView SPI methods, -_detectDataWithTypes:completionHandler: and
-_removeAllDataDetectedLinks:, to allow internal WebKit clients to run data detection and add links to data
detected content, or remove all data detected links from the document.

Test: WebKit.AddAndRemoveDataDetectors

  • Shared/Cocoa/DataDetectionResult.h:
  • Shared/Cocoa/DataDetectionResult.mm:

(WebKit::DataDetectionResult::decode):

Modernize DataDetectionResult's IPC decoding, so that it can be used with reply-based async IPC.

  • UIProcess/API/Cocoa/WKWebView.mm:

(-[WKWebView _removeDataDetectedLinks:]):
(-[WKWebView _detectDataWithTypes:completionHandler:]):

  • UIProcess/API/Cocoa/WKWebViewPrivate.h:
  • UIProcess/WebPageProxy.cpp:

(WebKit::WebPageProxy::detectDataInAllFrames):
(WebKit::WebPageProxy::removeDataDetectedLinks):

Add or remove data detected links from each frame in the page, and then propagate the new data detector
results of the main frame to the UI process (this matches current behavior, where the results of -[WKWebView
_dataDetectionResults] only reflects data detection results in the main frame of the page).

  • UIProcess/WebPageProxy.h:
  • WebProcess/WebPage/WebPage.cpp:

(WebKit::WebPage::removeDataDetectedLinks):
(WebKit::WebPage::detectDataInAllFrames):

  • WebProcess/WebPage/WebPage.h:
  • WebProcess/WebPage/WebPage.messages.in:

Tools:

Add an API test to exercise the new WebKit SPI.

  • TestWebKitAPI/DataDetectorsCoreSPI.h: Added.
  • TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj:
  • TestWebKitAPI/Tests/WebKitCocoa/DataDetection.mm:

(-[WKWebView synchronouslyDetectDataWithTypes:]):
(-[WKWebView synchronouslyRemoveDataDetectedLinks]):
(TEST):

  • TestWebKitAPI/Tests/WebKitCocoa/WKAttachmentTests.mm:

(TestWebKitAPI::TEST):
(-[TestWKWebView tagsInBody]): Deleted.
(-[TestWKWebView expectElementTagsInOrder:]): Deleted.
(-[TestWKWebView expectElementCount:tagName:]): Deleted.
(-[TestWKWebView expectElementTag:toComeBefore:]): Deleted.

Rename this from -expectElementCount:tagName: to -expectElementCount:querySelector:.

  • TestWebKitAPI/Tests/WebKitCocoa/data-detectors.html: Added.

Add a new test page containing some content that can be data detected.

  • TestWebKitAPI/cocoa/TestWKWebView.h:
  • TestWebKitAPI/cocoa/TestWKWebView.mm:

(-[WKWebView tagsInBody]):
(-[WKWebView expectElementTagsInOrder:]):
(-[WKWebView expectElementCount:querySelector:]):
(-[WKWebView expectElementTag:toComeBefore:]):

Move some testing helper functions from WKAttachmentTests to a testing category on WKWebView. This allows us to
use -expectElementCount:querySelector: in tests outside of WKAttachmentTests.

(-[WKWebView objectByEvaluatingJavaScript:]):
(-[WKWebView objectByEvaluatingJavaScriptWithUserGesture:]):
(-[WKWebView stringByEvaluatingJavaScript:]):

Move some common helper functions from TestWKWebView to a testing category on WKWebView.

(-[TestWKWebView objectByEvaluatingJavaScript:]): Deleted.
(-[TestWKWebView objectByEvaluatingJavaScriptWithUserGesture:]): Deleted.
(-[TestWKWebView stringByEvaluatingJavaScript:]): Deleted.

Location:
trunk
Files:
1 added
19 edited
1 copied

Legend:

Unmodified
Added
Removed
  • trunk/Source/WebCore/ChangeLog

    r238470 r238471  
     12018-11-24  Wenson Hsieh  <wenson_hsieh@apple.com>
     2
     3        [Cocoa] Add WKWebView SPI to trigger and remove data detection
     4        https://bugs.webkit.org/show_bug.cgi?id=191918
     5        <rdar://problem/36185051>
     6
     7        Reviewed by Tim Horton.
     8
     9        Add a helper method on DataDetection to remove all data detected links in the given document. See WebKit changes
     10        for more detail.
     11
     12        * editing/cocoa/DataDetection.h:
     13        * editing/cocoa/DataDetection.mm:
     14        (WebCore::DataDetection::removeDataDetectedLinksInDocument):
     15
    1162018-11-24  Andy Estes  <aestes@apple.com>
    217
  • trunk/Source/WebCore/editing/cocoa/DataDetection.h

    r237266 r238471  
    3838namespace WebCore {
    3939
     40class Document;
    4041class Element;
    4142class FloatRect;
     
    6263#endif
    6364    WEBCORE_EXPORT static NSArray *detectContentInRange(RefPtr<Range>& contextRange, DataDetectorTypes, NSDictionary *context);
     65    WEBCORE_EXPORT static void removeDataDetectedLinksInDocument(Document&);
    6466#if PLATFORM(IOS_FAMILY)
    6567    WEBCORE_EXPORT static bool canBePresentedByDataDetectors(const URL&);
  • trunk/Source/WebCore/editing/cocoa/DataDetection.mm

    r238470 r238471  
    430430}
    431431
     432void DataDetection::removeDataDetectedLinksInDocument(Document& document)
     433{
     434    Vector<Ref<HTMLAnchorElement>> allAnchorElements;
     435    for (auto& anchor : descendantsOfType<HTMLAnchorElement>(document))
     436        allAnchorElements.append(anchor);
     437
     438    for (auto& anchor : allAnchorElements)
     439        removeResultLinksFromAnchor(anchor.get());
     440}
     441
    432442NSArray *DataDetection::detectContentInRange(RefPtr<Range>& contextRange, DataDetectorTypes types, NSDictionary *context)
    433443{
     
    648658
    649659#else
     660
    650661NSArray *DataDetection::detectContentInRange(RefPtr<Range>&, DataDetectorTypes, NSDictionary *)
    651662{
    652663    return nil;
    653664}
     665
     666void DataDetection::removeDataDetectedLinksInDocument(Document&)
     667{
     668}
     669
    654670#endif
    655671
  • trunk/Source/WebKit/ChangeLog

    r238470 r238471  
     12018-11-24  Wenson Hsieh  <wenson_hsieh@apple.com>
     2
     3        [Cocoa] Add WKWebView SPI to trigger and remove data detection
     4        https://bugs.webkit.org/show_bug.cgi?id=191918
     5        <rdar://problem/36185051>
     6
     7        Reviewed by Tim Horton.
     8
     9        Adds support for two new WKWebView SPI methods, `-_detectDataWithTypes:completionHandler:` and
     10        `-_removeAllDataDetectedLinks:`, to allow internal WebKit clients to run data detection and add links to data
     11        detected content, or remove all data detected links from the document.
     12
     13        Test: WebKit.AddAndRemoveDataDetectors
     14
     15        * Shared/Cocoa/DataDetectionResult.h:
     16        * Shared/Cocoa/DataDetectionResult.mm:
     17        (WebKit::DataDetectionResult::decode):
     18
     19        Modernize DataDetectionResult's IPC decoding, so that it can be used with reply-based async IPC.
     20
     21        * UIProcess/API/Cocoa/WKWebView.mm:
     22        (-[WKWebView _removeDataDetectedLinks:]):
     23        (-[WKWebView _detectDataWithTypes:completionHandler:]):
     24        * UIProcess/API/Cocoa/WKWebViewPrivate.h:
     25        * UIProcess/WebPageProxy.cpp:
     26        (WebKit::WebPageProxy::detectDataInAllFrames):
     27        (WebKit::WebPageProxy::removeDataDetectedLinks):
     28
     29        Add or remove data detected links from each frame in the page, and then propagate the new data detector
     30        results of the main frame to the UI process (this matches current behavior, where the results of -[WKWebView
     31        _dataDetectionResults] only reflects data detection results in the main frame of the page).
     32
     33        * UIProcess/WebPageProxy.h:
     34        * WebProcess/WebPage/WebPage.cpp:
     35        (WebKit::WebPage::removeDataDetectedLinks):
     36        (WebKit::WebPage::detectDataInAllFrames):
     37        * WebProcess/WebPage/WebPage.h:
     38        * WebProcess/WebPage/WebPage.messages.in:
     39
    1402018-11-24  Andy Estes  <aestes@apple.com>
    241
  • trunk/Source/WebKit/Shared/Cocoa/DataDetectionResult.h

    r204668 r238471  
    3939
    4040    void encode(IPC::Encoder&) const;
    41     static bool decode(IPC::Decoder&, DataDetectionResult&);
     41    static std::optional<DataDetectionResult> decode(IPC::Decoder&);
    4242};
    4343
  • trunk/Source/WebKit/Shared/Cocoa/DataDetectionResult.mm

    r232520 r238471  
    4747}
    4848
    49 bool DataDetectionResult::decode(IPC::Decoder& decoder, DataDetectionResult& result)
     49std::optional<DataDetectionResult> DataDetectionResult::decode(IPC::Decoder& decoder)
    5050{
    5151    RetainPtr<CFDataRef> data;
    5252    if (!IPC::decode(decoder, data))
    53         return false;
     53        return std::nullopt;
    5454
     55    DataDetectionResult result;
    5556    auto unarchiver = secureUnarchiverFromData((__bridge NSData *)data.get());
    5657    @try {
     
    5859    } @catch (NSException *exception) {
    5960        LOG_ERROR("Failed to decode NSArray of DDScanResult: %@", exception);
    60         return false;
     61        return std::nullopt;
    6162    }
    6263   
    6364    [unarchiver finishDecoding];
    64     return true;
     65    return { WTFMove(result) };
    6566}
    6667#endif
  • trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebView.mm

    r238468 r238471  
    54245424}
    54255425
     5426- (void)_removeDataDetectedLinks:(dispatch_block_t)completion
     5427{
     5428#if ENABLE(DATA_DETECTION)
     5429    _page->removeDataDetectedLinks([completion = makeBlockPtr(completion), page = makeWeakPtr(_page.get())] (auto& result) {
     5430        if (page)
     5431            page->setDataDetectionResult(result);
     5432        if (completion)
     5433            completion();
     5434    });
     5435#else
     5436    UNUSED_PARAM(completion);
     5437#endif
     5438}
     5439
    54265440#pragma mark iOS-specific methods
    54275441
    54285442#if PLATFORM(IOS_FAMILY)
     5443
     5444- (void)_detectDataWithTypes:(WKDataDetectorTypes)types completionHandler:(dispatch_block_t)completion
     5445{
     5446#if ENABLE(DATA_DETECTION)
     5447    _page->detectDataInAllFrames(fromWKDataDetectorTypes(types), [completion = makeBlockPtr(completion), page = makeWeakPtr(_page.get())] (auto& result) {
     5448        if (page)
     5449            page->setDataDetectionResult(result);
     5450        if (completion)
     5451            completion();
     5452    });
     5453#else
     5454    UNUSED_PARAM(types);
     5455    UNUSED_PARAM(completion);
     5456#endif
     5457}
    54295458
    54305459#if ENABLE(FULLSCREEN_API)
  • trunk/Source/WebKit/UIProcess/API/Cocoa/WKWebViewPrivate.h

    r238388 r238471  
    2828#if WK_API_ENABLED
    2929
     30#import <WebKit/WKDataDetectorTypes.h>
    3031#import <WebKit/_WKActivatedElementInfo.h>
    3132#import <WebKit/_WKAttachment.h>
     
    194195
    195196- (void)_isJITEnabled:(void(^)(BOOL))completionHandler WK_API_AVAILABLE(macosx(WK_MAC_TBA), ios(WK_IOS_TBA));
     197- (void)_removeDataDetectedLinks:(dispatch_block_t)completion WK_API_AVAILABLE(macosx(WK_MAC_TBA), ios(WK_IOS_TBA));
     198
    196199- (IBAction)_alignCenter:(id)sender WK_API_AVAILABLE(macosx(WK_MAC_TBA), ios(WK_IOS_TBA));
    197200- (IBAction)_alignJustified:(id)sender WK_API_AVAILABLE(macosx(WK_MAC_TBA), ios(WK_IOS_TBA));
     
    216219- (void)_setFontSize:(CGFloat)fontSize sender:(id)sender WK_API_AVAILABLE(ios(WK_IOS_TBA));
    217220- (void)_setTextColor:(UIColor *)color sender:(id)sender WK_API_AVAILABLE(ios(WK_IOS_TBA));
     221
     222- (void)_detectDataWithTypes:(WKDataDetectorTypes)types completionHandler:(dispatch_block_t)completion WK_API_AVAILABLE(ios(WK_IOS_TBA));
    218223
    219224// DERECATED: The setters of the three following function are deprecated, please use overrideLayoutParameters.
  • trunk/Source/WebKit/UIProcess/WebPageProxy.cpp

    r238438 r238471  
    82448244}
    82458245
     8246#if ENABLE(DATA_DETECTION)
     8247
     8248void WebPageProxy::detectDataInAllFrames(WebCore::DataDetectorTypes types, CompletionHandler<void(const DataDetectionResult&)>&& completionHandler)
     8249{
     8250    m_process->connection()->sendWithAsyncReply(Messages::WebPage::DetectDataInAllFrames(static_cast<uint64_t>(types)), WTFMove(completionHandler), m_pageID);
     8251}
     8252
     8253void WebPageProxy::removeDataDetectedLinks(CompletionHandler<void(const DataDetectionResult&)>&& completionHandler)
     8254{
     8255    m_process->connection()->sendWithAsyncReply(Messages::WebPage::RemoveDataDetectedLinks(), WTFMove(completionHandler), m_pageID);
     8256}
     8257
     8258#endif
     8259
    82468260} // namespace WebKit
    82478261
  • trunk/Source/WebKit/UIProcess/WebPageProxy.h

    r238468 r238471  
    363363#if ENABLE(DATA_DETECTION)
    364364    NSArray *dataDetectionResults() { return m_dataDetectionResults.get(); }
     365    void detectDataInAllFrames(WebCore::DataDetectorTypes, CompletionHandler<void(const DataDetectionResult&)>&&);
     366    void removeDataDetectedLinks(CompletionHandler<void(const DataDetectionResult&)>&&);
    365367#endif
    366368       
  • trunk/Source/WebKit/WebProcess/WebPage/WebPage.cpp

    r238454 r238471  
    33863386
    33873387#if ENABLE(DATA_DETECTION)
     3388
    33883389void WebPage::setDataDetectionResults(NSArray *detectionResults)
    33893390{
     
    33923393    send(Messages::WebPageProxy::SetDataDetectionResult(dataDetectionResult));
    33933394}
    3394 #endif
     3395
     3396void WebPage::removeDataDetectedLinks(Messages::WebPage::RemoveDataDetectedLinks::AsyncReply&& reply)
     3397{
     3398    for (auto frame = makeRefPtr(&m_page->mainFrame()); frame; frame = frame->tree().traverseNext()) {
     3399        auto document = makeRefPtr(frame->document());
     3400        if (!document)
     3401            continue;
     3402
     3403        DataDetection::removeDataDetectedLinksInDocument(*document);
     3404        frame->setDataDetectionResults(nullptr);
     3405    }
     3406    reply({ m_page->mainFrame().dataDetectionResults() });
     3407}
     3408
     3409void WebPage::detectDataInAllFrames(uint64_t types, Messages::WebPage::DetectDataInAllFrames::AsyncReply&& reply)
     3410{
     3411    auto dataDetectorTypes = static_cast<WebCore::DataDetectorTypes>(types);
     3412    for (auto frame = makeRefPtr(&m_page->mainFrame()); frame; frame = frame->tree().traverseNext()) {
     3413        auto document = makeRefPtr(frame->document());
     3414        if (!document)
     3415            continue;
     3416
     3417        RefPtr<Range> range = Range::create(*document, Position { document.get(), Position::PositionIsBeforeChildren }, Position { document.get(), Position::PositionIsAfterChildren });
     3418        frame->setDataDetectionResults(DataDetection::detectContentInRange(range, dataDetectorTypes, m_dataDetectionContext.get()));
     3419    }
     3420    reply({ m_page->mainFrame().dataDetectionResults() });
     3421}
     3422
     3423#endif // ENABLE(DATA_DETECTION)
    33953424
    33963425#if PLATFORM(COCOA)
  • trunk/Source/WebKit/WebProcess/WebPage/WebPage.h

    r238454 r238471  
    4949#include "UserData.h"
    5050#include "WebBackForwardListProxy.h"
     51#include "WebPageMessages.h"
    5152#include "WebURLSchemeHandler.h"
    5253#include "WebUserContentController.h"
     
    9394#if PLATFORM(IOS_FAMILY)
    9495#include "GestureTypes.h"
    95 #include "WebPageMessages.h"
    9696#include <WebCore/IntPointHash.h>
    9797#include <WebCore/ViewportConfiguration.h>
     
    106106#elif ENABLE(TOUCH_EVENTS)
    107107#include <WebCore/PlatformTouchEvent.h>
     108#endif
     109
     110#if ENABLE(DATA_DETECTION)
     111#include <WebCore/DataDetection.h>
    108112#endif
    109113
     
    993997#if ENABLE(DATA_DETECTION)
    994998    void setDataDetectionResults(NSArray *);
     999    void detectDataInAllFrames(uint64_t, Messages::WebPage::DetectDataInAllFrames::AsyncReply&&);
     1000    void removeDataDetectedLinks(Messages::WebPage::RemoveDataDetectedLinks::AsyncReply&&);
    9951001#endif
    9961002
  • trunk/Source/WebKit/WebProcess/WebPage/WebPage.messages.in

    r238438 r238471  
    194194#endif
    195195
     196#if ENABLE(DATA_DETECTION)
     197    DetectDataInAllFrames(uint64_t types) -> (struct WebKit::DataDetectionResult result) Async
     198    RemoveDataDetectedLinks() -> (struct WebKit::DataDetectionResult result) Async
     199#endif
     200
    196201#if PLATFORM(MAC)
    197202    PerformDictionaryLookupOfCurrentSelection()
  • trunk/Tools/ChangeLog

    r238467 r238471  
     12018-11-24  Wenson Hsieh  <wenson_hsieh@apple.com>
     2
     3        [Cocoa] Add WKWebView SPI to trigger and remove data detection
     4        https://bugs.webkit.org/show_bug.cgi?id=191918
     5        <rdar://problem/36185051>
     6
     7        Reviewed by Tim Horton.
     8
     9        Add an API test to exercise the new WebKit SPI.
     10
     11        * TestWebKitAPI/DataDetectorsCoreSPI.h: Added.
     12        * TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj:
     13        * TestWebKitAPI/Tests/WebKitCocoa/DataDetection.mm:
     14        (-[WKWebView synchronouslyDetectDataWithTypes:]):
     15        (-[WKWebView synchronouslyRemoveDataDetectedLinks]):
     16        (TEST):
     17        * TestWebKitAPI/Tests/WebKitCocoa/WKAttachmentTests.mm:
     18        (TestWebKitAPI::TEST):
     19        (-[TestWKWebView tagsInBody]): Deleted.
     20        (-[TestWKWebView expectElementTagsInOrder:]): Deleted.
     21        (-[TestWKWebView expectElementCount:tagName:]): Deleted.
     22        (-[TestWKWebView expectElementTag:toComeBefore:]): Deleted.
     23
     24        Rename this from `-expectElementCount:tagName:` to `-expectElementCount:querySelector:`.
     25
     26        * TestWebKitAPI/Tests/WebKitCocoa/data-detectors.html: Added.
     27
     28        Add a new test page containing some content that can be data detected.
     29
     30        * TestWebKitAPI/cocoa/TestWKWebView.h:
     31        * TestWebKitAPI/cocoa/TestWKWebView.mm:
     32        (-[WKWebView tagsInBody]):
     33        (-[WKWebView expectElementTagsInOrder:]):
     34        (-[WKWebView expectElementCount:querySelector:]):
     35        (-[WKWebView expectElementTag:toComeBefore:]):
     36
     37        Move some testing helper functions from WKAttachmentTests to a testing category on WKWebView. This allows us to
     38        use `-expectElementCount:querySelector:` in tests outside of WKAttachmentTests.
     39
     40        (-[WKWebView objectByEvaluatingJavaScript:]):
     41        (-[WKWebView objectByEvaluatingJavaScriptWithUserGesture:]):
     42        (-[WKWebView stringByEvaluatingJavaScript:]):
     43
     44        Move some common helper functions from TestWKWebView to a testing category on WKWebView.
     45
     46        (-[TestWKWebView objectByEvaluatingJavaScript:]): Deleted.
     47        (-[TestWKWebView objectByEvaluatingJavaScriptWithUserGesture:]): Deleted.
     48        (-[TestWKWebView stringByEvaluatingJavaScript:]): Deleted.
     49
    1502018-11-23  Sam Weinig  <sam@webkit.org>
    251
  • trunk/Tools/TestWebKitAPI/DataDetectorsCoreSPI.h

    r238470 r238471  
    11/*
    2  * Copyright (C) 2016 Apple Inc. All rights reserved.
     2 * Copyright (C) 2018 Apple Inc. All rights reserved.
    33 *
    44 * Redistribution and use in source and binary forms, with or without
     
    2424 */
    2525
    26 #ifndef DataDetectionResult_h
    27 #define DataDetectionResult_h
     26#pragma once
    2827
    2928#if ENABLE(DATA_DETECTION)
    3029
    31 #import "ArgumentCoders.h"
     30#import <pal/spi/cocoa/DataDetectorsCoreSPI.h>
    3231
    33 #import <wtf/RetainPtr.h>
     32#if !USE(APPLE_INTERNAL_SDK)
    3433
    35 namespace WebKit {
     34@interface DDScannerResult (Private)
     35@property (readonly, nonatomic) NSString *value;
     36@property (readonly, nonatomic) NSString *type;
     37@property (readonly, nonatomic) DDResultCategory category;
     38@end
    3639
    37 struct DataDetectionResult {
    38     RetainPtr<NSArray> results;
    39 
    40     void encode(IPC::Encoder&) const;
    41     static bool decode(IPC::Decoder&, DataDetectionResult&);
    42 };
    43 
    44 }
     40#endif // !USE(APPLE_INTERNAL_SDK)
    4541
    4642#endif // ENABLE(DATA_DETECTION)
    47 
    48 #endif // DataDetectionResult_h
  • trunk/Tools/TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj

    r238408 r238471  
    853853                F46A095B1ED8A6E600D4AA55 /* gif-and-file-input.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = F47D30ED1ED28A6C000482E1 /* gif-and-file-input.html */; };
    854854                F47728991E4AE3C1007ABF6A /* full-page-contenteditable.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = F47728981E4AE3AD007ABF6A /* full-page-contenteditable.html */; };
     855                F47DFB2621A878DF00021FB6 /* data-detectors.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = F47DFB2421A8704A00021FB6 /* data-detectors.html */; };
    855856                F4811E5921940BDE00A5E0FD /* WKWebViewEditActions.mm in Sources */ = {isa = PBXBuildFile; fileRef = F4811E5821940B4400A5E0FD /* WKWebViewEditActions.mm */; };
    856857                F4856CA31E649EA8009D7EE7 /* attachment-element.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = F4856CA21E6498A8009D7EE7 /* attachment-element.html */; };
     
    10201021                                F4AB578A1F65165400DB0DA1 /* custom-draggable-div.html in Copy Resources */,
    10211022                                290F4275172A221C00939FF0 /* custom-protocol-sync-xhr.html in Copy Resources */,
     1023                                F47DFB2621A878DF00021FB6 /* data-detectors.html in Copy Resources */,
    10221024                                F486B1D01F67952300F34BDD /* DataTransfer-setDragImage.html in Copy Resources */,
    10231025                                F457A9D6202D68AF00F7E9D5 /* DataTransfer.html in Copy Resources */,
     
    21482150                F47D30EB1ED28619000482E1 /* apple.gif */ = {isa = PBXFileReference; lastKnownFileType = image.gif; path = apple.gif; sourceTree = "<group>"; };
    21492151                F47D30ED1ED28A6C000482E1 /* gif-and-file-input.html */ = {isa = PBXFileReference; lastKnownFileType = text.html; path = "gif-and-file-input.html"; sourceTree = "<group>"; };
     2152                F47DFB2421A8704A00021FB6 /* data-detectors.html */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.html; path = "data-detectors.html"; sourceTree = "<group>"; };
     2153                F47DFB2721A885E700021FB6 /* DataDetectorsCoreSPI.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = DataDetectorsCoreSPI.h; sourceTree = "<group>"; };
    21502154                F4811E5821940B4400A5E0FD /* WKWebViewEditActions.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = WKWebViewEditActions.mm; sourceTree = "<group>"; };
    21512155                F4856CA21E6498A8009D7EE7 /* attachment-element.html */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.html; path = "attachment-element.html"; sourceTree = "<group>"; };
     
    23122316                                F4517B682054E0AC00C26721 /* ClassMethodSwizzler.h */,
    23132317                                F4517B692054E0AC00C26721 /* ClassMethodSwizzler.mm */,
     2318                                F47DFB2721A885E700021FB6 /* DataDetectorsCoreSPI.h */,
    23142319                                F46128B4211C861A00D9FADB /* DragAndDropSimulator.h */,
    23152320                                F44D06481F3962E3001A0E29 /* EditingTestHarness.h */,
     
    27412746                                9B62630B1F8C2510007EE29B /* copy-url.html */,
    27422747                                F4AB57891F65164B00DB0DA1 /* custom-draggable-div.html */,
     2748                                F47DFB2421A8704A00021FB6 /* data-detectors.html */,
    27432749                                F486B1CF1F6794FF00F34BDD /* DataTransfer-setDragImage.html */,
    27442750                                F457A9B3202D535300F7E9D5 /* DataTransfer.html */,
  • trunk/Tools/TestWebKitAPI/Tests/WebKitCocoa/DataDetection.mm

    r237266 r238471  
    2626#include "config.h"
    2727
     28#import "DataDetectorsCoreSPI.h"
    2829#import "PlatformUtilities.h"
    2930#import "Test.h"
    3031#import "TestNavigationDelegate.h"
     32#import "TestWKWebView.h"
    3133#import <WebKit/WebKit.h>
    3234#import <wtf/RetainPtr.h>
    3335
    3436#if WK_API_ENABLED && PLATFORM(IOS_FAMILY)
     37
     38@interface WKWebView (DataDetection)
     39- (void)synchronouslyDetectDataWithTypes:(WKDataDetectorTypes)types;
     40- (void)synchronouslyRemoveDataDetectedLinks;
     41@end
     42
     43@implementation WKWebView (DataDetection)
     44
     45- (void)synchronouslyDetectDataWithTypes:(WKDataDetectorTypes)types
     46{
     47    __block bool done = false;
     48    [self _detectDataWithTypes:types completionHandler:^{
     49        done = true;
     50    }];
     51    TestWebKitAPI::Util::run(&done);
     52}
     53
     54- (void)synchronouslyRemoveDataDetectedLinks
     55{
     56    __block bool done = false;
     57    [self _removeDataDetectedLinks:^{
     58        done = true;
     59    }];
     60    TestWebKitAPI::Util::run(&done);
     61}
     62
     63@end
    3564
    3665static bool ranScript;
     
    98127}
    99128
     129TEST(WebKit, AddAndRemoveDataDetectors)
     130{
     131    auto webView = adoptNS([[TestWKWebView alloc] initWithFrame:CGRectMake(0, 0, 320, 500)]);
     132    [webView synchronouslyLoadTestPageNamed:@"data-detectors"];
     133    [webView expectElementCount:0 querySelector:@"a[x-apple-data-detectors=true]"];
     134    EXPECT_EQ(0U, [webView _dataDetectionResults].count);
     135
     136    auto checkDataDetectionResults = [] (NSArray<DDScannerResult *> *results) {
     137        EXPECT_EQ(3U, results.count);
     138        EXPECT_EQ(DDResultCategoryUnknown, results[0].category);
     139        EXPECT_TRUE([results[0].value containsString:@"+1-234-567-8900"]);
     140        EXPECT_TRUE([results[0].value containsString:@"https://www.apple.com"]);
     141        EXPECT_TRUE([results[0].value containsString:@"2 Apple Park Way, Cupertino 95014"]);
     142        EXPECT_WK_STREQ("SignatureBlock", results[0].type);
     143        EXPECT_EQ(DDResultCategoryCalendarEvent, results[1].category);
     144        EXPECT_WK_STREQ("Date", results[1].type);
     145        EXPECT_WK_STREQ("December 21, 2021", results[1].value);
     146        EXPECT_EQ(DDResultCategoryMisc, results[2].category);
     147        EXPECT_WK_STREQ("FlightInformation", results[2].type);
     148        EXPECT_WK_STREQ("AC780", results[2].value);
     149    };
     150
     151    [webView synchronouslyDetectDataWithTypes:WKDataDetectorTypeAll];
     152    [webView expectElementCount:5 querySelector:@"a[x-apple-data-detectors=true]"];
     153    checkDataDetectionResults([webView _dataDetectionResults]);
     154
     155    [webView synchronouslyRemoveDataDetectedLinks];
     156    [webView expectElementCount:0 querySelector:@"a[x-apple-data-detectors=true]"];
     157    EXPECT_EQ(0U, [webView _dataDetectionResults].count);
     158
     159    [webView synchronouslyDetectDataWithTypes:WKDataDetectorTypeAddress | WKDataDetectorTypePhoneNumber];
     160    [webView expectElementCount:2 querySelector:@"a[x-apple-data-detectors=true]"];
     161    checkDataDetectionResults([webView _dataDetectionResults]);
     162}
     163
    100164#endif
  • trunk/Tools/TestWebKitAPI/Tests/WebKitCocoa/WKAttachmentTests.mm

    r238360 r238471  
    216216@implementation TestWKWebView (AttachmentTesting)
    217217
    218 - (NSArray<NSString *> *)tagsInBody
    219 {
    220     return [self objectByEvaluatingJavaScript:@"Array.from(document.body.getElementsByTagName('*')).map(e => e.tagName)"];
    221 }
    222 
    223 - (void)expectElementTagsInOrder:(NSArray<NSString *> *)tagNames
    224 {
    225     auto remainingTags = adoptNS([tagNames mutableCopy]);
    226     NSArray<NSString *> *tagsInBody = self.tagsInBody;
    227     for (NSString *tag in tagsInBody.reverseObjectEnumerator) {
    228         if ([tag isEqualToString:[remainingTags lastObject]])
    229             [remainingTags removeLastObject];
    230         if (![remainingTags count])
    231             break;
    232     }
    233     EXPECT_EQ([remainingTags count], 0U);
    234     if ([remainingTags count])
    235         NSLog(@"Expected to find ordered tags: %@ in: %@", tagNames, tagsInBody);
    236 }
    237 
    238 - (void)expectElementCount:(NSInteger)count tagName:(NSString *)tagName
    239 {
    240     NSString *script = [NSString stringWithFormat:@"document.querySelectorAll('%@').length", tagName];
    241     EXPECT_EQ(count, [self stringByEvaluatingJavaScript:script].integerValue);
    242 }
    243 
    244 - (void)expectElementTag:(NSString *)tagName toComeBefore:(NSString *)otherTagName
    245 {
    246     [self expectElementTagsInOrder:@[tagName, otherTagName]];
    247 }
    248 
    249218- (_WKAttachment *)synchronouslyInsertAttachmentWithFileWrapper:(NSFileWrapper *)fileWrapper contentType:(NSString *)contentType
    250219{
     
    832801
    833802    auto checkAttachmentConsistency = [webView, file, folder] (_WKAttachment *expectedFileAttachment, _WKAttachment *expectedFolderAttachment) {
    834         [webView expectElementCount:2 tagName:@"ATTACHMENT"];
     803        [webView expectElementCount:2 querySelector:@"ATTACHMENT"];
    835804        EXPECT_TRUE(UTTypeConformsTo((__bridge CFStringRef)[webView valueOfAttribute:@"type" forQuerySelector:@"attachment[title=folder]"], kUTTypeDirectory));
    836805        EXPECT_TRUE(UTTypeConformsTo((__bridge CFStringRef)[webView valueOfAttribute:@"type" forQuerySelector:@"attachment[title^=test]"], kUTTypeData));
     
    929898        [webView _synchronouslyExecuteEditCommand:@"DeleteBackward" argument:nil];
    930899        observer.expectAttachmentUpdates(@[ ], @[ ]);
    931         [webView expectElementCount:0 tagName:@"BR"];
     900        [webView expectElementCount:0 querySelector:@"BR"];
    932901    }
    933902}
     
    972941    [webView _synchronouslyExecuteEditCommand:@"InsertParagraph" argument:nil];
    973942    [webView expectElementTag:@"IMG" toComeBefore:@"STRONG"];
    974     [webView expectElementCount:1 tagName:@"IMG"];
     943    [webView expectElementCount:1 querySelector:@"IMG"];
    975944
    976945    // Drag the attachment element to somewhere below the strong text.
     
    978947
    979948    [webView expectElementTag:@"STRONG" toComeBefore:@"IMG"];
    980     [webView expectElementCount:1 tagName:@"IMG"];
     949    [webView expectElementCount:1 querySelector:@"IMG"];
    981950    EXPECT_EQ([simulator insertedAttachments].count, [simulator removedAttachments].count);
    982951
     
    10351004
    10361005    EXPECT_TRUE(zipAttachment && imageAttachment && pdfAttachment);
    1037     [webView expectElementCount:2 tagName:@"ATTACHMENT"];
    1038     [webView expectElementCount:1 tagName:@"IMG"];
     1006    [webView expectElementCount:2 querySelector:@"ATTACHMENT"];
     1007    [webView expectElementCount:1 querySelector:@"IMG"];
    10391008    EXPECT_WK_STREQ("application/pdf", [webView stringByEvaluatingJavaScript:@"document.querySelectorAll('attachment')[0].getAttribute('type')"]);
    10401009
     
    13391308    ObserveAttachmentUpdatesForScope observer(webView.get());
    13401309    [webView _synchronouslyExecuteEditCommand:@"Paste" argument:nil];
    1341     [webView expectElementCount:2 tagName:@"IMG"];
     1310    [webView expectElementCount:2 querySelector:@"IMG"];
    13421311
    13431312    for (_WKAttachment *attachment in observer.observer().inserted) {
     
    14741443    ObserveAttachmentUpdatesForScope observer(secondWebView.get());
    14751444    [secondWebView paste:nil];
    1476     [secondWebView expectElementCount:3 tagName:@"attachment"];
     1445    [secondWebView expectElementCount:3 querySelector:@"attachment"];
    14771446    EXPECT_EQ(3U, observer.observer().inserted.count);
    14781447
     
    15171486    }
    15181487
    1519     [webView expectElementCount:1 tagName:@"ATTACHMENT"];
    1520     [webView expectElementCount:1 tagName:@"IMG"];
     1488    [webView expectElementCount:1 querySelector:@"ATTACHMENT"];
     1489    [webView expectElementCount:1 querySelector:@"IMG"];
    15211490    EXPECT_WK_STREQ("application/pdf", [webView stringByEvaluatingJavaScript:@"document.querySelector('attachment').getAttribute('type')"]);
    15221491    EXPECT_WK_STREQ("test.pdf", [webView stringByEvaluatingJavaScript:@"document.querySelector('attachment').getAttribute('title')"]);
     
    15531522    [simulator runFrom:CGPointMake(0, 0) to:CGPointMake(50, 50)];
    15541523
    1555     [webView expectElementCount:1 tagName:@"ATTACHMENT"];
    1556     [webView expectElementCount:1 tagName:@"IMG"];
     1524    [webView expectElementCount:1 querySelector:@"ATTACHMENT"];
     1525    [webView expectElementCount:1 querySelector:@"IMG"];
    15571526    EXPECT_EQ(2U, [simulator insertedAttachments].count);
    15581527
     
    15741543    auto removedAttachments = retainPtr([simulator removedAttachments]);
    15751544    EXPECT_EQ(2U, [removedAttachments count]);
    1576     [webView expectElementCount:0 tagName:@"ATTACHMENT"];
    1577     [webView expectElementCount:0 tagName:@"IMG"];
     1545    [webView expectElementCount:0 querySelector:@"ATTACHMENT"];
     1546    [webView expectElementCount:0 querySelector:@"IMG"];
    15781547    EXPECT_TRUE([removedAttachments containsObject:[insertedAttachments firstObject]]);
    15791548    EXPECT_TRUE([removedAttachments containsObject:[insertedAttachments lastObject]]);
     
    16821651        EXPECT_GT([attachment info].data.length, 0U);
    16831652
    1684     [webView expectElementCount:2 tagName:@"ATTACHMENT"];
     1653    [webView expectElementCount:2 querySelector:@"ATTACHMENT"];
    16851654    EXPECT_WK_STREQ("hello.rtf", [webView stringByEvaluatingJavaScript:@"document.querySelectorAll('attachment')[0].getAttribute('title')"]);
    16861655    EXPECT_WK_STREQ("text/rtf", [webView stringByEvaluatingJavaScript:@"document.querySelectorAll('attachment')[0].getAttribute('type')"]);
     
    17071676    EXPECT_EQ(0U, [dragAndDropSimulator removedAttachments].count);
    17081677    [[dragAndDropSimulator insertedAttachments].firstObject expectRequestedDataToBe:data];
    1709     [webView expectElementCount:1 tagName:@"ATTACHMENT"];
     1678    [webView expectElementCount:1 querySelector:@"ATTACHMENT"];
    17101679    EXPECT_WK_STREQ("archive.zip", [webView valueOfAttribute:@"title" forQuerySelector:@"attachment"]);
    17111680    EXPECT_WK_STREQ("application/zip", [webView valueOfAttribute:@"type" forQuerySelector:@"attachment"]);
  • trunk/Tools/TestWebKitAPI/cocoa/TestWKWebView.h

    r238381 r238471  
    4949
    5050@interface WKWebView (TestWebKitAPI)
     51@property (nonatomic, readonly) NSArray<NSString *> *tagsInBody;
    5152- (BOOL)_synchronouslyExecuteEditCommand:(NSString *)command argument:(NSString *)argument;
     53- (void)expectElementTagsInOrder:(NSArray<NSString *> *)tagNames;
     54- (void)expectElementCount:(NSInteger)count querySelector:(NSString *)querySelector;
     55- (void)expectElementTag:(NSString *)tagName toComeBefore:(NSString *)otherTagName;
     56- (NSString *)stringByEvaluatingJavaScript:(NSString *)script;
     57- (id)objectByEvaluatingJavaScriptWithUserGesture:(NSString *)script;
     58- (id)objectByEvaluatingJavaScript:(NSString *)script;
    5259@end
    5360
     
    6572- (void)synchronouslyLoadHTMLString:(NSString *)html baseURL:(NSURL *)url;
    6673- (void)synchronouslyLoadTestPageNamed:(NSString *)pageName;
    67 - (id)objectByEvaluatingJavaScript:(NSString *)script;
    68 - (id)objectByEvaluatingJavaScriptWithUserGesture:(NSString *)script;
    69 - (NSString *)stringByEvaluatingJavaScript:(NSString *)script;
    7074- (void)waitForMessage:(NSString *)message;
    7175- (void)performAfterLoading:(dispatch_block_t)actions;
  • trunk/Tools/TestWebKitAPI/cocoa/TestWKWebView.mm

    r238381 r238471  
    7979}
    8080
     81- (NSArray<NSString *> *)tagsInBody
     82{
     83    return [self objectByEvaluatingJavaScript:@"Array.from(document.body.getElementsByTagName('*')).map(e => e.tagName)"];
     84}
     85
     86- (void)expectElementTagsInOrder:(NSArray<NSString *> *)tagNames
     87{
     88    auto remainingTags = adoptNS([tagNames mutableCopy]);
     89    NSArray<NSString *> *tagsInBody = self.tagsInBody;
     90    for (NSString *tag in tagsInBody.reverseObjectEnumerator) {
     91        if ([tag isEqualToString:[remainingTags lastObject]])
     92            [remainingTags removeLastObject];
     93        if (![remainingTags count])
     94            break;
     95    }
     96    EXPECT_EQ([remainingTags count], 0U);
     97    if ([remainingTags count])
     98        NSLog(@"Expected to find ordered tags: %@ in: %@", tagNames, tagsInBody);
     99}
     100
     101- (void)expectElementCount:(NSInteger)count querySelector:(NSString *)querySelector
     102{
     103    NSString *script = [NSString stringWithFormat:@"document.querySelectorAll('%@').length", querySelector];
     104    EXPECT_EQ(count, [self stringByEvaluatingJavaScript:script].integerValue);
     105}
     106
     107- (void)expectElementTag:(NSString *)tagName toComeBefore:(NSString *)otherTagName
     108{
     109    [self expectElementTagsInOrder:@[tagName, otherTagName]];
     110}
     111
     112- (id)objectByEvaluatingJavaScript:(NSString *)script
     113{
     114    bool isWaitingForJavaScript = false;
     115    RetainPtr<id> evalResult;
     116    [self _evaluateJavaScriptWithoutUserGesture:script completionHandler:[&] (id result, NSError *error) {
     117        evalResult = result;
     118        isWaitingForJavaScript = true;
     119        EXPECT_TRUE(!error);
     120        if (error)
     121            NSLog(@"Encountered error: %@ while evaluating script: %@", error, script);
     122    }];
     123    TestWebKitAPI::Util::run(&isWaitingForJavaScript);
     124    return evalResult.autorelease();
     125}
     126
     127- (id)objectByEvaluatingJavaScriptWithUserGesture:(NSString *)script
     128{
     129    bool isWaitingForJavaScript = false;
     130    RetainPtr<id> evalResult;
     131    [self evaluateJavaScript:script completionHandler:[&] (id result, NSError *error) {
     132        evalResult = result;
     133        isWaitingForJavaScript = true;
     134        EXPECT_TRUE(!error);
     135        if (error)
     136            NSLog(@"Encountered error: %@ while evaluating script: %@", error, script);
     137    }];
     138    TestWebKitAPI::Util::run(&isWaitingForJavaScript);
     139    return evalResult.autorelease();
     140}
     141
     142- (NSString *)stringByEvaluatingJavaScript:(NSString *)script
     143{
     144    return [NSString stringWithFormat:@"%@", [self objectByEvaluatingJavaScript:script]];
     145}
     146
    81147@end
    82148
     
    290356}
    291357
    292 - (id)objectByEvaluatingJavaScript:(NSString *)script
    293 {
    294     bool isWaitingForJavaScript = false;
    295     RetainPtr<id> evalResult;
    296     [self _evaluateJavaScriptWithoutUserGesture:script completionHandler:[&] (id result, NSError *error) {
    297         evalResult = result;
    298         isWaitingForJavaScript = true;
    299         EXPECT_TRUE(!error);
    300         if (error)
    301             NSLog(@"Encountered error: %@ while evaluating script: %@", error, script);
    302     }];
    303     TestWebKitAPI::Util::run(&isWaitingForJavaScript);
    304     return evalResult.autorelease();
    305 }
    306 
    307 - (id)objectByEvaluatingJavaScriptWithUserGesture:(NSString *)script
    308 {
    309     bool isWaitingForJavaScript = false;
    310     RetainPtr<id> evalResult;
    311     [self evaluateJavaScript:script completionHandler:[&] (id result, NSError *error) {
    312         evalResult = result;
    313         isWaitingForJavaScript = true;
    314         EXPECT_TRUE(!error);
    315         if (error)
    316             NSLog(@"Encountered error: %@ while evaluating script: %@", error, script);
    317     }];
    318     TestWebKitAPI::Util::run(&isWaitingForJavaScript);
    319     return evalResult.autorelease();
    320 }
    321 
    322 - (NSString *)stringByEvaluatingJavaScript:(NSString *)script
    323 {
    324     return [NSString stringWithFormat:@"%@", [self objectByEvaluatingJavaScript:script]];
    325 }
    326 
    327358- (void)waitForMessage:(NSString *)message
    328359{
Note: See TracChangeset for help on using the changeset viewer.