【问题标题】:Understanding goroutines for web API了解 Web API 的 goroutines
【发布时间】:2015-05-06 16:06:57
【问题描述】:

刚开始使用 Go 并希望创建一个简单的 Web API。我正在研究使用 Gorilla mux (http://www.gorillatoolkit.org/pkg/mux) 来处理 Web 请求。

我不确定如何最好地使用 Go 的并发选项来处理请求。我是否在某处读到 main 函数实际上是一个 goroutine,或者我应该在收到每个请求时将它们分派给一个 goroutine?如果我“走远了”,请道歉。

【问题讨论】:

  • 您实际上并不需要 Web 服务的例程。库本身已经能够单独处理请求。您只需担心处理调用的效率如何,而库将处理其余的。整个net 机制大多已经被设计成这样工作了。这就是为什么 Go 如此出色的主要原因,它提供了开箱即用的出色功能。
  • 谢谢 - 但我假设如果在处理程序中我需要从数据库中获取数据,那么这可以/应该通过 goroutine 完成?
  • 没有更好的 mysql 库(或任何其他流行的库)也通过相同的逻辑处理它们的调用。在使用 SQlite3 等库时,您不需要像在 Objective-C/C/C++ 中习惯的那样启动高级队列。再说一次;只关注代码的简洁性。这些图书馆已经很棒了:D
  • 哇——听起来好得令人难以置信,哈哈
  • 是的!我正在通过我 5 岁的 macbook pro 上的 tiedot 数据库发送数以万计的请求。无论您来自哪种语言,这都是一种解脱。当您的文件甚至不到 200 行长时,您几乎无法相信您的代码已经完成。这就是我爱上 Go 的原因 :) 不用担心线程或开销。在 Go 中调整也非常容易,而在其他语言中,后期优化主要是 *ss 中最大的痛苦。

标签: go


【解决方案1】:

假设您使用 Go 的 http.ListenAndServe 来处理您的 http 请求,文档明确指出每个传入连接都由一个单独的 goroutine 为您处理。 http://golang.org/pkg/net/http/#Server.Serve 您通常会从您的 main 函数中调用 ListenAndServe

Gorilla mux 只是一个包,它比http.DefaultServeMux 更灵活地将请求路由到您的处理程序。它实际上并不处理传入的连接或请求,只是简单地将其中继到您的处理程序。

我强烈建议您阅读一些文档,特别是本指南 https://golang.org/doc/articles/wiki/#tmp_3 关于编写 Web 应用程序。

【讨论】:

    【解决方案2】:

    尽管我因过于宽泛而投票结束,但我仍在提供答案。

    无论如何,这些都不是必需的。你想多了。如果你还没有读过这篇文章,它看起来像是一个不错的教程; http://thenewstack.io/make-a-restful-json-api-go/

    您真的可以像使用大多数典型的休息框架一样设置路由,让网络服务器/框架担心请求处理级别的并发性。您只会使用 goroutine 来生成请求的响应,例如,如果您需要聚合来自文件夹中的 10 个文件的数据。人为的示例,但这是您将在每个文件中分离出 1 个 goroutine,通过在非阻塞选择中读取通道来聚合所有信息,然后返回结果。如果有意义的话,您可以期望以异步、非阻塞方式调用代码的所有入口点...

    【讨论】:

    • 正如 Rob Pike 一遍又一遍地指出的那样,你也需要担心,即使 groroutine 非常便宜,你也不应该过度使用它们,看看它们的实际用途。说实话;当没有真正做任何双向的事情(比如聊天或实时反馈系统)时,我从不使用 goroutines。我更喜欢只在临时的事情需要某种形式的负载分布时才使用它们作为最后的手段(这可能还包括一些往往不能最有效地使用 cpu 周期的库;让它们并行运行而不是串联运行)。
    • @Allendar 我确实注意到了这篇博文,尽管它建议在 MongoDB 中使用 goroutines(我可能会使用它):blog.mongodb.org/post/80579086742/…
    • 因为 NoSQL 系统不像 RDBMS 那样受到锁的影响。快速浏览该文章,似乎他们使用例程将任务生成到数据库而无需等待直接确认。当您不关心结果时,这可能会很方便。我在为商店下订单时主要做这样的事情。只需告诉客户您已完成,他们会在处理完所有内容后收到邮件。当例程从支付提供商那里得到确认时,它将向客户发送邮件。这对客户来说感觉非常流畅,因为主流程不必等待。
    • @tommyd456 我并没有真正看那个例子,但是如果你必须聚合多个查询的结果,它是有意义的。只有当工作实际上可以被划分时,使用 goroutine 才有意义,如果我必须从多个集合中获取对象并将它们合并(忽略它对 Mongo 的不良使用,并且可能只是使用 SQL)在内存中然后分配一些这项工作可能是一个很好的用途。但是,这些例程将针对单个请求,而不是在请求处理程序级别。它实际上与我的文件示例没有什么不同,只是商店是 Mongo。
    猜你喜欢
    • 2017-03-06
    • 1970-01-01
    • 1970-01-01
    • 2017-01-13
    • 1970-01-01
    • 2013-08-04
    • 2021-09-02
    • 2018-07-29
    • 1970-01-01
    相关资源
    最近更新 更多