目录:
App项目实战之路(一):概述篇
App项目实战之路(二):API篇
App项目实战之路(三):原型篇
App项目实战之路(四):UI篇
App项目实战之路(五):服务端篇
App项目实战之路(六):数据库篇
这个系列文章主要是讲服务端的设计和实现, 对这部分的知识有个概念性的理解即可.
http://keeganlee.me/post/practice/20160807
App项目实战之路(一):概述篇
这章讲的是app的功能需求.
类似微博的程序员社交app.
http://keeganlee.me/post/practice/20160812
App项目实战之路(二):API篇
假如现在要定义登录、退出登录、注册、查询用户资料的接口,那么,可以这样定义:
接口 方法 Endpoint
登录 POST /user/login
退出登录 POST /user/logout
注册 POST /user/register
查询用户资料 GET /user/queryInfo
这种最传统普遍定义的API就是所谓的RPC方式.
最直接的区别就是:RPC抽象的是过程,REST抽象的是资源。过程是以动词为核心,而资源是以名词为核心。也可以简单类比为:RPC是面向过程的,REST是面向对象的。
给我的感觉就是:好混乱!这种大部分都是在对REST有过很初浅的了解,但却缺少正确理解的情况下做出的设计。或者是对于部分接口不知道该如何抽象为资源,所以就直接用RPC方式去定义了。
其实,使用REST风格设计API,我觉得难点就在于如何抽象资源。使用RPC则相对容易很多。这时,也许有人就会提出疑问了。既然使用RPC比用REST更容易抽象出接口,那为何还要用REST呢?要解答这个疑问,可以从面向过程和面向对象的角度去思考。我们知道,面向过程的思考方式处理问题更直接简单,那为什么我们还要使用面向对象呢?至于这个问题的答案,我就不再展开了。
其实这点我也不理解, 现在暂时勉强浅显的理解吧.
一个定义良好的URI,应该具有可读性,即从URI本身即可知道它所代表的资源。
接着,就需要对每个资源定义操作的方法了。我倾向于使用以下四个方法
POST 创建新资源
GET 查询资源
PUT 修改资源
DELETE 删除资源
不过,并不是所有资源都会开放这四个方法。例如,对/post是不开放PUT和DELETE方法的。对于以上资源,具体需要定义哪些方法,这里就不再列出来了。
最终以RestFul定义出来的API是这样的:
Endpoint 资源
/users 用户
/users/{user_id} 某用户
/users/{user_id}/posts 某用户发布的内容
/users/{user_id}/following 某用户关注的人
/users/{user_id}/followers 某用户的粉丝
/posts 发布的内容
/posts/{post_id} 某条内容
/posts/{post_id}/comments 某条内容的评论
/me 当前用户
/me/posts 我发布的内容
/me/stars 我星标的内容
/me/following 我关注的人
/me/followers 我的粉丝
/me/messages 我的消息
说白了, 以RestFul方式定义出来的API,名字上以资源为核心, 通过POST, GET, PUT, DELETE这几种操作对资源进行增删改查, 传统上, 以RPC方式定义出来的API, 名字上以动作为核心, 一般情况下, 使用的http方法也只是POST和GET.
API版本控制使用这种方式:
http://api.domain.com/v2.1/posts
最后,再定义下响应的数据协议。初期打算使用JSON,后期可能会考虑使用Protocol Buffers。数据结构则如下:
{
code:200,
message: "success",
data: { key1: value1, key2: value2, ... }
}
响应统一使用code、message、data的JSON数据格式
protocol buffer是和json等价的一种数据结构, 这点基础概念要了解.
文件格式以*.proto结尾, 到现在, 项目中还没有用到过.
API安全设计
安全设计方面,首先,我打算全面使用HTTPS。使用HTTPS,虽然牺牲了性能,但可以解决大部分安全问题。另外,苹果在之前的WWDC上就已宣布,从2017年1月1日起,所有iOS应用将强制使用HTTPS。这其实也意味着,从2017年起,所有App都将会使用HTTPS,不只是iOS。
全面https化是个趋势.
其次,用户鉴权方面则打算采用Token方式。用户登录之后分配一个accessToken和一个refreshToken,accessToken用于发起用户请求,refreshToken用于更新accessToken。accessToken会设置有效期,可以设为24小时。而用户退出登录之后,accessToken和refreshToken都将作废。重新登录之后会分配新的accessToken和refreshToken。
accessToken和一个refreshToken的概念要了解
然后,我还打算在App层级分配AppKey和AppSecret
每次向服务端发送请求时,AppKey都必须带上,服务端会对相应的AppKey进行校验。而AppSecret则需要安全保存在客户端,也不能在网络上进行传输,防止泄露。AppSecret只用于加密一些安全性级别较高的数据,以及为URL生成签名。
URL签名算法步骤如下:
- 将所有参数按参数名进行升序排序;
- 将排序后的参数名和值拼接成字符串stringParams,格式:key1value1key2value2...;
- 在上一步的字符串前面拼接上请求URI的Endpoint,字符串后面拼接上AppSecret,即:stringURI + stringParams + AppSecret;
- 使用AppSecret为密钥,对上一步的结果字符串使用HMAC算法计算MAC值,这个MAC值就是签名。
上面讲的是使用AppSecret生成签名的过程, 不必深究, 现在了解概念即可.
URL签名在每次发送请求时都需要附加在参数中,服务端接收到请求后会使用同样的签名算法计算签名值,只有服务端计算出来的签名值和接收到的签名值一致时才认为请求是安全的。
自此,API部分的设计就完成了。在此总结一下:
- 采用REST风格定义API,接口抽象成对资源的操作;
- 添加API版本控制,版本号嵌在URL中;
- 响应统一使用code、message、data的JSON数据格式;
- 全站采用HTTPS;
- 使用Token方式对用户鉴权;
- 使用AppKey方式对应用鉴权;(也就是分辨是Android端还是IOS端发过来的请求)
- 使用URL签名对请求鉴权;
- 参数中添加nonce值增强签名的不可预测性。
http://keeganlee.me/post/practice/20160816
App项目实战之路(三):原型篇
作者使用的是墨刀工具来设计原型.
也有人提出使用 Sketch 做原型设计。无可否认,Sketch 也是可以设计原型的,PS、AI 等工具也同样可以。至于交互,用标注的方式就好了。但这些工具,确切地说,更适合用来做 UI 设计,而不是原型设计。做原型设计,要求的就是能够快速看到效果,不只是界面效果,还有交互效果。用UI设计工具来做,一是很难达到快速的要求,二是交互效果等于没有。
http://keeganlee.me/post/practice/20160903
App项目实战之路(四):UI篇
设计工具自然是用强大的Sketch
http://keeganlee.me/post/practice/20161006
App项目实战之路(五):服务端篇
对服务端的开发, 大致了解下背景就可以了.
之前,我是没打算将服务端也列入开源名单的。但现在的想法已经改变了,我打算将整个项目都开源,不只是Android端和iOS端,也包括服务端,为一些有志于成为全栈工程师(甚至是全栈架构师)的程序猿提供一个不断进化的完整的学习项目。
数据库方面,我选择了广泛使用的MySQL。原因有二:一是据闻Facebook、Twitter等社交平台核心数据库也是MySQL;二是MySQL 5.7版本加入了对JSON格式的原生支持,这点特性使得MySQL也具备了NoSQL的功能。但本项目初期考虑先只用关系型的数据结构。
最后,应用服务器自然就是选择Tomcat了.
http://keeganlee.me/post/practice/20161016
App项目实战之路(六):数据库篇
浏览器项目的数据库的表结构起码要总结的出来.
这章讲的是服务端数据库的设计,大致了解下技术背景就可以了.
---------DONE.----------