How to use QWebEngineUrlRequestInterceptor

前端 未结 2 1874
时光说笑
时光说笑 2021-01-06 11:34

I need to intercept requests made in our WebEngine qml component in our Qt application.

I have found documentation on QWebEngineUrlRequestInterceptor which seems to

相关标签:
2条回答
  • 2021-01-06 11:53

    Managed to puzzle it together with the help of this post: https://forum.qt.io/topic/69135/how-to-send-network-requests-in-qwebengine/2

    This is my solution to hook up a QWebEngineUrlRequestInterceptor:

    .h file

    class WebUrlRequestInterceptor : public QWebEngineUrlRequestInterceptor
    {
        Q_OBJECT
    
    public:
        WebUrlRequestInterceptor(QObject *p = Q_NULLPTR);
        void interceptRequest(QWebEngineUrlRequestInfo &info);
    };
    

    .cpp file

    WebUrlRequestInterceptor::WebUrlRequestInterceptor(QObject *p)
      :QWebEngineUrlRequestInterceptor(p)
    {
    
    }
    void WebUrlRequestInterceptor::interceptRequest(QWebEngineUrlRequestInfo &info) {
        QString rsrct = "";
        switch(info.resourceType()){
            case 0:rsrct="ResourceTypeMainFrame = 0, // top level page";break;
            case 1:rsrct="ResourceTypeSubFrame, // frame or iframe";break;
            case 2:rsrct="ResourceTypeStylesheet, // a CSS stylesheet";break;
            case 3:rsrct="ResourceTypeScript, // an external script";break;
            case 4:rsrct="ResourceTypeImage, // an image (jpg/gif/png/etc)";break;
            case 5:rsrct="ResourceTypeFontResource, // a font";break;
            case 6:rsrct="ResourceTypeSubResource, // an other subresource.";break;
            case 7:rsrct="ResourceTypeObject, // an object (or embed) tag for a plugin,";break;
            case 8:rsrct="ResourceTypeMedia, // a media resource.";break;
            case 9:rsrct="ResourceTypeWorker, // the main resource of a dedicated worker.";break;
            case 10:rsrct="ResourceTypeSharedWorker, // the main resource of a shared worker.";break;
            case 11:rsrct="ResourceTypePrefetch, // an explicitly requested prefetch";break;
            case 12:rsrct="ResourceTypeFavicon, // a favicon";break;
            case 13:rsrct="ResourceTypeXhr, // a XMLHttpRequest";break;
            case 14:rsrct="ResourceTypePing, // a ping request for <a ping>";break;
            case 15:rsrct="ResourceTypeServiceWorker, // the main resource of a service worker.";break;
            case 16:rsrct="ResourceTypeUnknown";break;
    
            default : rsrct="Unknown type";break;
        }
    
      qDebug()<<"\t"<<Q_FUNC_INFO<<":\n\t\t" << "WebUrlRequestInterceptor::interceptRequest    " <<info.requestMethod()
             <<"\r\n  "<<info.requestUrl()<<"   "<<rsrct      <<"\r\n";
    
    }
    

    main.cpp file

    WebUrlRequestInterceptor *wuri = new WebUrlRequestInterceptor();
    QWebEngineProfile::defaultProfile()->setRequestInterceptor(wuri);
    
    0 讨论(0)
  • 2021-01-06 12:01

    The QWebEngineUrlRequestInterceptor class provides an abstract base class for URL interception, i recommend it to handle custom protocols, (mail://, example:// ....)

    Let's implement it by subclasing QWebEngineUrlRequestInterceptor:

    Your header file exampleurlschemehandler.h file:

    class ExampleUrlSchemeHandler : public QWebEngineUrlSchemeHandler
    {
        Q_OBJECT
    public:
        explicit ExampleUrlSchemeHandler(QObject *parent = 0);
    public:
    
        void requestStarted(QWebEngineUrlRequestJob *request);
    };
    

    Your cpp file:

    ExampleUrlSchemeHandler::ExampleUrlSchemeHandler(QObject *parent) : QWebEngineUrlSchemeHandler(parent){}
    
    void ExampleUrlSchemeHandler::requestStarted(QWebEngineUrlRequestJob *request){
        // Abort the request if you want to redirect it or something
        request->fail(QWebEngineUrlRequestJob::RequestAborted);
        // Get the URL
        const QUrl url = request->requestUrl();
        // Do amazing thing with your URL
        // .....
    }
    

    Now install it in your default QWebEngineProfile:

    const QString EXAMPLE_SCHEMA_HANDLER = "example://" /* http://, https://, mail:// ....   */;
    const QWebEngineUrlSchemeHandler* installed =  QWebEngineProfile::defaultProfile()->urlSchemeHandler(EXAMPLE_SCHEMA_HANDLER);
            if (!installed)
                profile()->installUrlSchemeHandler(EXAMPLE_SCHEMA_HANDLER, new WebAppUrlSchemeHandler(this));
    

    Other method, to handle HTTP/HTTPS request is subclassing QWebEnginePage, and reimplementing acceptNavigationRequest():

    bool WebAppPage::acceptNavigationRequest(const QUrl &url, QWebEnginePage::NavigationType type, bool main) {
        // Example: We want to redirect all links clicked by user to native webbrowser
            if (type == QWebEnginePage::NavigationTypeLinkClicked)
                    QDesktopServices::openUrl(url);
    }
    

    Now, set this page in your QWebEngineView.

    0 讨论(0)
提交回复
热议问题