项目反思

一个小项目

实验室接了一个小项目, 是一个网站, 急着要用, 要求两周做完. 师兄找了我和另一个同学来做, 我做后端, 她做前端. 用什么写呢? 我在这个项目开始之前刚好学了一些 Python Web( Flask ), 看到了一些感觉很不错的特性, 所以我就想用 Python 写. 我是唯一的后端, 我说用 Python, 大家都不反对, 其实也无所谓吧. Python 写起来比 Java 确实要舒服一些, 语法更简洁, 很快就部署了起来. Flask 框架本身就非常小巧, 在 Java 上都属于框架的在 Python 通过几个很小的插件, 加几行代码就解决可以一个问题.

这是个比较简单的项目, 但我完成的并不好, 甚至在项目上线的第三天, 我在半夜 1 点左右改了一个非常明显的 bug, 或许可以说出现 bug 很正常, 但那个 bug, 是因为那部分功能没测试. 我也不想再回顾, 先写下反思吧, 其他的以后有机会再说.

出现的问题

写测试

如果没有刻意练习, 很难主动写测试, 整个项目我没写一行测试代码, 也出现了很多问题. 很多时候修改了某处代码, 而类似逻辑/用到同一部分的地方却忘记修改导致出现 bug, 这种情况发生过好几次, 但在改的时候又确实没想起来, 这时候如果有写好的测试, 跑一下立刻就知道改动是否有遗漏.

Git 没意义

项目使用了 Git, 但只有一个作用就是让我和前端稍微方便地合并代码 (其实还是面对面肉眼合并). 从 repo 建立到最终项目结束, 项目一直只有一个分支 commit 基本没什么道理, push 随意, 加上没有测试, head 上常常放着刚提交的 bug.

设计混乱

本身我也有认真设计数据库的, 但是因为只有我一个后端, 所以随着需求的变更, 数据库被我改造的越来越奇怪. 我用一个 int 字段来表示一个实体的不同状态, 每次状态改变都自增, 这个设计给后来编码带来了许多麻烦, 甚至带来了一个隐藏 bug 现在项目中还存在. 而这一切的源头就是我不愿意全盘考虑整个流程, 同时我懒得增加字段, 而是不断地给字段赋予新功能.

跟 Java Web不同, Python Web 的实体不是 plain old object, 它被定义具有许多功能, 就比如说 Person 对象会自己告诉我它有几岁, 它的年薪多少, 它的孩子们都是谁, 这似乎是完全地面向对象. 受这种想法影响, 我在实体类中定义了大量各种功能的函数, 在路由层, 通过我拥有的对象的即可直接进行各种操作, 这种做法初衷很好. 但是需要对 OOP 仔细思考. 我设计的很差, 以至于后来我想要添加一个函数我都不知道应该写在哪里, 后来追加的 service.py 里面装满了各种我不知道应该放在哪里的各种中间函数, 我想如果他人看我的代码, 对于这个文件一定觉得莫名奇妙.

不会 Python

其实在学 Flask 之前, 我甚至没怎么学过 Python, 对于 Python 的认识和 Go, Ruby 的认识一样多, 但我还是开始了这个项目. 对 Python的不理解表面上并没有给我带来什么难以解决的问题, 代码都是一样的写, 但更深层次上, 我常常用 Java 的方式在写 Python. 我能感觉到有一些做法是不恰当的, 但是能运行, 结果没什么异常也就作罢.

虚心

在项目中期, 需求没发生大变化之前, 主要的逻辑我都写好了, 不禁有些膨胀, 感觉有些洋洋得意, 这么快就写完了, 只要静静等前端就好了. 这直接导致我后来多次测试不认真, 多次出现测试过的代码仍然存在问题的情况.

感想

Web 都差不多

Flask 也好, Spring 也罢, 大家都在做的事情是类似的, 做事情的方法也大差不差. 有很多做法都互相借鉴, 虽然没有使用, 但我在 Flask 里面也见到了依赖注入相关的内容, 虽然没用 Hibernate, 但 orm 的一些做法也都接近.

理解复杂

很多框架帮忙解决的地方, 都是复杂所在. 这些地方可能搞一些不知所谓的配置, 加几个类就有效果了, 但怎么产生效果是完全不知道. 这些地方确实没那么容易理解, 但是不容易理解的不是背后的原理, 而是实现的复杂. 很多看起来非常复杂的实现背后都是很简单的一些思路和方法, 但是实现看起来就是没那么容易理解. 所以要尽量去理解复杂, 把事情看开来.

Flask 中的蓝图

蓝图的概念很有意思, 在我理解, 每一个蓝图就是一个微缩的 Flask App, 如果不看数据, 它自己是自给自足的, 它的功能是内聚的, 然后多个蓝图组合在一起成为一个完整的网站.

View Model

很多时候实体的中拥有的字段并不是前端真正需要的, 它们需要的是处理过的, 保存过的数据实体, 这时候可以建一些 View Model 作为前后端传输数据的格式, 我猜想 Java 里面也有类似的设计, 但我还没看到.

url_for('app.index')

Licensed under CC BY-NC-SA 4.0
comments powered by Disqus
May Breeze Bless U
Built with Hugo
Theme Stack designed by Jimmy