如何实现可扩展且安全的银行/跨订单类型更新

时间:2013-04-12 02:57:10

标签: python google-app-engine

我正在开发一个关于Google App Engine的小项目,尝试实施一个允许参与者买卖假货的网站,类似于股票市场,系统将显示实时的BID / ASK点差。

作为一个简单的例子:

  • 卖方下达并命令以8.00(订单1)
  • 出售10个方框
  • 买方随后下订单购买最多9.00(订单2)的5个盒子

当下达第二个订单时,系统将需要执行多个任务,所有任务都取决于所有成功完成的任务。

  • 拿出资金(8.00 x 5)来支付买方的包装盒并将其交给卖方
  • 从卖方取出方框(5)并将其交给买方
  • 将订单更新为完整(OID 2)或更新为部分填充(OID 1),以便它们不能双重匹配
  • 从每位参与者处收取费用并将其添加到系统帐户

如果我需要的只是将资金从一个参与者转移到另一个参与者,即使系统在中间失败,我也可以安全地做到这一点。但要确保上述所有任务都正确完成,并且如果其中任何一个失败则回滚在App Engine中显得过于复杂。

此外,我的“订单簿”和订单匹配引擎现在都是单线程(使用互斥锁进行锁定。)这似乎违背了使用App Engine的全部要点,但我不确定我是否看到了解决方法它

所以(最后) - 我的问题是:

  • 使用App Engine时是否有最佳做法,其中有多个步骤都依赖于每个步骤正确完成?
  • 有没有人有任何建议如何,允许订单簿是多线程的,或者如果它仍然是单线程的 - 最好的做法是不要让这个核心部分阻止使用网站,因为它可以扩展?我已经考虑过使用任务对订单添加/更新/取消进行排队,以使本书与直接参与者输入分开。

谢谢,我期待着您的帮助!

2 个答案:

答案 0 :(得分:1)

我认为如果您可以对商品的订单进行排序,那么您可以离线清除订单。通过“离线”,我的意思是你可以在一天结束时来找我,告诉我订单的顺序,我可以告诉你哪些交易发生了。一个障碍是,如果买方在交易清算时没有资金怎么办?您可以通过两种方式解决此问题:

  1. 将资金存入托管,以便任何可以清除的订单都可以。
  2. 如果资金不可用,请尝试清除购买订单。
  3. 正如您所建议的那样,您可能需要跨实体群体交易以确保资金转移是正确的(即资金既不会被创建也不会被销毁)。

    您可以按时间对订单进行排序(例如,paced_at = db.DateTimeProperty(auto_now_add = True))。如果两个订单有相同的时间,那么使用一些东西(最好是公平和确定的东西)打破平局。数字id(对于确定性)的哈希(公平)可能不是一个糟糕的选择。

    App Engine本质上是多线程的,因为应用程序可以有许多并发实例(实例不一定是同一进程中的线程)。实例是自动创建的,目前无法将实例数限制为1.如果您的应用程序状态位于数据存储区(而不是本地内存,memecache或其他位置),并且您的事务是正确的,那么你的应用程序将是“免费的”多线程。当然,您的交易是正确的并非易事。

    要记住的另一个工具是任务可以是事务性的。如果您想使用任务进行离线图书清算,这可能会派上用场。

答案 1 :(得分:0)

对于偶然发现此事的其他人 -

似乎现在可以在Google App Engine中实现跨群组交易:

https://developers.google.com/appengine/docs/python/datastore/transactions#Using_Cross_Group_Transactions

这意味着您可以在单个事务中同时读取,执行逻辑,然后一次写入多个实体。

我相信这解决了我在问题中提出的第一个问题。

第二个问题 - 是否有办法让订单簿不是单线程的,仍然是开放的。

谢谢!