How to Build a Unified Cross‑Platform Routing SDK for iOS Apps
This article explains the design and implementation of a unified routing SDK for iOS that enables page jumps, parameter passing, return values, interceptors, redirection, and cross‑technology integration (Native, Flutter, HTML5, Mini‑Programs) while remaining non‑intrusive to existing codebases.
1. Background
In front‑end web development, routing makes page navigation simple, but iOS lacks a native routing concept; traditionally a view controller must be instantiated and pushed via a navigation controller. To allow arbitrary page jumps from push notifications or UI elements, we launched the “BaiPing Unified Jump Routing” project.
Unified jump: using the SDK’s open() method to navigate to any page, supporting Native, Flutter, HTML5, WeChat Mini‑Program, system apps, and third‑party apps.
2. Problems Solved
2.1 Page Jump
Provide a target page route to the SDK, which then navigates directly without manual view controller creation.
2.2 Parameter Passing
Parameters can be attached to the target page for proper logic handling.
2.3 Return Values
Target pages can return data to the source when closed.
2.4 Back to Specific Route
Enable returning to a designated page in a navigation stack.
2.5 Unified Routing Rules
Basic ideas: one route per page, meaningful string routes, cross‑platform applicability, and binding routes to pages on each platform.
Scheme definitions : native, flutter, http/https, wxmp, tp, etc.
2.6 Cross‑Module API Calls
Allow modules to call each other without direct imports, avoiding circular dependencies.
2.7 Action Routing
Configure click actions that trigger non‑navigation behavior, e.g., invoking native share from an HTML5 page.
2.8 Route Interceptor
Provide authentication, parameter rewriting, breakpoints, and redirection.
2.9 Group Interceptor
Apply interceptor logic to a group of routes.
2.10 Route Redirection
Redirect old routes to new implementations without code changes.
2.11 Isolation Between Technology Stacks
Dispatch routes to the appropriate scheduler (Native, Flutter, HTML5, etc.).
3. Provided APIs
Key BBRouter API design:
NS_ASSUME_NONNULL_BEGIN
@interface BBRouter : NSObject<BBNativeRouter, BBBlockRouter>
@property (nonatomic, strong, class, readonly) BBRouterConfig *routerConfig;
+ (void)setUndefinedRouteHandle:(void(^)(BBRouterParameter *))undefinedRouteHandle;
+ (void)setWillOpenBlock:(void(^)(BBRouterParameter *))willOpenBlock;
+ (void)setDidOpenBlock:(void(^)(BBRouterParameter *))didOpenBlock;
+ (BOOL)registerRouterDispatcher:(id<BBRouterDispatcher>)dispatcher scheme:(NSString *)scheme;
+ (BOOL)registerTask:(NSString *)path action:(BBBlockDispatcherAction)action;
+ (BOOL)removeTask:(NSString *)path;
+ (void)routeWithRouterParameter:(BBRouterParameter *)parameter;
+ (BOOL)canOpen:(NSString *)url;
+ (void)open:(NSString *)url;
+ (void)open:(NSString *)url urlParams:(NSDictionary * _Nullable)urlParams;
+ (void)open:(NSString *)url urlParams:(NSDictionary * _Nullable)urlParams onPageFinished:(void(^ _Nullable)(NSDictionary *result))resultCallback;
+ (void)open:(NSString *)url urlParams:(NSDictionary * _Nullable)urlParams exts:(NSDictionary * _Nullable)exts onPageFinished:(void(^ _Nullable)(NSDictionary *result))resultCallback;
+ (BOOL)registerClass:(Class)cls withPath:(NSString *)path;
+ (BOOL)registerWithClassName:(NSString *)className andPath:(NSString *)path;
+ (BOOL)registerWithClassName:(NSString *)className andPath:(NSString *)path verifyBlock:(BOOL(^ _Nullable)(NSString *path, BBRouterParameter *routerParameter))verifyBlock;
+ (BOOL)removeRegisteredPath:(NSString *)path;
+ (id _Nullable)invokeTaskWithUrl:(NSString *)url urlParams:(NSDictionary *)urlParams;
+ (id _Nullable)invokeTaskWithUrl:(NSString *)url urlParams:(NSDictionary *)urlParams error:(NSError **)error;
+ (BOOL)addPath:(NSString *)path toGroup:(NSString *)group;
+ (void)addPaths:(NSArray<NSString *> *)paths toGroup:(NSString *)group;
+ (NSArray<NSString *> *)pathsInGroup:(NSString *)group;
+ (void)configGroup:(NSString *)group verifyBlock:(BOOL(^ _Nullable)(NSString *path, BBRouterParameter *routerParameter))verifyBlock;
+ (UIViewController * _Nullable)backwardCompletion:(void(^ _Nullable)(void))completion;
+ (UIViewController * _Nullable)backwardAnimated:(BOOL)animated completion:(void(^ _Nullable)(void))completion;
+ (void)backwardCount:(NSInteger)count completion:(void(^ _Nullable)(void))completion;
+ (void)openVC:(UIViewController *)vc routerParameter:(BBRouterParameter *)parameter;
+ (UIViewController * _Nullable)containsRouteObjectByPath:(NSString *)path;
+ (UIViewController * _Nullable)backwardVC:(UIViewController *)vc animatedBlock:(BOOL(^)(NSString *toppath))animatedBlock completion:(void(^ _Nullable)(void))completion;
@end
NS_ASSUME_NONNULL_END3.1 Register/Remove Dispatcher
Dispatchers isolate routing logic per domain.
3.2 Bind Routes to Pages
Register page‑to‑route mappings so the SDK can instantiate view controllers dynamically.
3.3 Open Route with Callback
Open a page and receive a result via a callback.
3.4 Back to Previous Page
Provide a method to return to the previous page.
3.5 Back to Specific Page
Allow popping to a designated page or N levels up.
3.6 Handle Undefined Routes
Redirect or prompt users when a route is not found.
4. Core Design and Specification
Adopt RESTful URI scheme: URI = scheme:[//authority]path[?query][#fragment] (see RFC3986).
Use scheme prefixes: native, flutter, http/https, wxmp, tp, etc.
4.1 High Extensibility
Abstract routing via schedulers to keep the system extensible.
4.2 Non‑Intrusive Integration
SDK works with existing codebases without requiring major changes.
4.3 Route Table Management
Centralized, versioned route tables with metadata (name, description, parameters, permissions).
4.4 Dynamic Route Table Distribution
Configuration center pushes updates to clients.
5. iOS Implementation
5.1 Compatibility with Native Development
Traditional iOS navigation steps (create VC, set properties, find navigation controller, push/present, callback) are encapsulated by the SDK.
RouterParameter class holds scheme, fullPath, query, fragment, style, url, addition, exts, response, and callback.
5.2 Architecture
6. Usage
6.1 Overall Flow
Initialize: load route table, register interceptors, register native routes, register non‑page routes, register group interceptors.
6.2 Page Routing
Register a view controller:
// Objective‑C view controller
BBRouter.register(withClassName: "MomentsViewController", andPath: BBRouterPaths.moments)
// Swift view controller (include module name)
BBRouter.register(withClassName: swiftClassFullName("MomentsViewController", "Community"), andPath: BBRouterPaths.moments)Navigate:
// No return value
[BBRouter open:BBRouterPaths.moments urlParams:@{@"momentId":@"11223344"}];
// With return value
[BBRouter open:BBRouterPaths.selectAlcohol urlParams:@{@"alcoholId":@"112233"} onPageFinished:^(NSDictionary *result) {
DEBUGLog(@"%@", result.r_data);
}];6.3 Method/Action Routing
// Register action
[BBRouter registerTask:@"action://xxx.com/yyy/zzz" action:^id _Nullable(BBRouterParameter *routerParameter) {
return routerParameter.addition;
}];
// Async call
[BBRouter open:@"action://xxx.com/yyy/zzz" urlParams:@{@"name":@"xiaoming"} onPageFinished:^(NSDictionary *result) {
DEBUGLog(@"%@", result);
}];
// Sync call
NSError *error = nil;
id result = [BBRouter invokeTaskWithUrl:@"action://xxx.com/yyy/zzz" urlParams:@{@"name":@"xiaoming"} error:&error];6.4 Interceptor Example
// Parameter normalization
BBRouter.register(withClassName: "XXXViewController", andPath: BBRouterPaths.xxx, verifyBlock: { path, routerParameter in
routerParameter.addition["ID"] = routerParameter.addition["id"]
return true
})6.5 Undefined Route Handling
BBRouter.setUndefinedRouteHandle { parameter in
let url = parameter.url
BBRouter.open(BBRouterPaths.routerNotFound, urlParams: ["url": url])
}Conclusion
The BaiPing Unified Jump Routing SDK makes cross‑platform page navigation a reality, supports visual page construction, and has driven componentization and modularization for over a year with near‑zero migration cost for iOS projects.
Signed-in readers can open the original source through BestHub's protected redirect.
This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactand we will review it promptly.
BaiPing Technology
Official account of the BaiPing app technology team. Dedicated to enhancing human productivity through technology. | DRINK FOR FUN!
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.
