ios源生开发中,怎么衡量ios业务组件化开发设计

iOS关于模块化开发解决方案(纯干货)
招聘信息:
关于iOS模块化开发解决方案网上也有一些介绍,但真正落实在在具体的实例却很少看到,计划编写系统文章来介绍关于我对模块化解决方案的理解,里面会有包含到一些关于解耦、路由、封装、私有Pod管理等内容;并编写的一个实例项目放在git进行开源[],里面现在已经放着一些封装的功能模块;会不断的进行更新,假如你感兴趣可以Star一下,项目也不断的更新完善优化;如果你有更好的方案或者说好的建议可以lssues,我会在短时间进行更新并修改相应的问题;一:项目中存在的问题1:当公司里面有多个项目同时进行,并且有可能是多个人分别不同项目时,就会存在如上图出现的情况,其实每个APP中都是有很多共同的模块,当然有可能你会把相同功能模块代码复制一份在新项目中,但这其实并不是最好的方式,在后期不断迭代过程中,不同的人会往里面增加很多带有个人色彩的代码;这样就像相同的模块项目后期对于多个项目统一管理也是灾难性,有可能会失控,哪怕项目转移别人接手也会无形中浪费很多时间,增加维护成本,所以实例中更注重对于一些相同模块进行提取,求同存异;而模块化结合私有Pods进行管理,对于常用功能的封装,只要开放出一些简单开关配置方式,就可以实现一个功能,比如日志记录、网络请求模块、网络状态变化提示等;2:对于页面之间相互耦合,而页面之间的传参也各不相同,由于不同的开发人员或者简便方式等原因,传参的类型都有差异,包含如实体、简单基本类型等,先前项目对于路由方式也不支持,导致要实现收到消息推送进行不同的页面跳转存在硬编码情况,对于功能扩展存在相当大的问题;而右边则是模块化后页面之间的交互方式;页面之间也不存在耦合关系,都只跟JiaMediator这个中介者相依赖;而传参都统一成以字典的形式;虽然可能牺牲一些方便跟随意,却可以解耦模块化;并且加入对路由方式的处理;约定好相关的协议进行交互;用这种路由方式代替那些第三方的路由插件则是因为它的灵活性,最主要还是省去了第三方路由插件在启动时要注册路由的问题;二:解决方案实现之模块化1:JiaCore(基础功能封装)JiaCore是整个APP最基础模块,所有的模块化都要依赖,主要包含一些全局的功能模块,比如JiaBaseViewController、JiaAppDelegate等;目前已经把一些默认的功能进行集成在里面,包含网络状态变化判断及提示、日志记录功能等;并把一些相关配置的内容用JiaCoreConfigManager这个管理类进行统一设置,比如是否打开日志记录功能;JiaCoreConfigManager类则是开放给具体APP设置全局的相关配置;下面就以其中一个日志记录功能进行讲解://JiaCore基础模块相关配置
JiaCoreConfigManager&*jiaCoreConfig=[JiaCoreConfigManager&sharedInstance];
jiaCoreConfig.recordlogger=YES;然后具体APP的PrefixHeader.pch引入命名空间并进行设置记录日志的等级:#import&"JiaCocoaLumberjack.h"
//DDLog等级
static&const&int&ddLogLevel&=&DDLogLevelV这样就完成的一个APP对于日志记录模块的引入,JiaCore已经帮你完成的关于日志记录的相关配置,并且错误内容以一种可读性较好的格式记录到file文件中,而且这些file文件生成规则也都定义好了,当然如何时你要是在Xcode控制台显示不同等级色彩,只要安装XcodeColors插件并简单进行设置就可以了,对于不同等级不同色彩都已经在JiaCore配置完成;2:JSPatch热更新功能在JiaCore里面也默认集成了热更新的功能,只要传入简单的对象数组就会启动热更新;其中JiaPathchModel已经是定义好的模型,在APP中把接口请求转化成模型数组,其中patchId是唯一值名称、md5则是JS文件的MD5值、url是JS的下载路径、ver则是对哪个版本起作用;因为一般我们在外面的APP都是多版本共存,热更新也要进行版本区分,只下载与本版本相对应的热更新JS文件加载;而MD5值则是为了增加安全性,避免JS文件被别人进行修改而影响APP的运行,在JiaCore会对下载后的JS文件进行MD5计算并比较;对于没有在jSPatchMutableArray以前的JS文件会被删除;//热更新内容
JiaPathchModel&*sample=[[JiaPathchModel&alloc]init];
sample.patchId&=&@"patchId_sample1";
sample.md5&=&@"2cf1c6f6cbf42c698706b";
sample.url&=&@"http://test.qshmall.net:9090/demo1.js";
sample.ver&=&@"1";
JiaPathchModel&*sample1=[[JiaPathchModel&alloc]init];
sample1.patchId&=&@"patchId_sample2";
sample1.md5&=&@"e8a4eaeadce5ae09c75fd";
sample1.url&=&@"http://test.qshmall.net:9090/demo2.js";
sample1.ver&=&@"1";
//JiaCore基础模块相关配置
JiaCoreConfigManager&*jiaCoreConfig=[JiaCoreConfigManager&sharedInstance];
jiaCoreConfig.jSPatchMutableArray=[@[sample,sample1]&mutableCopy];3:JiaGT模块(个推封装)消息推送对于一个APP是相当重要性,一般是采用第三方的SDK进行集成,其实大部分的SDK处理代码都是差不多,在这实例中对差异化的内容进行提取,实例中将以个推进行模块化,因为消息推送的大部分代码都集中在AppDelegate中,造成的一大堆杂乱代码,当然也有一部分人对AppDelegate进行扩展分类进行移除代码,实例中将采用另外一种解决方案进行抽取,可以达到完全解耦,在具体的APP里面将不会再出现个推SDK相关内容,只要简单进行配置跟处理消息就可以,下面只是简单的列出部分代码,其它封装代码见源代码;//设置个推模块的配置
jiaGTConfigManager&*gtConfig=[jiaGTConfigManager&sharedInstance];
gtConfig.jiaGTAppId=@"0uuwznWonIANoK07JeRWgAs";
gtConfig.jiaGTAppKey=@"26LeO4stbrA7TeyMUJdXlx3";
gtConfig.jiaGTAppSecret=@"2282vl0IwZd9KL3ZpDyoUL7";#pragma&mark&消息推送相关处理
&*&&@author&wujunyang,&16-07-07&16:07:25
&*&&@brief&&处理个推消息
&*&&@param&NotificationMessage
-(void)gtNotification:(NSDictionary&*)NotificationMessage
&&&&NSLog(@"%@",NotificationMessage[@"payload"]);
&&&&NSLog(@"-----接收到个推通知------");
&*&&@author&wujunyang,&16-07-07&16:07:40
&*&&@brief&&处理远程苹果通知
&*&&@param&RemoteNotificationMessage
-(void)receiveRemoteNotification:(NSDictionary&*)RemoteNotificationMessage
&&&&NSLog(@"%@",RemoteNotificationMessage[@"message"]);
&&&&NSLog(@"-----接收到苹果通知------");
&*&&@author&wujunyang,&16-09-21&14:09:33
&*&&@brief&获得注册成功时的deviceToken&可以在里面做一些绑定操作
&*&&@param&deviceToken&
-(void)receiveDeviceToken:(NSString&*)deviceToken
&&&&NSLog(@"-----当前deviceToken:%@------",deviceToken);
}4:JiaAnalytics模块(友盟统计封装)JiaAnalytics模块是在友盟统计SDK跟Aspect相结合基础上完成,对于页面的进出统计采用Aop切面方式进行,把原本应该在每个页面生命周期的统计代码移除,App运用只要简单配置友盟相对应的信息,也可以设置要统计页面的过滤条件,目前已经有三种如要统计的开头页面的前缀字符串数组、要统计的页面名称字符串数组、不统计的页面名称字符串数组;可以结合使用,达到精确统计页面的目的;而且把统计的代码放在异步线程进行,不会影响主线程的响应;__weak&typeof(self)&ws&=&
&&&&dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT,&0),&^{
&&&&&&&&[UIViewController&aspect_hookSelector:@selector(viewWillAppear:)&withOptions:AspectPositionAfter&usingBlock:^(id&info,&BOOL&animated){
&&&&&&&&&&&&UIViewController&*controller&=&[info&instance];
&&&&&&&&&&&&BOOL&filterResult=[ws&fileterWithControllerName:NSStringFromClass([controller&class])];
&&&&&&&&&&&&if&(filterResult)&{
&&&&&&&&&&&&&&&&[ws&beginLogPageView:[controller&class]];
&&&&&&&&&&&&}
&&&&&&&&}&error:NULL];
&&&&&&&&[UIViewController&aspect_hookSelector:@selector(viewWillDisappear:)&withOptions:AspectPositionAfter&usingBlock:^(id&info,&BOOL&animated){
&&&&&&&&&&&&UIViewController&*controller&=&[info&instance];
&&&&&&&&&&&&BOOL&filterResult=[ws&fileterWithControllerName:NSStringFromClass([controller&class])];
&&&&&&&&&&&&if&(filterResult)&{
&&&&&&&&&&&&&&&&[ws&endLogPageView:[controller&class]];
&&&&&&&&&&&&}
&&&&&&&&}&error:NULL];
&&&&});三:解决方案实现之页面解耦JiaMediator起到一个中介的作用,所有的模块间响应交互都是通过它进行,每个模块都会对它进行扩展分类(例如:JiaMediator+模块A),分类主要是为了用于本地间调用而又不想用路由的方式,若要用路由的方式则要注意关于路由约束准确编写,它将会直接影响到能否正确响应到目标;实例中也有关于使用通知的方式进行回调参数的回传问题;这部发页面解耦也是参照网络上大部分的实现方式,并对它进行修改;基本上满足我们平时开发的要求;里面还有一些优化的代码,可以查看源代码;NSDictionary&*curParams=@{kDesignerModuleActionsDictionaryKeyName:@"wujunyang",kDesignerModuleActionsDictionaryKeyID:@"1001",kDesignerModuleActionsDictionaryKeyImage:@"designerImage"};
&&&&switch&(indexPath.row)&{
&&&&&&&&case&0:
&&&&&&&&&&&&UIViewController&*viewController=[[JiaMediator&sharedInstance]JiaMediator_Designer_viewControllerForDetail:curParams];
&&&&&&&&&&&&[self&presentViewController:viewController&animated:YES&completion:nil];
&&&&&&&&&&&&
&&&&&&&&case&1:
&&&&&&&&&&&&UIViewController&*viewController=[[JiaMediator&sharedInstance]JiaMediator_Designer_viewControllerForDetail:curParams];
&&&&&&&&&&&&[self.navigationController&pushViewController:viewController&animated:YES];
&&&&&&&&&&&&
&&&&&&&&case&2:
&&&&&&&&&&&&NSString&*curRoue=@"jiaScheme://Designer/nativeFetchDetailViewController?name=wujunyang&ID=1001&image=designerImage";
&&&&&&&&&&&&UIViewController&*viewController=[[JiaMediator&sharedInstance]performActionWithUrl:[NSURL&URLWithString:curRoue]&completion:^(NSDictionary&*info)&{
&&&&&&&&&&&&&&&&
&&&&&&&&&&&&}];
&&&&&&&&&&&&[self.navigationController&pushViewController:viewController&animated:YES];
&&&&&&&&&&&&
&&&&&&&&case&3:
&&&&&&&&&&&&NSDictionary&*userParaDictionary=@{kUserModuleActionsDictionaryKeyID:@"1"};
&&&&&&&&&&&&UIViewController&*viewController=[[JiaMediator&sharedInstance]&JiaMediator_User_viewControllerForDetail:userParaDictionary];
&&&&&&&&&&&&[self.navigationController&pushViewController:viewController&animated:YES];
&&&&&&&&&&&&
&&&&&&&&default:
&&&&&&&&&&&&
&&&&}四:模块化结合私有Pods方案实例中只是把相关模块化的提取都在一个工程进行体现,最后还是要落实结合Pods进行管理,把每个模块分开管理,不同的APP可以简单通过Pods指令就可以达到引入模块的效果,对于一些相同模块可以在不同的APP重复引用,减小重复开发成本;项目中已经引入的Pod来管理目前开发的几个模块,并导入在我目前的Github的一个库里Spec进行统一管理,首先要引入Pod来管理则要增加jiaModule.podspec文件;Pod::Spec.new&do&|s|
s.name&&&&&&&&&=&"jiaModule"
s.version&&&&&&=&"0.0.6"
s.summary&&&&&&=&"iOS模块化功能的引用"
s.homepage&&&&&=&"/wujunyang/jiaModuleDemo"
s.license&&&&&&=&{&:type&=>&"MIT",&:file&=>&"FILE_LICENSE"&}
s.author&&&&&&&&&&&&&=&{&"wujunyang"&=>&""&}
s.platform&&&&&=&:ios,&"7.0"
s.source&&&&&&&=&{&:git&=>&"/wujunyang/jiaModuleDemo.git",&:tag&=>&"0.0.6"&}
s.requires_arc&=&true
s.subspec&'JiaCore'&do&|jiaCore|
jiaCore.source_files&=&'jiaModuleDemo/BaseModule/JiaCore/**/*.{h,m}'
jiaCore.dependency&'XAspect'
jiaCore.dependency&'YYCache'
jiaCore.dependency&'JSPatch'
jiaCore.dependency&'RealReachability'
jiaCore.dependency&'FLEX',&'~>&2.0'
jiaCore.dependency&'CocoaLumberjack',&'~>&2.0.0-rc'
jiaCore.dependency&'AFNetworking',&'~>2.6.0'
s.subspec&'JiaGT'&do&|jiaGT|
jiaGT.source_files&=&'jiaModuleDemo/BaseModule/JiaGT/**/*'
jiaGT.dependency&'jiaModule/JiaCore'
jiaGT.dependency&'XAspect'
jiaGT.dependency&'GTSDK',&'~>&1.5.0'
s.subspec&'JiaAnalytics'&do&|jiaAnalytics|
jiaAnalytics.source_files&=&'jiaModuleDemo/BaseModule/JiaAnalytics/**/*'
jiaAnalytics.dependency&'jiaModule/JiaCore'
jiaAnalytics.dependency&'XAspect'
jiaAnalytics.dependency&'Aspects'
jiaAnalytics.dependency&'UMengAnalytics-NO-IDFA',&'~>&4.1.1'
s.frameworks&=&'UIKit'
#&s.xcconfig&=&{&"HEADER_SEARCH_PATHS"&=>&"$(SDKROOT)/usr/include/libxml2"&}
#&s.dependency&"JSONKit",&"~>&1.4"
end关于项目源代码是把模块化直接落实在代码层面上,所以你可以直接下载运行,可以了解其中的实现方式,因为还有很多关于实现的细节没有在这里面详细讲解,当然要是大家有兴趣我将另起文章进行讲解;当然要是有帮助一定记得给上Star,会不断完善优化;
微信扫一扫
订阅每日移动开发及APP推广热点资讯公众号:CocoaChina
您还没有登录!请或
点击量10298点击量9771点击量7229点击量6382点击量5839点击量5174点击量4957点击量3727点击量3521
&2016 Chukong Technologies,Inc.
京公网安备89IOS组件化开发架构设计 - 简书
IOS组件化开发架构设计
目前公司的APP是一个面向特定业务群体的产品化应用,可针对不同的客户需求和具体业务差异性进行适当的功能调整和裁剪,是一个以核心业务为主,同时具有多样性的产品。产品的开发按照多版本迭代、逐次分发的方式进行,如何能够更好的适用客户的需求,同时降低我们的版本迭代的工作量,是我们在构建系统之处初要重点解决的问题。
引入业务的组件化封装,使得我们可以像搭积木一样动态的构建我们的产品,降低整体的迭代和升级频次,满足客户个性化需求。业务组件的目的是以方便业务组件独立升级和减少不必要的组件之间的交互为基本原则,通过一定程度的分离,实现软件重用(Software Reuse)。
组件的定义和划分
核心业务组件:是包含在APP内部,随APP发布出去的业务核心。
扩展业务组件:是对部分业务单独封装的组件库,由App负责对其进行管理和运行,可以和App进行交互最大程度的数据共享。通过APP加载启动,不能单独运行。
扩展业务APP:本身并不属于组件范畴包含完整的业务处理,是一个可单独发布、运行的APP。它做为我们核心业务的补充和扩充产生而来,也可以通过主APP对其进行管理和数据共享。扩展业务APP可以是来自面向企业分发或者是来源于AppStore的产品,可以通过主业务APP进行下载和启动。
业务组件内部可能还存在大量的技术组件,技术组件之间也可能是一种紧耦合的关系,这些都无关紧要,重要的就是抽象出业务组件和业务组件的服务后,屏蔽掉内部技术组件之间交互的复杂度。
层次划分是为了进一步的组件化为了能实现最大程度的实现共通化和产品复用度,将基础服务层、基础业务层和基础模块层抽离出来进行组件化,复用到每个子业务系统和模块库中。
组件的管理
组件管理模块的主要职责负责扩展业务组件和扩展业务APP的基本管理,组件的下载、升级、加载、启动和APP的下载、升级、启动。
基于IOS 我们的业务组件方案主要有以下 2 种:
Html5的方式大家都懂不做介绍。
使用framework 的方式来更新可以不依赖第三方库,使用原生的 OC/Swift 来开发,体验更好,开发成本也更低。将APP中的某个模块(比如一个 tab)的内容独立成一个 framework 的形式动态加载在 APP的 main bundle 中。当 app启动后通过组件管理模块从服务器上下载新版本的 framework 并加载即可达到动态更新的目的 。
关于动态的使用的基本事项
创建与编译具体操作参见 。
加载和启动目录下寻找更新后的framework。利用 OC 的动态特性 NSClassFromString 进行加载通过performSelector 执行加载 framework的类的具体方法
资源共享在storyboard/xib 中可以直接访问图片。使用代码方式访问的图片不可以放在xcassets 中,需要单独创建专属的Bundle。
基于组件化业务基础平台和传统的业务基础平台主要的差异在于组件化业务基础平台具有更多的灵活性、可扩展性,能够更加方便的进行组件升级和组件维护。特别是对于大型的行业APP来说,易于升级、易于维护,能够灵活的扩展成为评测一个业务基础平台的一个重要标准,随着业务的不断发展,很多行业APP软件包的尺寸已经达到几十M,如何对如此庞大规模的代码进行维护、升级成为软件开发者和运维管理者日益关注的一个课题,代码关系复杂、系统启动慢成为一个大型APP所面临的一个主要矛盾。
组件化业务基础平台主要用于解决简化开发,快速系统维护的问题。业务的组件化,并不是所有的内容全部组件化,有些内容是无法分离出去的。因此首先要确定APP业务的基本定位,业务定位中核心业务保留在APP中可以根据技术特征选择性组建化,保证核心业务和每一个业务组件紧密相关性。
高级项目经理 移动医疗产品开发负责人用 Sketch 做 iOS 设计时,一般选用哪个尺寸? - 知乎636被浏览49427分享邀请回答1610 条评论分享收藏感谢收起11449 条评论分享收藏感谢收起更多

我要回帖

更多关于 ios 组件化开发 pod 的文章

 

随机推荐