说句题外话,如果使用 PostgreSQL 的话,查询 tree 结构的 children/ancestors 都可以用 WITH
(CTE) 做递归查询,稍微封装一下就可以不依赖任何库。详细信息可以看 文档 。
优点:
- 单条 SQL 查多级父子关系,而且不用缓存都很高效。
- 不需要额外的字段,只需要
parent_id
。
缺点:
- SQL 查出来的结果始终是平铺的记录,如果需要树形结构的数据,得在应用层面做转换。不过平铺的数据在某些特定场景下(比如 JSON API 规范的 compound documents,或者其他展平关联数据的 API 格式)反而是优点。
- 上一点提到在应用层面做转换,但对 ActiveRecord 而言不太好做,因为
model.relationship = another_model
会引发一些副作用,如果是转成纯 Ruby 对象就不存在这种问题。