apifaker 开发记

AntonydasWang · · 3488 次点击 · 开始浏览    置顶
这是一个创建于 的主题,其中的信息可能已经有所发展或是发生改变。

最近在准备毕业设计,虽然为 Android 项目,但还是需要一些后端支持,所以我就想能不能有一种方便的方式开发后端 api 的方式。 在之前 Rails 开发中,养成的了“急躁”的好习惯,转到 Go 后,明显感觉思维的转变,Go 的思维方式相对 Rails 来说,更注重正交性,清晰度,KISS。 所以开发之前,我明确了这个项目的定位: 1. 能快速开启一个符合 Restful 原则的 api 服务器。 2. 实现 `http.Helper` 接口,能组合别的路由,保证扩展性。 3. 用 json 文件,不用数据库,降低复杂度,能回写到文件,保证数据一致性。 4. 能实现简单的数据验证。 然后,决定了主要的 struct ApiFaker 的主要成员变量及其对外接口: ```go type ApiFaker struct { // 匿名组合,使用 Engine 的路由 *gin.Engine // json api 文件目录 ApiDir string // 内部路由 Routers []*Router // 外部路由 TrueMux http.Handler // 内部路由的前缀 Prefix string } // 创建新的 ApiFaker func NewWithApiDir(dir string) (*ApiFaker, error) // 设置 ApiFaker 前缀并组合其外部路由 func (af *ApiFaker) MountTo(path string, handler http.Handler) // 将运行事的数据回写到 json 文件中 func (af *ApiFaker) SaveToFile() // 实现 http.Handler 接口 func (af *ApiFaker) ServeHTTP(rw http.ResponseWriter, req *http.Request) ``` 这一步,非常重要,因为它关系到整个项目的走向,正所谓,选择比努力重要。然而,大部分项目都不能在一开始就确定所有变量和方法,然后不再改变,所以我们的设计标准就是KISS,从最核心的功能出发,逐步迭代。 接下来要设计的就是 `Router` 及其包含的最复杂的 `Model`: 1. 一个 Rouer 应该包含一个资源,可等同于数据库中的 table, 及其一系列 restful 的 path。 2. 资源对应的就是 Model,它应该: 1. 记录资源的每一个 table 的 column 2. 基本的 CRUD 3. 由于还要回写到 json 文件,所以应该有一个标示记录数据是否改变 4. 需要对应 json 文件的结构,和运行时数据的容器 ```go type Router struct { Model *Model Routes []Route filePath string } ``` ```go type Model struct { Name string Seeds []map[string]interface{} Columns []*Column Set *gset.SetThreadSafe dataChanged bool sync.Mutex } ``` 这里用到的我之前的实现的一个集合 [gset](https://github.com/focinfi/gset) 到这里,我们已经设计好项目的边界,和主要的数据结构,当然还有一些细节没有设计,比如,`Route` 和 `Colmun` 还有运行时的数据管理。 然而只要方向确定,内部不断迭代,一定能到达一个稳定的水平。 由于我 Go 开发经验和设计能力有限,还请高手可以指点。 源码:[github.com/Focinfi/apifaker](https://github.com/Focinfi/apifaker) 服务器设计文章:[许式伟:服务端开发那些事儿](http://www.csdn.net/article/2015-11-06/2826139)

有疑问加站长微信联系(非本文作者)

入群交流(和以上内容无关):加入Go大咖交流群,或添加微信:liuxiaoyan-s 备注:入群;或加QQ群:692541889

3488 次点击  
加入收藏 微博
添加一条新回复 (您需要 登录 后才能回复 没有账号 ?)
  • 请尽量让自己的回复能够对别人有帮助
  • 支持 Markdown 格式, **粗体**、~~删除线~~、`单行代码`
  • 支持 @ 本站用户;支持表情(输入 : 提示),见 Emoji cheat sheet
  • 图片支持拖拽、截图粘贴等方式上传