In‑Depth Analysis and Implementation of JSBridge for Mobile Hybrid Development
This article provides a comprehensive overview of JSBridge, covering its origins, use cases, communication mechanisms, and detailed JavaScript‑side implementation with code examples for iOS and Android, helping developers understand and build robust hybrid mobile applications.
1 Introduction
Most developers first encounter JSBridge through WeChat's WeiXinJSBridge (now wrapped as JSSDK), which allows web pages to call native functions. JSBridge has existed long before mobile, appearing in desktop software for notifications, product details, and ads that use Web UI but trigger native actions. In the mobile era, hybrid apps and React‑Native rely heavily on JSBridge, as do WeChat Mini‑Programs.
2 Origin of JSBridge
The name "JSBridge" stems from JavaScript's dominance as the easiest, most maintainable, and most deployable UI technology. Web pages can be updated instantly without user intervention, making Web a low‑cost choice for hybrid development. JavaScript therefore naturally became the bridge between Web and native layers. PhoneGap (the predecessor of Cordova) was the first widely recognized JSBridge use case, and WeChat popularized it for sharing content.
JSBridge is applied in two main technical schemes:
Web‑based hybrid solutions such as the WeChat browser and company‑specific hybrid frameworks.
Non‑Web UI solutions whose business logic is JavaScript, e.g., React‑Native.
WeChat Mini‑Programs use a Web UI but isolate JavaScript for performance, placing them between the two categories.
3 Uses of JSBridge
JSBridge provides JavaScript with an interface to invoke native capabilities (location, camera, payment, etc.) and establishes a two‑way communication channel between native and non‑native code.
JavaScript → Native: send messages to call functions or notify native of state.
Native → JavaScript: return results, push messages, or notify JavaScript of native state.
4 Implementation Principles of JSBridge
JavaScript runs in an isolated JS context (e.g., WebKit, JSC). This isolation is analogous to RPC, where each call is a remote procedure invocation. The design therefore follows the typical RPC client‑server model.
4.1 Communication Principles
4.1.1 JavaScript Calls Native
4.1.1.1 Injected API
Injecting an API uses the WebView interface to add objects or methods to the JavaScript window, allowing direct native execution when called.
iOS UIWebView example:
JSContext *context = [uiWebView valueForKeyPath:@"documentView.webView.mainFrame.javaScriptContext"];
context[@"postBridgeMessage"] = ^(NSArray<NSArray *> *calls) {
// Native logic
};Front‑end call:
window.postBridgeMessage(message);iOS WKWebView example:
@interface WKWebVIewVC ()
@end
@implementation WKWebVIewVC
- (void)viewDidLoad {
[super viewDidLoad];
WKWebViewConfiguration *configuration = [[WKWebViewConfiguration alloc] init];
configuration.userContentController = [[WKUserContentController alloc] init];
WKUserContentController *userCC = configuration.userContentController;
// Inject object, native can capture calls
[userCC addScriptMessageHandler:self name:@"nativeBridge"];
WKWebView *wkWebView = [[WKWebView alloc] initWithFrame:self.view.frame configuration:configuration];
// TODO: display WebView
}
- (void)userContentController:(WKUserContentController *)userContentController didReceiveScriptMessage:(WKScriptMessage *)message {
if ([message.name isEqualToString:@"nativeBridge"]) {
NSLog(@"Front‑end data %@: ",message.body);
// Native logic
}
}
@endFront‑end call:
window.webkit.messageHandlers.nativeBridge.postMessage(message);4.1.1.2 Intercept URL Scheme
URL Scheme is a custom protocol (e.g., qunarhy://hy/url?url=... ) that the native side intercepts. The Web side typically uses an iframe.src request. This method suffers from URL length limits and higher latency, but historically supported iOS 6.
4.1.2 Native Calls JavaScript
Native simply evaluates a JavaScript string. The JavaScript function must be attached to the global window object.
iOS UIWebView:
result = [uiWebview stringByEvaluatingJavaScriptFromString:javaScriptString];iOS WKWebView:
[wkWebView evaluateJavaScript:javaScriptString completionHandler:completionHandler];Android pre‑KitKat:
webView.loadUrl("javascript:" + javaScriptString);Android KitKat and later:
webView.evaluateJavascript(javaScriptString, new ValueCallback
() {
@Override
public void onReceiveValue(String value) {
// handle result
}
});4.2 JSBridge Interface Implementation
The bridge provides two core functions: invoke (JavaScript → Native) and receiveMessage (Native → JavaScript). A simple implementation looks like:
window.JSBridge = {
// Call Native
invoke: function(msg) {
nativeBridge.postMessage(msg);
},
// Receive from Native
receiveMessage: function(msg) {
// handle msg
}
};To support callbacks, a unique callbackId is generated and stored on the JavaScript side. Native returns the same callbackId so the original callback can be executed.
(function () {
var id = 0,
callbacks = {};
window.JSBridge = {
invoke: function (bridgeName, callback, data) {
var thisId = id++;
callbacks[thisId] = callback;
nativeBridge.postMessage({
bridgeName: bridgeName,
data: data || {},
callbackId: thisId
});
},
receiveMessage: function (msg) {
var bridgeName = msg.bridgeName,
data = msg.data || {},
callbackId = msg.callbackId;
if (callbackId && callbacks[callbackId]) {
callbacks[callbackId](msg.data);
} else if (bridgeName) {
// handle bridgeName logic
}
},
register: function (bridgeName, callback) {
if (!registerFuncs[bridgeName]) {
registerFuncs[bridgeName] = [];
}
registerFuncs[bridgeName].push(callback);
}
};
})();The full example (omitting some details) combines the above ideas into a more complete bridge that also supports native‑to‑JavaScript callbacks.
5 How to Include JSBridge
5.1 Injection from Native
Native injects the entire bridge script into the WebView. This ensures version consistency but requires retry logic if injection fails.
5.2 Reference from JavaScript
JavaScript loads the bridge script itself, guaranteeing its presence before calls, but the bridge must remain compatible with multiple native versions.
6 Summary
This article dissected the principles of communication between JavaScript and native code, presented a JavaScript‑side implementation of JSBridge, discussed reference strategies, and supplied illustrative code snippets to help developers build reliable hybrid mobile applications.
Qunar Tech Salon
Qunar Tech Salon is a learning and exchange platform for Qunar engineers and industry peers. We share cutting-edge technology trends and topics, providing a free platform for mid-to-senior technical professionals to exchange and learn.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.