Using WebKit’s Remote Web Inspector for Embedded Webkit ports

I am sure every JavaScript developer is familiar with the “Inspect Element” feature in Chrome and Safari.  It is a very useful tool for debugging web applications.  On an embedded target, pulling up the web inspector is technically possible, but may not be practical with limited screen real estate or limited inputs. Luckily, WebKit.org has recently added support to make all this easier with the Remote Web Inspector.

The Remote Web Inspector allows you to open up the Inspector in your desktop browser (Chrome or Safari) and connect to your target platform.  Now you can use the luxuries of a desktop environment to debug your web application on the embedded target.

If you want to try it out launch Chrome Canary with the following Option:

chrome --remote-debugging-port=9222

then launch a second browser and navigate to http://localhost:9222

HOW IT WORKS

Here is how it works under the hood.  The inspector has 2 main components, the front-end and the backend client. The Front-end is simply a JavaScript webpage, which is the UI for this tool.

To view Front-end Source Code:
http://trac.webkit.org/browser/trunk/Source/WebCore/inspector/front-end

The inspector backend is the agent that interacts with WebKits engine.  The inspector frontend and backend communicate with each other via a Json formatted debug protocol.

In the case of the local inspector the backend calls for receiving and sending message to/from the  frontend are as follows:
Receive Message from Frontend:

InspectorController::dispatchMessageFromFrontend()

Send Message to Frontend:

InspectorClient:: doDispatchMessageOnFrontendPage(..)

For the Remote Web Inspector the JSON debug protocol messages are sent over a Web Socket.   To enable this, a new component was added called WebInspectorServer.  The WebInspectorServer is a mini webserver that is able to serve up the inspector frontend, establish a websocket connection for the debug JSON message communication and tie in to the Inspector backend.

The Web Inspector Server listens on a specified port (in the chrome example above port 9222 is used).  When you initiate the connection via the remote browser by navigating to landing page (ex. http://localhost:9222), the inspector backend returns a list of webviews (note of you have a single view implementation you could bypass this and load the inspector frontend directly).   When you load the Inspector Frontend, the front-end will establish a Web Socket connection. The Web Inspector server will notify the Inspector backend of the remote Frontend.

The send and receive functions for the Remote communication are as follows:

Receive Message from Frontend

WebInspectorProxy::dispatchMessageFromRemoteFrontend(const String& message)

Send Message to frontend.

 WebInspectorProxy::sendMessageToRemoteFrontend(const String& message)

 PORTING REMOTE INSPECTOR TO WEBKIT:

The only downside to the Remote Inspector is webkit.org only supports it on WebKit2.  So if your running WebKit, you will need to take the Inspector Server from WebKit2:

http://trac.webkit.org/browser/trunk/Source/WebKit2/UIProcess/InspectorServer

and put it in your WebKit directory.

The WebInpectorServer will need to be modified to replace WebInspectorProxy calls with InspectorClient calls.

 

Depending on the vintage of the port you may need to grab the changes to WebSockets to support the changes needed to support the WebInspectorServer.

FURTHER READING:

For more information on the Remote Inspector check out webkit.org blog post:

(http://www.webkit.org/blog/1875/announcing-remote-debugging-protocol-v1-0/)

Further information on web sockets:

http://www.websocket.org/