Since the same RabbitMQ server instance will be used by both CBS and SEPA Connector, it is necessary for its configuration to be agreed upon ahead of time.
It is possible for queues to be set up by the applications using them. That would ensure both CBS and SEPA Connector use the same definitions, but would also necessitate synchronizing any changes in CBS and SEPA connector code, because AMQP clients validate preexisting queues if they are found. For this reason using `definitions.json` file for RabbitMQ instance setup was deemed more efficient.
Of course, it may prove beneficial to add queue definitions to both CBS and SEPA Connector code sometime in the future for purpose of server settings validation on application startup.
## Docker Compose
The following Docker Compose configuration creates RabbitMQ server with management plugin enabled, SSL disabled for AMQP connections, SSL enabled for Management Web UI and with users, virtual hosts and queues preconfigured.
SSL for Web UI can be disabled by removing `RABBITMQ_MANAGEMENT_SSL_CERTFILE` and `RABBITMQ_MANAGEMENT_SSL_KEYFILE` environment variables as well as volumes with certificate and key and changing port 15671 to 15672.
Similarly SSL for AMQP connections can be enabled by adding `RABBITMQ_SSL_CERTFILE` and `RABBITMQ_SSL_KEYFILE` environment variables with appropriate values as well as volumes with certificate and key and changing port 5672 to 5671.
By default enabling SSL for AMQP connections also enables SSL for Web UI using the same certificate and key pair. No tests were performed to ascertain if Web UI can be used without SSL or with different SSL certificate and key pair if SSL for AMQP connections is enabled.
Users:
| Username | Password | Permissions |
| ------ | ------ | ------ |
| syncad | dandandan | all (admin) |
| cbs | cbs | read and write permissions to all queues on `/cbs-sc` |
| sc | sc | read and write permissions to all queues on `/cbs-sc` |
Communication between CBS and SEPA Connector requires 4 queues: one for sending messages from CBS to SEPA Connector, one for sending messages from SEPA Connector to CBS and one dead letter queue for each of the previous queues.
## Message acknowledgment and error handling
> In order to make sure a message is never lost, RabbitMQ supports message acknowledgments. An acknowledgement is sent back by the consumer to tell RabbitMQ that a particular message has been received, processed and that RabbitMQ is free to delete it.
>
> If a consumer dies (its channel is closed, connection is closed, or TCP connection is lost) without sending an ack, RabbitMQ will understand that a message wasn't processed fully and will re-queue it.
The aforementioned mechanism may or may not be enabled by default, depending on which library is used for connecting to RabbitMQ. **Message acknowledgment is always enabled by a consumer and not by a producer or server.**
Since, by definition, message acknowledgement (`basick.ack`) is not sent until after the message is processed, any errors or exceptions will, most likely, prevent it from being sent. This must be addressed to prevent infinite redelivery loop, which quickly depletes server's resources and causes both RabbitMQ and the consumer (CBS or SEPA Connector) to crash.
That loop can be avoided by sending either negative acknowledgement (`basic.nack`) or rejection (`basic.reject`) message to RabbitMQ on the same queue that the original message was read from.
### SEPA Connector
In SEPA Connector the infinite redelivery loop problem was solved by configuring the error handler to consider all exceptions as fatal, which causes it to rethrow them wrapped in an exception recognized by the listener as a signal to respond with `basic.reject` message to the AMQP server.