QCborValue: refactor extended types so isTag() is true
This makes QCborValue more future compatible, as code written today for tags that QCborValue does not recognize will continue to work if QCborValue gains support for it in the future. This change also obviates the need for reinterpretAsTag(), which I had not written unit tests for as I knew this change was coming. Change-Id: I052407b777ec43f78378fffd15302bdc34f66755 Reviewed-by: Simon Hausmann <simon.hausmann@qt.io> Reviewed-by: Edward Welbourne <edward.welbourne@qt.io>
This commit is contained in:
parent
22c1a46a03
commit
340472534c
@ -543,12 +543,12 @@ QT_BEGIN_NAMESPACE
|
|||||||
Returns true if this QCborValue is of the tag type. The tag value can be
|
Returns true if this QCborValue is of the tag type. The tag value can be
|
||||||
retrieved using tag() and the tagged value using taggedValue().
|
retrieved using tag() and the tagged value using taggedValue().
|
||||||
|
|
||||||
This function does not return true for extended types that the API
|
This function also returns true for extended types that the API
|
||||||
recognizes. For code that handles extended types directly before the Qt API
|
recognizes. For code that handles extended types directly before the Qt API
|
||||||
is updated to support them, it is possible to recreate the tag + tagged
|
is updated to support them, it is possible to recreate the tag + tagged
|
||||||
value pair by using reinterpretAsTag().
|
value pair by using taggedValue().
|
||||||
|
|
||||||
\sa type(), tag(), taggedValue(), reinterpretAsTag()
|
\sa type(), tag(), taggedValue(), taggedValue()
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
@ -862,7 +862,7 @@ static void writeDoubleToCbor(QCborStreamWriter &writer, double d, QCborValue::E
|
|||||||
static inline int typeOrder(Element e1, Element e2)
|
static inline int typeOrder(Element e1, Element e2)
|
||||||
{
|
{
|
||||||
auto comparable = [](Element e) {
|
auto comparable = [](Element e) {
|
||||||
if (e.type >= 0x10000)
|
if (e.type >= 0x10000) // see QCborValue::isTag_helper()
|
||||||
return QCborValue::Tag;
|
return QCborValue::Tag;
|
||||||
return e.type;
|
return e.type;
|
||||||
};
|
};
|
||||||
@ -976,17 +976,6 @@ QString DiagnosticNotation::createFromValue(const QCborValue &v)
|
|||||||
return QLatin1Char('[') + createFromArray(v.toArray()) + indent + QLatin1Char(']');
|
return QLatin1Char('[') + createFromArray(v.toArray()) + indent + QLatin1Char(']');
|
||||||
case QCborValue::Map:
|
case QCborValue::Map:
|
||||||
return QLatin1Char('{') + createFromMap(v.toMap()) + indent + QLatin1Char('}');
|
return QLatin1Char('{') + createFromMap(v.toMap()) + indent + QLatin1Char('}');
|
||||||
case QCborValue::Tag: {
|
|
||||||
bool byteArrayFormat = opts & QCborValue::ExtendedFormat && isByteArrayEncodingTag(v.tag());
|
|
||||||
if (byteArrayFormat)
|
|
||||||
byteArrayFormatStack.push(int(v.tag()));
|
|
||||||
QString result = QString::fromLatin1("%1(%2)").arg(quint64(v.tag())).arg(createFromValue(v.taggedValue()));
|
|
||||||
if (byteArrayFormat)
|
|
||||||
byteArrayFormatStack.pop();
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
case QCborValue::SimpleType:
|
|
||||||
break;
|
|
||||||
case QCborValue::False:
|
case QCborValue::False:
|
||||||
return QStringLiteral("false");
|
return QStringLiteral("false");
|
||||||
case QCborValue::True:
|
case QCborValue::True:
|
||||||
@ -997,13 +986,23 @@ QString DiagnosticNotation::createFromValue(const QCborValue &v)
|
|||||||
return QStringLiteral("undefined");
|
return QStringLiteral("undefined");
|
||||||
case QCborValue::Double:
|
case QCborValue::Double:
|
||||||
return makeFpString(v.toDouble());
|
return makeFpString(v.toDouble());
|
||||||
case QCborValue::DateTime:
|
|
||||||
case QCborValue::Url:
|
|
||||||
case QCborValue::RegularExpression:
|
|
||||||
case QCborValue::Uuid:
|
|
||||||
return createFromValue(v.reinterpretAsTag());
|
|
||||||
case QCborValue::Invalid:
|
case QCborValue::Invalid:
|
||||||
return QStringLiteral("<invalid>");
|
return QStringLiteral("<invalid>");
|
||||||
|
|
||||||
|
case QCborValue::Tag:
|
||||||
|
case QCborValue::SimpleType:
|
||||||
|
default: // tags and other simple types that are recognized
|
||||||
|
break; // are all handled below
|
||||||
|
}
|
||||||
|
|
||||||
|
if (v.isTag()) {
|
||||||
|
bool byteArrayFormat = opts & QCborValue::ExtendedFormat && isByteArrayEncodingTag(v.tag());
|
||||||
|
if (byteArrayFormat)
|
||||||
|
byteArrayFormatStack.push(int(v.tag()));
|
||||||
|
QString result = QString::fromLatin1("%1(%2)").arg(quint64(v.tag())).arg(createFromValue(v.taggedValue()));
|
||||||
|
if (byteArrayFormat)
|
||||||
|
byteArrayFormatStack.pop();
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
// must be a simple type
|
// must be a simple type
|
||||||
@ -1912,7 +1911,7 @@ QCborValue::QCborValue(const QCborValue &other)
|
|||||||
\l{QCborKnownTags}{UnixTime_t}. When parsing CBOR streams, QCborValue will
|
\l{QCborKnownTags}{UnixTime_t}. When parsing CBOR streams, QCborValue will
|
||||||
convert \l{QCborKnownTags}{UnixTime_t} to the string-based type.
|
convert \l{QCborKnownTags}{UnixTime_t} to the string-based type.
|
||||||
|
|
||||||
\sa toDateTime(), isDateTime(), reinterpretAsTag()
|
\sa toDateTime(), isDateTime(), taggedValue()
|
||||||
*/
|
*/
|
||||||
QCborValue::QCborValue(const QDateTime &dt)
|
QCborValue::QCborValue(const QDateTime &dt)
|
||||||
: QCborValue(QCborKnownTags::DateTimeString, dt.toString(Qt::ISODateWithMs).toLatin1())
|
: QCborValue(QCborKnownTags::DateTimeString, dt.toString(Qt::ISODateWithMs).toLatin1())
|
||||||
@ -1929,7 +1928,7 @@ QCborValue::QCborValue(const QDateTime &dt)
|
|||||||
The CBOR URL type is an extended type represented by a string tagged as an
|
The CBOR URL type is an extended type represented by a string tagged as an
|
||||||
\l{QCborKnownTags}{Url}.
|
\l{QCborKnownTags}{Url}.
|
||||||
|
|
||||||
\sa toUrl(), isUrl(), reinterpretAsTag()
|
\sa toUrl(), isUrl(), taggedValue()
|
||||||
*/
|
*/
|
||||||
QCborValue::QCborValue(const QUrl &url)
|
QCborValue::QCborValue(const QUrl &url)
|
||||||
: QCborValue(QCborKnownTags::Url, url.toString(QUrl::DecodeReserved).toUtf8())
|
: QCborValue(QCborKnownTags::Url, url.toString(QUrl::DecodeReserved).toUtf8())
|
||||||
@ -1949,7 +1948,7 @@ QCborValue::QCborValue(const QUrl &url)
|
|||||||
regular expressions only store the patterns, so any flags that the
|
regular expressions only store the patterns, so any flags that the
|
||||||
QRegularExpression object may carry will be lost.
|
QRegularExpression object may carry will be lost.
|
||||||
|
|
||||||
\sa toRegularExpression(), isRegularExpression(), reinterpretAsTag()
|
\sa toRegularExpression(), isRegularExpression(), taggedValue()
|
||||||
*/
|
*/
|
||||||
QCborValue::QCborValue(const QRegularExpression &rx)
|
QCborValue::QCborValue(const QRegularExpression &rx)
|
||||||
: QCborValue(QCborKnownTags::RegularExpression, rx.pattern())
|
: QCborValue(QCborKnownTags::RegularExpression, rx.pattern())
|
||||||
@ -1966,7 +1965,7 @@ QCborValue::QCborValue(const QRegularExpression &rx)
|
|||||||
The CBOR UUID type is an extended type represented by a byte array tagged
|
The CBOR UUID type is an extended type represented by a byte array tagged
|
||||||
as an \l{QCborKnownTags}{Uuid}.
|
as an \l{QCborKnownTags}{Uuid}.
|
||||||
|
|
||||||
\sa toUuid(), isUuid(), reinterpretAsTag()
|
\sa toUuid(), isUuid(), taggedValue()
|
||||||
*/
|
*/
|
||||||
QCborValue::QCborValue(const QUuid &uuid)
|
QCborValue::QCborValue(const QUuid &uuid)
|
||||||
: QCborValue(QCborKnownTags::Uuid, uuid.toRfc4122())
|
: QCborValue(QCborKnownTags::Uuid, uuid.toRfc4122())
|
||||||
@ -2005,12 +2004,7 @@ QCborValue &QCborValue::operator=(const QCborValue &other)
|
|||||||
stored representation. This function returns that number. To retrieve the
|
stored representation. This function returns that number. To retrieve the
|
||||||
representation, use taggedValue().
|
representation, use taggedValue().
|
||||||
|
|
||||||
This function does not directly return the tag associated with extended
|
\sa isTag(), taggedValue(), isDateTime(), isUrl(), isRegularExpression(), isUuid()
|
||||||
types. In order to do that, first convert the extended type to tag type
|
|
||||||
using reinterpretAsTag().
|
|
||||||
|
|
||||||
\sa isTag(), taggedValue(), reinterpretAsTag(),
|
|
||||||
isDateTime(), isUrl(), isRegularExpression(), isUuid()
|
|
||||||
*/
|
*/
|
||||||
QCborTag QCborValue::tag(QCborTag defaultValue) const
|
QCborTag QCborValue::tag(QCborTag defaultValue) const
|
||||||
{
|
{
|
||||||
@ -2026,12 +2020,7 @@ QCborTag QCborValue::tag(QCborTag defaultValue) const
|
|||||||
stored representation. This function returns that representation. To
|
stored representation. This function returns that representation. To
|
||||||
retrieve the tag, use tag().
|
retrieve the tag, use tag().
|
||||||
|
|
||||||
This function does not directly return the representation associated with
|
\sa isTag(), tag(), isDateTime(), isUrl(), isRegularExpression(), isUuid()
|
||||||
extended types. In order to do that, first convert the extended type to tag
|
|
||||||
type using reinterpretAsTag().
|
|
||||||
|
|
||||||
\sa isTag(), tag(), reinterpretAsTag(),
|
|
||||||
isDateTime(), isUrl(), isRegularExpression(), isUuid()
|
|
||||||
*/
|
*/
|
||||||
QCborValue QCborValue::taggedValue(const QCborValue &defaultValue) const
|
QCborValue QCborValue::taggedValue(const QCborValue &defaultValue) const
|
||||||
{
|
{
|
||||||
@ -2039,24 +2028,6 @@ QCborValue QCborValue::taggedValue(const QCborValue &defaultValue) const
|
|||||||
container->valueAt(1) : defaultValue;
|
container->valueAt(1) : defaultValue;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*!
|
|
||||||
Returns the equivalent representation of a QCborValue extended type, in the
|
|
||||||
form of a tag object. If this object is not an extended type, this function
|
|
||||||
returns an invalid QCborValue object (not undefined).
|
|
||||||
|
|
||||||
\sa isTag(), tag(), taggedValue(), isInvalid(),
|
|
||||||
isDateTime(), isUrl(), isRegularExpression(), isUuid()
|
|
||||||
*/
|
|
||||||
QCborValue QCborValue::reinterpretAsTag() const
|
|
||||||
{
|
|
||||||
QCborValue result = *this;
|
|
||||||
if (t >= 0x10000)
|
|
||||||
result.t = Tag;
|
|
||||||
else
|
|
||||||
result.t = Invalid;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
Returns the byte array value stored in this QCborValue, if it is of the byte
|
Returns the byte array value stored in this QCborValue, if it is of the byte
|
||||||
array type. Otherwise, it returns \a defaultValue.
|
array type. Otherwise, it returns \a defaultValue.
|
||||||
|
@ -192,7 +192,7 @@ public:
|
|||||||
bool isString() const { return type() == String; }
|
bool isString() const { return type() == String; }
|
||||||
bool isArray() const { return type() == Array; }
|
bool isArray() const { return type() == Array; }
|
||||||
bool isMap() const { return type() == Map; }
|
bool isMap() const { return type() == Map; }
|
||||||
bool isTag() const { return type() == Tag; }
|
bool isTag() const { return isTag_helper(type()); }
|
||||||
bool isFalse() const { return type() == False; }
|
bool isFalse() const { return type() == False; }
|
||||||
bool isTrue() const { return type() == True; }
|
bool isTrue() const { return type() == True; }
|
||||||
bool isBool() const { return isFalse() || isTrue(); }
|
bool isBool() const { return isFalse() || isTrue(); }
|
||||||
@ -228,7 +228,6 @@ public:
|
|||||||
|
|
||||||
QCborTag tag(QCborTag defaultValue = QCborTag(-1)) const;
|
QCborTag tag(QCborTag defaultValue = QCborTag(-1)) const;
|
||||||
QCborValue taggedValue(const QCborValue &defaultValue = QCborValue()) const;
|
QCborValue taggedValue(const QCborValue &defaultValue = QCborValue()) const;
|
||||||
QCborValue reinterpretAsTag() const;
|
|
||||||
|
|
||||||
QByteArray toByteArray(const QByteArray &defaultValue = {}) const;
|
QByteArray toByteArray(const QByteArray &defaultValue = {}) const;
|
||||||
QString toString(const QString &defaultValue = {}) const;
|
QString toString(const QString &defaultValue = {}) const;
|
||||||
@ -311,6 +310,11 @@ private:
|
|||||||
{
|
{
|
||||||
return Type(quint8(st) | SimpleType);
|
return Type(quint8(st) | SimpleType);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Q_DECL_CONSTEXPR static bool isTag_helper(Type t)
|
||||||
|
{
|
||||||
|
return t == Tag || t >= 0x10000;
|
||||||
|
}
|
||||||
};
|
};
|
||||||
Q_DECLARE_SHARED(QCborValue)
|
Q_DECLARE_SHARED(QCborValue)
|
||||||
|
|
||||||
@ -328,7 +332,7 @@ public:
|
|||||||
bool isString() const { return type() == QCborValue::String; }
|
bool isString() const { return type() == QCborValue::String; }
|
||||||
bool isArray() const { return type() == QCborValue::Array; }
|
bool isArray() const { return type() == QCborValue::Array; }
|
||||||
bool isMap() const { return type() == QCborValue::Map; }
|
bool isMap() const { return type() == QCborValue::Map; }
|
||||||
bool isTag() const { return type() == QCborValue::Tag; }
|
bool isTag() const { return QCborValue::isTag_helper(type()); }
|
||||||
bool isFalse() const { return type() == QCborValue::False; }
|
bool isFalse() const { return type() == QCborValue::False; }
|
||||||
bool isTrue() const { return type() == QCborValue::True; }
|
bool isTrue() const { return type() == QCborValue::True; }
|
||||||
bool isBool() const { return isFalse() || isTrue(); }
|
bool isBool() const { return isFalse() || isTrue(); }
|
||||||
|
@ -308,12 +308,13 @@ void tst_QCborValue::extendedTypes()
|
|||||||
{
|
{
|
||||||
QFETCH(QCborValue, extended);
|
QFETCH(QCborValue, extended);
|
||||||
QFETCH(QCborValue, tagged);
|
QFETCH(QCborValue, tagged);
|
||||||
QVERIFY(!extended.isTag());
|
QVERIFY(extended.isTag());
|
||||||
QVERIFY(tagged.isTag());
|
QVERIFY(tagged.isTag());
|
||||||
|
|
||||||
// despite that, they actually compare equal
|
|
||||||
QVERIFY(extended == tagged);
|
QVERIFY(extended == tagged);
|
||||||
QVERIFY(tagged == extended);
|
QVERIFY(tagged == extended);
|
||||||
|
|
||||||
|
QCOMPARE(extended.tag(), tagged.tag());
|
||||||
|
QCOMPARE(extended.taggedValue(), tagged.taggedValue());
|
||||||
}
|
}
|
||||||
|
|
||||||
void tst_QCborValue::copyCompare()
|
void tst_QCborValue::copyCompare()
|
||||||
|
Loading…
Reference in New Issue
Block a user