问题描述
最简单的MRE是rails g scaffold users
在创建用户时,其ID将为1、2、3、4等,其“显示”路线为/show/:id
有时我们不希望网站的用户确切知道我们拥有多少用户-是否有一种简便的方法来对此进行混淆?
我可以想到一种手动完成此操作的方法,方法是在注册时添加一个带有12位数字随机整数的附加列,同时还要检查随机生成的整数是否不存在。
但是我不知道有没有更聪明的方法?
注释
-
示例:https://www.youtube.com/watch?v=Gzj723LkRJY(其中
Gzj723LkRJY
可能是随机生成的,并且无法预测) -
为什么incremental ids can be a bad idea(从2m 52s开始约30秒)的示例
许多设计不当的网站都使用增量计数器。它可以告诉竞争对手您有多少客户..它可以使人们轻松下载所有记录
解决方法
Rails实际上并不关心您为模型使用的主要标识符是什么。
在创建用户时,其ID将为1、2、3、4等,并且其“显示” 路线将是/ show /:id
不正确。路线将为purr
。运行woof
以查看生成的路由。
您的路由实际上不仅会匹配整数,而且还会匹配除有限子集(特别是/users/?(:id)
和rails routes | grep users
)之外的所有字符到命名的.
段。
因此,将使以下内容与用户#show操作相符:
/
但不是:
:id
默认情况下,自动递增的整数列在Rails中用作主键,因为它们简单,简短并且在99%的时间内都能完成工作。通常,如果您切换到UUID,原因是您正在以需要多个数据库的规模进行操作,并且顺序生成ID不会削减它。将标识符切换为随机生成的内容将使猜测变得无穷无尽,但仍不能代替实际授权对资源的访问,因为它们仍可能泄漏到日志,电子邮件等中。
我可以想到一种通过添加其他列来手动完成此操作的方法 使用12位随机整数进行注册,同时还要检查 随机生成的整数尚不存在。 但是我想知道有没有更聪明的方法?
是的。不要重新发明轮子。
Ruby已经具有内置的SecureRandom#uuid方法,该方法生成UUIDs according to RFC 4122:
GET /users/1
GET /users/gabba-gabba-hey
GET /users/gabba%20gabba%20hey
由于此处发生冲突的风险极低,因此该循环可能不会运行一次以上,并且只需对(希望)索引的主键运行一个GET /users/1/2
GET /users/gabba/gabba
GET /users/gabba/gabba/hey
查询-因此成本相对较低。 / p>
通过不仅使用整数,而且使用字母,您可以生成较短的标识符,而发生碰撞的可能性较小。
如果您使用的是内置有UUID支持的数据库(例如Postgres),则这是一个更好的选择,因为这确实是最好的解决方案,因为它避免了应用程序膨胀并减少了开销。
,您可以使用UUID
,它将为您提供随机的安全令牌,没人能轻易理解用户的系列。
迁移如下所示
create_table :users,id: :uuid do |t|
t.string :name
t.string :phone
....
t.timestamps
end
希望它能对您有所帮助。