电影订票系统 一些问题

  1. 如果transaction table不考虑退票的话,感觉transaction table和ticket table有点重复

  2. 1.7 接口设计只给了 搜票购票的接口,是不是还需要考虑一个event点进去查询座位的request,点了一个座位预留座位的request(之后需要付款)?

  3. 1.8 讨论扩展性里面为啥是2-phase commit?扩展性不是应该讨论怎样才能support更多的request/user么(sharding?增加机器?),2-phase commit只是保证transaction,和扩展性有啥关系?

1 个赞
  1. 不一样,ticket db 跟付款没有关系,即使票是免费的也需要 ticket db。Transaction DB 是记录这笔交易的。
  2. 提得很好,确实需要一个根据票查询座位的接口。
  3. 确实关系不大,我会在课件上去掉。
  1. 容灾设计里面讲到kafka as distributed log,log不是一般都存在本地disk里面的么?等机器restart以后就读本地log来回复状态的吧?之所以说这些participant是stateless server是因为把保存状态的log放到了distributed kafka里面么?

  2. 购票api是不是用put更好,这样不小心点了两次付款也不会扣两次钱?

  3. 排队等票这个feature一般用户需要选择座位以后加入waitlist吗还是说用户只是加入某一个event的waitlist一旦有这个event的空座位就会自动尝试付款?

  4. 关于ticket table pending 状态的ticket现在的设计我感觉会有race condition的问题。比如快要ttl到期的时候,之前那个reserver票的thread在付款前可能再check一下ticket table发现还没过期,于是去付款。然后刚过期的时候另一个人check我们的ticket table发现过期了于是也reserve了这张票并把modified time改了。这个时候第一个人已经call了external的payment api把钱付了但是回头想改ticket table到unavaialble的时候发现modified time对不上了,但payment由于是external的api不是一个可逆的操作吧,可能还需要涉及到refund。其实可以在pending状态之后加一个paying的状态,right before我们的系统调用external payment api的时候可以把ticket table状态改成paying的状态,到了这个状态别人就不能通过ttl来把票抢走,这样如果付款成功就变成unavailable,如果付款失败就变成pending状态。pending状态下如果ttl到期别人是可以把票抢过去的。

  5. 2-phase commit如果有机器永久性宕机也没关系吧。可以每台机器对于每个transaction都有一个ttl,ttl过了以后就当作失败,然后读undo log来revert change不就好了?

  6. 电影订票系统里面这个distributed transaction的隔离级别是什么?读提交还是可重复读?

  1. 机器的硬盘有可能会失灵,这样本地 log 就读不出来了,需要靠 Kafka as distributed log.
  2. 还是用 POST 合适,idempotency 不是唯一的考虑,可以参考 Stackoverflow 高赞回答 以及 Stripe 是怎么处理 idempotent POST
  3. waitlist 的机制两个都可以处理,需求上比较合理的是后者。
  4. 可以这么做。在课上提到的做法认为这个 payment 是可逆的,出现 race condition 就 refund。
  5. 你说的做法没法保证在TTL完了之后系统状态是 ALL or Nothing。其中永久宕机的那台机器没法回复到最初状态。
  6. Saga Pattern 不提供 isolation guarantee。需要应用层解决。
  1. 应用层解决你是指这些相关的server的code要写的很精妙来确保isolation?

应用层需要做检测,如果isolation被突破了,就需要有修复机制。

想问一下 关于stripe的idempotent request 文章里说 “Subsequent requests with the same key return the same result, including 500 errors.” 如果后续的request succeed了,还是返回500 error吗 client怎么知道有没有succeed呢?谢谢

Stripe 文档的意思是如果 stripe 处理过一次以后就会记住当时的 response,下一次问的时候会原封不动的返回,所以不存在后续 request success 而第一次失败的问题。

搜索座位+1。
整个这个ticket booking system 对座位的支持都没有。

课上的电影订票系统支持选座位订票。请问你想支持的需求是?