3

I am using RabbitMQ in my app for chat module. It works fine with local server but somehow I am not able to connect to remote RabbitMQ server. I keep getting this error when I try to send a message.

Received connection: <RMQConnection: 0x6000022e2eb0> disconnectedWithError: Error Domain=GCDAsyncSocketErrorDomain Code=7 "Socket closed by remote peer" UserInfo={NSLocalizedDescription=Socket closed by remote peer}

My swift code looks like this:

func getRabbitMQUrl() -> String{
    var components = URLComponents()
    components.scheme = "amqps"
    components.host = "[broker-id].mq.[region].amazon.aws.com"
    components.user = "[username]"
    components.password = "[passowrd]"
    components.port = 5671
    let url = components.url?.absoluteString ?? "-"
    print("RabbitMQ URL", url)
    return url
}

    let uri = getRabbitMQUrl() 
    let conn = RMQConnection(uri: uri, delegate: RMQConnectionDelegateLogger())
    conn.start()
    let ch = conn.createChannel()
    let q = ch.queue(UUID().uuidString, options: .durable)
    let exc = ch.direct("my-exchange-name-here")
    q.bind(exc, routingKey: "my-routing-key")
    q.subscribe({(_ message: RMQMessage) -> Void in
        print("Message received")
    })

While using the local server, I set the uri "amqp://[username]:[password]@localhost:5672" and this works as expected.

PS: when I set this subscriber I do not get any error message regarding connection or anything. so I think it is connecting to the server without any issue.

But, when I send a message from the iOS app, the backend publish it and so the iOS app should receive it back. Exactly at this time, it gives me the above error!

EDIT: Though the C# backend is able to publish and subscribe messages successfully with RabbitMQ remote server. It is just the iOS client who fails!

Any help would be appreciated!

iRiziya
  • 3,235
  • 1
  • 22
  • 36
  • 1
    Check with BE developers for any config changes between local and remote setup, for example enabled SSL, authentication changes etc... – Gokul G Jul 21 '21 at 05:13

2 Answers2

3

After going through a lots of links, slack channels and Github issues, finally the issue has been resolved! The solution was unexpected.

The problem was, my C# backend has set the vhost to a slash / and in my Swift code I was passing an empty string instead. I got hint from here

I made these 2 changes in my code:

  1. In server uri I added %2f(a slash /) as the vhost at the end.
  2. I set the options of the exchange also to .durable just like the queue

Here is the complete working code:

func getRabbitMQUrl() -> String{
    var components = URLComponents()
    components.scheme = "amqps"
    components.host = "[broker-id].mq.[region].amazon.aws.com"
    components.user = "[username]"
    components.password = "[passowrd]"
    components.port = 5671
    components.path = "/%2f" //1st change
    let url = components.url?.absoluteString ?? "-"
    print("RabbitMQ URL", url)
    return url
}

let uri = getRabbitMQUrl() 
let conn = RMQConnection(uri: uri, delegate: RMQConnectionDelegateLogger())
conn.start()
let ch = conn.createChannel()
let q = ch.queue(UUID().uuidString, options: .durable)
let exc = ch.direct("my-exchange-name-here", options: .durable) // 2nd change
q.bind(exc, routingKey: "my-routing-key")
q.subscribe({(_ message: RMQMessage) -> Void in
    print("Message received")
})
iRiziya
  • 3,235
  • 1
  • 22
  • 36
  • 1
    I would recommend to use `URLComponents` for composing your uri. Your percent encoding is not correct: consider username, password or region are not ASCII strings. With a single `addingPercentEncoding:` you cannot accomplish this. – CouchDeveloper Jul 22 '21 at 16:32
  • Thanks for the recommendation @CouchDeveloper. I will change that. – iRiziya Jul 23 '21 at 04:48
0

Your URI is AMQP on the local host but AMQP is the example code.

You should connect to port 5671 if you are using AMQPS (And 5672 if you are on AMQP) Try that!