add publish options
- add publish options to Exchange (these need to move to a Basic abstraction) - listen for bmReturn in Exchange to catch errors - added auto tests to check behavior of an invalid mandatory publish - cleaned up bit fields in exchange and queue
This commit is contained in:
parent
cb52911bed
commit
4f808bef92
|
|
@ -64,19 +64,37 @@ bool ExchangePrivate::_q_method(const Frame::Method &frame)
|
||||||
if (ChannelPrivate::_q_method(frame))
|
if (ChannelPrivate::_q_method(frame))
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
if (frame.methodClass() != Frame::fcExchange)
|
if (frame.methodClass() == Frame::fcExchange) {
|
||||||
return false;
|
switch (frame.id()) {
|
||||||
|
case miDeclareOk:
|
||||||
|
declareOk(frame);
|
||||||
|
break;
|
||||||
|
|
||||||
switch(frame.id()) {
|
case miDeleteOk:
|
||||||
case miDeclareOk:
|
deleteOk(frame);
|
||||||
declareOk(frame);
|
break;
|
||||||
break;
|
|
||||||
case miDeleteOk:
|
default:
|
||||||
deleteOk(frame);
|
qDebug() << Q_FUNC_INFO << "unhandled exchange method: " << frame.id();
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
} else if (frame.methodClass() == Frame::fcBasic) {
|
||||||
|
switch (frame.id()) {
|
||||||
|
case bmReturn:
|
||||||
|
basicReturn(frame);
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
qDebug() << Q_FUNC_INFO << "unhandled basic method: " << frame.id();
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ExchangePrivate::declareOk(const Frame::Method &frame)
|
void ExchangePrivate::declareOk(const Frame::Method &frame)
|
||||||
|
|
@ -107,6 +125,31 @@ void ExchangePrivate::_q_disconnected()
|
||||||
declared = false;
|
declared = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ExchangePrivate::basicReturn(const Frame::Method &frame)
|
||||||
|
{
|
||||||
|
Q_Q(Exchange);
|
||||||
|
QByteArray data = frame.arguments();
|
||||||
|
QDataStream stream(&data, QIODevice::ReadOnly);
|
||||||
|
|
||||||
|
quint16 replyCode;
|
||||||
|
stream >> replyCode;
|
||||||
|
QString replyText = Frame::readField('s', stream).toString();
|
||||||
|
QString exchangeName = Frame::readField('s', stream).toString();
|
||||||
|
QString routingKey = Frame::readField('s', stream).toString();
|
||||||
|
|
||||||
|
Error checkError = static_cast<Error>(replyCode);
|
||||||
|
if (checkError != QAMQP::NoError) {
|
||||||
|
error = checkError;
|
||||||
|
errorString = qPrintable(replyText);
|
||||||
|
Q_EMIT q->error(error);
|
||||||
|
}
|
||||||
|
|
||||||
|
qAmqpDebug(">> replyCode: %d", replyCode);
|
||||||
|
qAmqpDebug(">> replyText: %s", qPrintable(replyText));
|
||||||
|
qAmqpDebug(">> exchangeName: %s", qPrintable(exchangeName));
|
||||||
|
qAmqpDebug(">> routingKey: %s", qPrintable(routingKey));
|
||||||
|
}
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
Exchange::Exchange(int channelNumber, Client *parent)
|
Exchange::Exchange(int channelNumber, Client *parent)
|
||||||
|
|
@ -175,20 +218,22 @@ void Exchange::remove(int options)
|
||||||
}
|
}
|
||||||
|
|
||||||
void Exchange::publish(const QString &message, const QString &routingKey,
|
void Exchange::publish(const QString &message, const QString &routingKey,
|
||||||
const MessageProperties &properties)
|
const MessageProperties &properties, int publishOptions)
|
||||||
{
|
{
|
||||||
publish(message.toUtf8(), routingKey, QLatin1String("text.plain"), QVariantHash(), properties);
|
publish(message.toUtf8(), routingKey, QLatin1String("text.plain"),
|
||||||
|
QVariantHash(), properties, publishOptions);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Exchange::publish(const QByteArray &message, const QString &routingKey,
|
void Exchange::publish(const QByteArray &message, const QString &routingKey,
|
||||||
const QString &mimeType, const MessageProperties &properties)
|
const QString &mimeType, const MessageProperties &properties,
|
||||||
|
int publishOptions)
|
||||||
{
|
{
|
||||||
publish(message, routingKey, mimeType, QVariantHash(), properties);
|
publish(message, routingKey, mimeType, QVariantHash(), properties, publishOptions);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Exchange::publish(const QByteArray &message, const QString &routingKey,
|
void Exchange::publish(const QByteArray &message, const QString &routingKey,
|
||||||
const QString &mimeType, const QVariantHash &headers,
|
const QString &mimeType, const QVariantHash &headers,
|
||||||
const MessageProperties &properties)
|
const MessageProperties &properties, int publishOptions)
|
||||||
{
|
{
|
||||||
Q_D(Exchange);
|
Q_D(Exchange);
|
||||||
Frame::Method frame(Frame::fcBasic, ExchangePrivate::bmPublish);
|
Frame::Method frame(Frame::fcBasic, ExchangePrivate::bmPublish);
|
||||||
|
|
@ -200,7 +245,7 @@ void Exchange::publish(const QByteArray &message, const QString &routingKey,
|
||||||
out << qint16(0); //reserved 1
|
out << qint16(0); //reserved 1
|
||||||
Frame::writeField('s', out, d->name);
|
Frame::writeField('s', out, d->name);
|
||||||
Frame::writeField('s', out, routingKey);
|
Frame::writeField('s', out, routingKey);
|
||||||
out << qint8(0);
|
out << qint8(publishOptions);
|
||||||
|
|
||||||
frame.setArguments(arguments);
|
frame.setArguments(arguments);
|
||||||
d->sendFrame(frame);
|
d->sendFrame(frame);
|
||||||
|
|
|
||||||
|
|
@ -26,9 +26,16 @@ public:
|
||||||
};
|
};
|
||||||
QString type() const;
|
QString type() const;
|
||||||
|
|
||||||
|
enum PublishOption {
|
||||||
|
poNoOptions = 0x0,
|
||||||
|
poMandatory = 0x01,
|
||||||
|
poImmediate = 0x02
|
||||||
|
};
|
||||||
|
Q_DECLARE_FLAGS(PublishOptions, PublishOption)
|
||||||
|
|
||||||
enum RemoveOption {
|
enum RemoveOption {
|
||||||
roForce = 0x0,
|
roForce = 0x0,
|
||||||
roIfUnused = 0x1,
|
roIfUnused = 0x01,
|
||||||
roNoWait = 0x04
|
roNoWait = 0x04
|
||||||
};
|
};
|
||||||
Q_DECLARE_FLAGS(RemoveOptions, RemoveOption)
|
Q_DECLARE_FLAGS(RemoveOptions, RemoveOption)
|
||||||
|
|
@ -37,8 +44,8 @@ public:
|
||||||
NoOptions = 0x0,
|
NoOptions = 0x0,
|
||||||
Passive = 0x01,
|
Passive = 0x01,
|
||||||
Durable = 0x02,
|
Durable = 0x02,
|
||||||
AutoDelete = 0x4,
|
AutoDelete = 0x04,
|
||||||
Internal = 0x8,
|
Internal = 0x08,
|
||||||
NoWait = 0x10
|
NoWait = 0x10
|
||||||
};
|
};
|
||||||
Q_DECLARE_FLAGS(ExchangeOptions, ExchangeOption)
|
Q_DECLARE_FLAGS(ExchangeOptions, ExchangeOption)
|
||||||
|
|
@ -57,12 +64,15 @@ public:
|
||||||
|
|
||||||
// AMQP Basic
|
// AMQP Basic
|
||||||
void publish(const QString &message, const QString &routingKey,
|
void publish(const QString &message, const QString &routingKey,
|
||||||
const MessageProperties &properties = MessageProperties());
|
const MessageProperties &properties = MessageProperties(),
|
||||||
|
int publishOptions = poNoOptions);
|
||||||
void publish(const QByteArray &message, const QString &routingKey,
|
void publish(const QByteArray &message, const QString &routingKey,
|
||||||
const QString &mimeType, const MessageProperties &properties = MessageProperties());
|
const QString &mimeType, const MessageProperties &properties = MessageProperties(),
|
||||||
|
int publishOptions = poNoOptions);
|
||||||
void publish(const QByteArray &message, const QString &routingKey,
|
void publish(const QByteArray &message, const QString &routingKey,
|
||||||
const QString &mimeType, const QVariantHash &headers,
|
const QString &mimeType, const QVariantHash &headers,
|
||||||
const MessageProperties &properties = MessageProperties());
|
const MessageProperties &properties = MessageProperties(),
|
||||||
|
int publishOptions = poNoOptions);
|
||||||
|
|
||||||
Q_SIGNALS:
|
Q_SIGNALS:
|
||||||
void declared();
|
void declared();
|
||||||
|
|
|
||||||
|
|
@ -25,6 +25,7 @@ public:
|
||||||
virtual bool _q_method(const Frame::Method &frame);
|
virtual bool _q_method(const Frame::Method &frame);
|
||||||
void declareOk(const Frame::Method &frame);
|
void declareOk(const Frame::Method &frame);
|
||||||
void deleteOk(const Frame::Method &frame);
|
void deleteOk(const Frame::Method &frame);
|
||||||
|
void basicReturn(const Frame::Method &frame);
|
||||||
|
|
||||||
QString type;
|
QString type;
|
||||||
Exchange::ExchangeOptions options;
|
Exchange::ExchangeOptions options;
|
||||||
|
|
|
||||||
|
|
@ -35,6 +35,7 @@ namespace QAMQP {
|
||||||
enum Error {
|
enum Error {
|
||||||
NoError = 0,
|
NoError = 0,
|
||||||
ContentTooLargeError = 311,
|
ContentTooLargeError = 311,
|
||||||
|
UnroutableKey = 312,
|
||||||
NoConsumersError = 313,
|
NoConsumersError = 313,
|
||||||
ConnectionForcedError = 320,
|
ConnectionForcedError = 320,
|
||||||
InvalidPathError = 402,
|
InvalidPathError = 402,
|
||||||
|
|
|
||||||
|
|
@ -30,24 +30,24 @@ public:
|
||||||
NoOptions = 0x0,
|
NoOptions = 0x0,
|
||||||
Passive = 0x01,
|
Passive = 0x01,
|
||||||
Durable = 0x02,
|
Durable = 0x02,
|
||||||
Exclusive = 0x4,
|
Exclusive = 0x04,
|
||||||
AutoDelete = 0x8,
|
AutoDelete = 0x08,
|
||||||
NoWait = 0x10
|
NoWait = 0x10
|
||||||
};
|
};
|
||||||
Q_DECLARE_FLAGS(QueueOptions, QueueOption)
|
Q_DECLARE_FLAGS(QueueOptions, QueueOption)
|
||||||
int options() const;
|
int options() const;
|
||||||
|
|
||||||
enum ConsumeOption {
|
enum ConsumeOption {
|
||||||
coNoLocal = 0x1,
|
coNoLocal = 0x01,
|
||||||
coNoAck = 0x02,
|
coNoAck = 0x02,
|
||||||
coExclusive = 0x04,
|
coExclusive = 0x04,
|
||||||
coNoWait = 0x8
|
coNoWait = 0x08
|
||||||
};
|
};
|
||||||
Q_DECLARE_FLAGS(ConsumeOptions, ConsumeOption)
|
Q_DECLARE_FLAGS(ConsumeOptions, ConsumeOption)
|
||||||
|
|
||||||
enum RemoveOption {
|
enum RemoveOption {
|
||||||
roForce = 0x0,
|
roForce = 0x0,
|
||||||
roIfUnused = 0x1,
|
roIfUnused = 0x01,
|
||||||
roIfEmpty = 0x02,
|
roIfEmpty = 0x02,
|
||||||
roNoWait = 0x04
|
roNoWait = 0x04
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -22,6 +22,7 @@ private Q_SLOTS:
|
||||||
void invalidDeclaration();
|
void invalidDeclaration();
|
||||||
void invalidRedeclaration();
|
void invalidRedeclaration();
|
||||||
void removeIfUnused();
|
void removeIfUnused();
|
||||||
|
void invalidMandatoryRouting();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
QScopedPointer<Client> client;
|
QScopedPointer<Client> client;
|
||||||
|
|
@ -140,5 +141,13 @@ void tst_QAMQPExchange::removeIfUnused()
|
||||||
QVERIFY(waitForSignal(queue, SIGNAL(removed())));
|
QVERIFY(waitForSignal(queue, SIGNAL(removed())));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void tst_QAMQPExchange::invalidMandatoryRouting()
|
||||||
|
{
|
||||||
|
Exchange *defaultExchange = client->createExchange();
|
||||||
|
defaultExchange->publish("some message", "unroutable-key", MessageProperties(), Exchange::poMandatory);
|
||||||
|
QVERIFY(waitForSignal(defaultExchange, SIGNAL(error(QAMQP::Error))));
|
||||||
|
QCOMPARE(defaultExchange->error(), QAMQP::UnroutableKey);
|
||||||
|
}
|
||||||
|
|
||||||
QTEST_MAIN(tst_QAMQPExchange)
|
QTEST_MAIN(tst_QAMQPExchange)
|
||||||
#include "tst_qamqpexchange.moc"
|
#include "tst_qamqpexchange.moc"
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue