VKURLAction 0.0.1

VKURLAction 0.0.1

测试已测试
语言语言 Obj-CObjective C
许可证 MIT
发布最后发布2016年10月

Awhisper维护。



  • 作者:
  • Awhisper

整个代码包括

  • openURL模块 VKURLAction
  • URL解析模块 VKURLParser
  • 中间人模式设计 VKMediatorAction
  • runtime工具 VKMsgSend

因为是基于中间人模式,所以VKMediatorAction是整个代码的核心。VKMediatorAction的主代码并未实现什么核心内容,只是写了一个单例以备将来可能的功能扩展。从现有的代码角度来看,可以删除单例,全部写成类方法。

本地调用

VKMediatorAction的category是中间人的主要代码所在,使用category的方式可以在业务无限庞大的时候分拆代码便于管理。可以在demo工程中的VKMediatorAction+webVC.m的源码中查看

-(void)doAlertWebViewControllerWith:(NSString *)title withMainUrl:(NSString *)url
{
    Class cls = NSClassFromString(@"WebViewController");
    id vc = [[cls alloc]VKCallSelectorName:@"initWithTitle:url:" error:nil,title,url];
    [vc VKCallSelectorName:@"doAlertAction" error:nil];
}


-(id)getWebViewControllerWithTitle:(NSString *)title withMainUrl:(NSString *)url
{
    Class cls = NSClassFromString(@"WebViewController");
    id vc = [[cls alloc]VKCallSelectorName:@"initWithTitle:url:" error:nil,title,url];
    return vc;
}

可以看到所有的API设计都是native api,你可以设计任意的参数命名,任意的参数种类。

换句话说,如果想执行本地调用,只需要引入VKMediatorAction,然后调用你想要的api即可

- (IBAction)native1click:(id)sender {
    [[VKMediatorAction sharedInstance] doAlertWebViewControllerWith:@"webview" withMainUrl:@"http://awhisper.github.io"];
}
- (IBAction)native2click:(id)sender {
    UIViewController *vc = [[VKMediatorAction sharedInstance]getWebViewControllerWithTitle:@"webview" withMainUrl:@"http://awhisper.github.io"];
    [self.navigationController pushViewController:vc animated:YES];
}

需要注意的是,VKMediatorAction+webVC.m内的源码完全不import业务模块,因此需要使用runtime的方式去调用对应方法,而我的源码里有一个封装的VKMsgSend的工具,使用这个工具可以减少写runtime代码的成本。这个方法就是工具提供的,后续还会详细介绍。

远程调用

当你需要使用url的方式打开界面的时候,首先,你需要让中间人能够处理url传来的字典型参数,因此特意为上面的2个mediatoraction增加了处理字典参数的版本。可以看到,这个代码最初符合设计初衷,url的action最后还是会调用原来的native的action。

-(void)doAlertWebViewControllerWithURLParams:(NSDictionary *)params
{
    NSString *title = params[@"title"];
    NSString *url = params[@"url"];
    [self doAlertWebViewControllerWith:title withMainUrl:url];
}


-(id)getWebViewControllerWithURLParams:(NSDictionary *)params
{
    NSString *title = params[@"title"];
    NSString *url = params[@"url"];
    return [self getWebViewControllerWithTitle:title withMainUrl:url];
}

完成了Mediator对URL参数的支持,其实就已经可以直接使用VKURLAction了。

VKURLAction使用

在使用VKURLAction时,需要提前指定url的scheme和host,一旦指定了app的scheme和host,所有不匹配scheme与host的url都不会被识别。具体可以参考demo源码,源码很简单,这里不再赘述。

VKURLAction支持对URL加入sign校验,如果url开启了sign校验功能,所有url必须附带sign参数,并且符合签名校验规则,否则不会进行识别跳转。具体代码可看源码,这些都是细节,这里不再细说。

只要完成了Mediator对URL参数的支持,其实就已经可以直接使用VKURLAction。比如我们已经写好了getWebViewControllerWithURLParams:方法,那么我们可以直接把getWebViewControllerWithURLParams当做url的path,以scheme://host/path?params=aa&parms2=bb的形式来打开url,这样就会自动把url中的参数解析成字典,传入到Mediator的对应方法里。

//初始化URLAction
[VKURLAction setupScheme:@"demo" andHost:@"nativeOpenUrl"];
//写url
NSString * url =@"demo://nativeOpenUrl/getWebViewControllerWithURLParams?title=webView&url=http%3A%2F%2Fawhisper.github.io";
//openURL
[VKURLAction doActionWithUrlString:url];

更多使用方法请参考demo工程。

URL生成

如果对如何编写url不熟悉,VKURLAction提供了接口来自动生成接口,尤其是在开启了签名校验后,url的签名规则会比较复杂。如果想测试的话,可以使用相关接口自动生成url,避免手动编写出错。

url的参数必须经过url标准的encode,这一点,自动生成url工具已经实现,如果由其他方式生成url(如server下发等),请注意调试。

URL简写

把getWebViewControllerWithURLParams当做一个path名字拼接到url里面实在有点冗长,也不太好记,因此VKURLAction提供了方法来注册简写(注意这不是必须的,不写也能执行url)

//注册简写
[VKURLAction mapKeyword:@"openWeb" toActionName:@"getWebViewControllerWithURLParams"];
//url就可以这么写了
NSString * url =@"demo://nativeOpenUrl/openWeb?title=webView&url=http%3A%2F%2Fawhisper.github.io";

注册了简写之后,写url也清爽了不少,也减少了别人猜测我们app代码的问题。╮(╯_╰)╭

URLParser

整个VKURLAction都是依托在URLParser这个模块之上,它可以解析url,识别出url中的scheme,host,path和每个参数,拼接到字典中,验证签名的可靠性。具体代码见源码,这部分代码不是很复杂。