上课,上实验,写文档,终于有时间写博客了。
我觉得这学期的 Android
实验上的还是很有意义的,课上,与我的舍友张一帆(自学 Android
及相关框架,有过 Android
比赛项目经验)一起讨论了 Android
的架构分层设计,以及对 Retrofit
和 RxAndroid
框架的封装。
经过在实验中的学习,以及请教了一些在 Android
界算是有小有经验的人之后,发现自己年初对 Android
实验设计的有些问题:
年初计划使用 Data-Binding
与 Fragmentation
实现单 Activity
架构,后来发现这样并不好。
Data-Binding
学习成本太高,且对原项目结构破坏性较大,对新人学习并理解 Android
无益。 Activity
架构虽然很优秀,但实际项目中仍然是多 Activity
+多 Fragment
架构,去追求单 Activity
意义不大,手动管理 Fragment
会十分麻烦。 发现错误,就改吧。目前已经在实验中引入并应用了 ButterKnife
、 Litepal
、 Retrofit
、 RxAndroid
等框架,感觉技术上应该不会有太大变化。以后再一起和大家分享一下我在 Android
方面的学习收获。
同时,华软虚拟化管理系统 1.0
版本正式完成,本周花费整三天完成了项目发布及部署文档的撰写(感谢潘佳琦,为了尽快交付, MySQL
的安装与配置文档是他帮我写的,写得非常好)。
现在再回想华软项目,还是存在很多细节当时没有考虑到,在此进行反思与总结。
后台设计得没什么问题:当发生错误时,后台会抛出异常,全局异常处理处理掉该异常,并将错误信息返回给前台。
笨拙在前台的拦截器这里:
起初设计的是拦截器处理掉所有异常,并给予用户友好的提示,这样订阅时就不用处理 error
了。
当需要的时候,再去写 error
方法,比如登录时要在 error
里提示用户名或密码错误的提示信息。
拦截器处理异常,为了拦截器能准确地提示错误信息,所以扩展了 HTTP
状态码,对 512
等状态码扩展了新的含义。
switch (error.status) { case 401: if (this.router.url !== '/passport/login') { this.msg.error('用户认证发生错误'); // noinspection JSIgnoredPromiseFromCall this.router.navigateByUrl('/passport/login'); } break; case 403: this.msg.error('访问被拒绝, ' + error.error); break; case 404: this.msg.error('资源不存在, ' + error.error); break; case 502: this.msg.error('服务器网关错误,请联系系统管理员'); break; case 504: this.msg.error('服务器网关请求超时,请联系系统管理员'); break; case 512: this.msg.error('数据同步异常,' + error.error); break; case 513: this.msg.error('主机操作异常,' + error.error); break; case 514: this.msg.error('访问被拒绝异常,' + error.error); break; }
当时写完这个拦截器的时候心里还是挺爽的,心想,以后可再也不用管理 error
了,多省事。现在再看看这个拦截器,说不上来什么原因,就是感觉怪怪的。
因为拦截器中是一个通用的提示信息,所以就出现了有时候需要在拦截器里加提示,有时候需要在 error
里提示,不想拦截器提示信息。
后来反思了一下,自定义状态码应该是合理的,也就是后台返回 512
、 513
之类的,前台能直接通过状态码准确地判断当前后台到底哪错了。
但是这个拦截器这样写,就变成了,后台一个状态码对应一个提示信息,相当于我这个拦截器和后台抛出的异常绑定了,所以有时候虽然也是那个错,但是在这个界面提示出来就显得格格不入。
奇怪就奇怪在前台误解了自定义状态码的本质,自定义的状态码其实不是我后台有什么,前台就要拦截什么,新加一个状态码,就是为了前台可以更准确地提示信息,而不是一个 500
的 服务器错误
。
改正:以后拦截器只处理通用的状态码,如: 401
跳转到登录, 403
提示访问被拒绝。而一些涉及到具体业务的状态码,还是应该放到 onError
方法中处理。
Loading
这是上次开会的时候晨澍提出来的,友好起见,当网络请求的时候应该显示 Loading
的动画。
想起来 NG-ALAIN
其实是为我们封装好了的,只是没有启用。
其实自己实现原理也简单,就是装饰器模式:
对原生的 HttpClient
进行装饰一下,组合一个带 Loading
的 YunzhiHttpClient
。
以后 Service
请求就使用 YunzhiHttpClient
,发起时,将 Loading
置为 true
,数据回来的时候,将 Loading
置为 false
。
组件中如果想用怎么办呢?直接注 YunzhiHttpClient
,因为在同一个模块中是单例的,所以直接使用注入的 YunzhiHttpClient
的 Loading
来控制加载动画是否显示。
改正:使用此方式添加 Loading
动画。
@Entity public class HostGroup { ... // 和电脑多对多 @ManyToMany @JsonView({NoneJsonView.class, HostGroupJsonView.getAllGroups.class, HostGroupJsonView.getGroupById.class, UserJsonView.getCurrentLoginUser.class }) private List<Host> hostList = new ArrayList<>(); ... }
HostGroup
中有字段是 hostList
,存储计算机列表。
具体的场景忘了,好像是潘佳琦在写功能的时候,我给提了点思路,突然一想,如果这个计算机存的是个 Set
,那就不用这样费事了。
假设我们这样改:
private Set<Host> hostSet = new HashSet<>();
后台是简单了,前台表示很无辜。
List
和 Set
,都是 Json
里的 []
,前台绑定的都是 Array
,我不管你后台怎么存,但是请你改数据结构的时候不要牵连前台。
既然 List
和 Set
在前台看起来一样,那为什么不改成 hosts
呢?后台数据结构随便改,对前台无影响。
改正:以后再有新实体,字段名与数据结构分离。
HTTPS
使用 BASIC
认证方式进行登录,前台将用户名和密码进行 Base64
加密传给后台。
HTTP
请求,在网络传输过程中黑客可以直接拦截数据,并查看 header
, Base64
解密很容易。
既然大势所趋,那以后要求安全的项目还是使用 HTTPS
吧。
简单学习了一下, SpringBoot
配置 SSL
需要证书,证书可以买也可以自己生成。 既然能自己生成,为什么还要买呢? HTTPS
证书好像还挺贵呢?
无意间点开天猫的 cookie
,发现里面只认识 XSRF-TOKEN
,其他的都不知道。仔细想了一下,应该是天猫对安全的要求很高,不光是 HTTPS
保证数据传输的安全,更重要的是要保证发起请求的一定是客户本人,可能有好多算法的验证,保证用户不受损失。
想想我写的,用户的 token
如果被窃取了,谁访问都行。
看来在数据安全的道路上,我们还有很多路要走。
写华软部署文档的时候发现,写一个软件如何安装的教程真的是太困难了,并且如何再有项目,再写文档,还需要再写一遍。
可以直接建一个软件安装的文档仓库,再写部署文档,直接说我需要 mysql
,需要 nginx
。
直接在 adoc
中使用文件包含,将网上的这个 adoc
文件包含到我的文档中,就好像是自己写的一样,其实是外部引进来的。
Angular
架构
大家看图,这是我的前台设计思路。
多模块主要是在 NG-ALAIN
那里学习的,此架构设计适用于权限分配系统,因为采用 loadChildren
动态加载模块,也就是说,只有当用户访问 /student
这个路由时,才会加载学生管理 Module
,而不是不管有没有这个模块的权限,直接都交给浏览器去加载。
Core Module
,被学生管理等实际的业务 Module
引用,该模块引入外部第三方组件。
包含基础实体,即与后台对应的实体,拓展实体,实际项目中发现不仅需要基础实体,还需要根据组件要的数据结构自己构建实体并传过去。
基础组件、基础过滤器、 Service
,都放在这里,这样在业务组件里想用就用,很方便。
设计出来了,感觉付诸实践时应该还是有所困难,毕竟目前用的是 NG-ALAIN
现成的,以后需要自己搭。
Angular
最后为 Angular
点个赞,经过一个项目的洗礼,发现技术选型是正确的,选择 Angular
是多么的明智。
我们追随的一直是国外的脚步, VAR
三者,肯定不用 Vue
,毕竟 TypeScript
都不支持。
所以国外的主流技术一直是 Angular
和 React
,两者都支持 TypeScript
,只是在设计思想上有所不同。
Google
和 Facebook
都是互联网巨头,我们中国的互联网企业与之相比根据不算什么。(去年 Facebook
的股票跌了 6
个京东)
Angular
是框架,完善,直接把 Angular
一安装,什么网络请求,什么路由都有了,直接拿来用。
React
是库,小巧灵活,需要整合其他库才能开发应用,在 Facebook
改协议之前, React
当之无愧的前端第一框架。
Facebook
改了开源协议,就被 Apache
基金会封杀,同时国内全面弃用 React
,所以国内涌现了无数类 React
框架。
即在不修改原 React
项目的前提下,只修改依赖的框架,框架对外提供的 api
相同,即可实现无缝切换。
最优秀的类 React
框架要数京东的 Nerv
,性能非常好。京东主页采用该框架构建。
之前看到过经过前端的性能优化博客,采用自己设计的链表优化性能,现在也算是明白了面试官的真意。能当上面试官的,肯定都是通读开源项目源码或自己写框架级别的人物,人太多,基础的框架使用是个人学习学习官方文档都会,怎么筛选呢?然后面试官写框架的技术功底就用上了。
所以,你进不去阿里,不是你不够优秀,是你不适合写框架。
总有一天,我们也要写一款属于自己的框架。