gpt4 book ai didi

go - 无法使用 msg := rang msgs (msgs is a channel) 阻止 rabbitmq msg

转载 作者:数据小太阳 更新时间:2023-10-29 03:26:36 27 4
gpt4 key购买 nike

我复制了 rabbitmq go example 并稍作改动以进行测试。

Example URL .正常工作

代码结构:

 func main() {
//dial rabbit server
//declare channel/exange/queue
msgs, err := ch.Consume() //typeof(msgs)=<-chan Delivery

forever := make(chan bool)

go func() {
for d := range msgs {
log.Printf("Received a message: %s", d.Body)
}
}()

log.Printf(" [*] Waiting for messages. To exit press CTRL+C")
<-forever
}

但是如果我将一些代码放入函数中,例如:

func ListenRabbit() (<-chan Delivery, error) {
//dial rabbit server
//declare channel/exange/queue
msgs, err := ch.Consume() //typeof(msgs)=<-chan Delivery
return msgs, err
}

func main(){
msgs, _ := ListenRabbit()
for d := range msgs {
log.Printf("Received a message: %s", d.Body)
}
}

无法阻止 main() 等待来自服务器的消息。它会立即退出。原始代码和更改后的代码之间有什么区别吗?非常感谢!

最佳答案

这是垃圾收集和关闭延迟的简单错误。

假设您的代码库与此类似,因为您省略了示例中的代码。

package main

import (
"log"

"github.com/streadway/amqp"
)

func failOnError(err error, msg string) {
if err != nil {
log.Fatalf("%s: %s", msg, err)
}
}

func ListenRabbit() (<-chan amqp.Delivery, error) {
conn, err := amqp.Dial("amqp://guest:guest@localhost:5672/")
failOnError(err, "Failed to connect to RabbitMQ")
defer conn.Close()

ch, err := conn.Channel()
failOnError(err, "Failed to open a channel")
defer ch.Close()

q, err := ch.QueueDeclare(
"hello", // name
false, // durable
false, // delete when usused
false, // exclusive
false, // no-wait
nil, // arguments
)
failOnError(err, "Failed to declare a queue")

msgs, err := ch.Consume(
q.Name, // queue
"", // consumer
true, // auto-ack
false, // exclusive
false, // no-local
false, // no-wait
nil, // args
)
failOnError(err, "Failed to register a consumer")

return msgs, err
}

func main() {
msgs, _ := ListenRabbit()

for d := range msgs {
log.Printf("Received a message: %s", d.Body)
}

log.Printf(" [*] Waiting for messages. To exit press CTRL+C")
}

您的问题是您在 ListenRabbit 方法上初始化与 Rabbit 的连接并同时关闭它。因此,当您在 channel 上进行测距时,它已经关闭。

defer conn.Close()

defer ch.Close()

一旦方法 ListenRabbit 退出,这些告诉去调用 connectionchannel 上的 Close 方法。此外,通过在该方法中初始化连接和 channel ,您将让所有这些对象被垃圾收集,因为一旦 moethod 完成,就不会留下对它们的引用。

您需要在您的 main 中初始化所有这些,以便它保持打开和工作,或者您可以在您的方法返回值上返回连接和 channel ,但请记住在完成后处理/关闭它们。

rabbit git repository 上的代码示例是正确的方法,但这只是设计代码的一种方法。您需要了解面向对象编程、go 编码(引用、延迟、垃圾回收等)的一些基本概念以及您想要做什么,以便您可以决定使用什么是最佳设计。

目前仅使用示例代码就足够了。

关于go - 无法使用 msg := rang msgs (msgs is a channel) 阻止 rabbitmq msg,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39636684/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com