能不让服务端干的事就别让服务端去干

  • 作者:KK

  • 发表日期:2016.12.8


我发现每次项目功能需要用cookie时,总是由服务端程序员来写setcookie这些代码

其实我并不认为所有涉及设置cookie的都要由服务端来,简单地说能不用后端设置cookie的就不要用后端来设置,让前端自己设置cookie


以前带过一个项目,其中要防止用户重复赞一个产品,最终决定用简单的方案:使用cookie记录赞过的ID,再赞的话就根据cookie检查是否已赞过

我看到程序员提交的代码是这样的:

前端代码点赞时判断是否有相关cookie,有就提示赞过,否则就请求后端赞+1 后端收到请求时也检查一下cookie,如果没有赞过的话就+1 后端赞+1后再执行setcookie

看上去可以实现,但是我觉得这犯不着让后端做这个cookie相关事

有的人肯定很反对:前端检查一遍,后端又检查一遍不是更加保险吗?

可是这个功能本质上就是简单设计的,无法彻底防御重复赞的,后台检查一遍只是“信不过前端的检查,再加一层检查做保险而已”


应该相信前面的流程,并保证前面的流程是正确的

首先自己项目的前端代码在完成的时候当然要做好质量验收工作,确认它是有检查cookie进行提示的

如果说前端有可能出问题导致直接绕到了后端,没错后端加多一层检查是对的

那能不能这样想:如果底层是其他人写的,他要不要也思考“我也害怕后端的控制器对请求参数校验逻辑会哪天被改坏没生效,我在底层update前也检查一下好了”

这压根就是后面的流程不信任前面流程的一种表现,要不要还这样啊:所有操作用户名的地方都判断一下用户名是否为空?而不是相信注册的时候就能校验好用户名是否为空?


前端自己检查cookie,前端也自己setcookie

这样也是功能上的前后分离的设计方式了,前端需要的功能,自己通过设置cookie来实现自身的需求而无需麻烦后端。如果未来不需要这个功能了,只是前端移除掉代码就行了,后端一点都不用改变,并且不会出现前端移除了代码,但又漏删了后端的代码(因为有时候负责前端和后端的就不是同一个人)的现象

这里还应该深入地讲讲,首先从功能设计上来说,一个小应用,采用了这样的方案防重复点赞,本质上就是“服务端其实允许了重复点赞”,只要请求不带cookie上来就是了嘛,所以要防重复的只是前端

就好比一个开放平台允许我们调用某推送接口把一些自定义信息推送给某一群用户,我们的产品使用者可以写一些广告什么的进行推送(使用者在我们的前端填写表单,提交到我们的后台,我们的后台再调用开放平台),可是由于次数有限,则我们做了一些限制,记录了使用者的推送次数,并提醒他们:如果1天内要推送第4次必须付费10元,否则不能推送

其实这个推送次数限制是我们的软件产品做的限制,但开放平台又没限制,只是我们的产品要做好用户体验,希望不要骚扰到用户来提高了一下门槛,或者又基于推送盈利的目的

因此这种限制工作是作为接口调用者要做的事情,而不是接口提供方的事情。被调用方本来就是设计成允许无限次推送的嘛


其实该怎么做,无定论,学会把握性价比

其实针对这个功能的话,本质上服务端还是希望能很好地限制重复赞的,只是又怕麻烦,抱着“我是个小项目,简单做就是”的心理才用了cookie的方式

但在项目规模变大,商业价值提升的时候就需要来真的了,及时把方案改成完全防止重复赞,这样前端可能都不需要修改,后端改校验和记录方法就行了

如果说设计简单的话,那绝对是前端自己处理cookie的方法是最简单的,我也比较推荐这个方案,包括服务端本来就不打算限制这种接口请求的话


然而写这篇文章希望可以分享的一个心得是:我们不能盲目地去跟风做一件事情,不要想着“要设置cookie了”就跟着人家说的直接用服务端语言去setcookie,要思考一下:如何安排这个设置cookie的代码才是最合适的

就以此功能为例,其实在哪里设置对整体没什么影响,而如果程序员能洞悉到这些问题的话,他其实是一个编程时态度比一般人都严谨的人,这是一件好事

不过我还是比较推荐:能不让服务端干的事就别让服务端去干