diff options
author | Alexei Rousskikh <ext-alexei.rousskikh@nokia.com> | 2012-02-17 16:14:11 -0500 |
---|---|---|
committer | Andrew Christian <andrew.christian@nokia.com> | 2012-02-21 18:05:20 +0100 |
commit | d3314a364be2e46190ecf93dfeb44484d55d6fc1 (patch) | |
tree | 17bafb41b1f18b22222e92cb1199183a78f68b72 | |
parent | 7073c61891b6b0bb92aea512692a7686568656f4 (diff) |
better error handling while loading of schemas
Change-Id: I1233adc436c4def39b3a4ff76c35bd2cbb6caf7e
Reviewed-by: Andrew Christian <andrew.christian@nokia.com>
-rw-r--r-- | src/qtjsonschema/schemaerror.cpp | 48 | ||||
-rw-r--r-- | src/qtjsonschema/schemaerror.h | 12 | ||||
-rw-r--r-- | src/qtjsonschema/schemavalidator.cpp | 49 | ||||
-rw-r--r-- | tests/auto/jsonschema/tst_jsonschema.cpp | 5 |
4 files changed, 100 insertions, 14 deletions
diff --git a/src/qtjsonschema/schemaerror.cpp b/src/qtjsonschema/schemaerror.cpp index 4d8fc67..1e134eb 100644 --- a/src/qtjsonschema/schemaerror.cpp +++ b/src/qtjsonschema/schemaerror.cpp @@ -41,10 +41,15 @@ #include "schemaerror.h" +#include <QStringList> + QT_BEGIN_NAMESPACE_JSONSTREAM -const QString SchemaError::kCodeStr = QString::fromLatin1("code"); -const QString SchemaError::kMessageStr = QString::fromLatin1("message"); +const QString SchemaError::kCodeStr = QString::fromLatin1("::code"); +const QString SchemaError::kMessageStr = QString::fromLatin1("::message"); +const QString SchemaError::kSourceStr = QString::fromLatin1("::source"); +const QString SchemaError::kCounterStr = QString::fromLatin1("::count"); +const QString SchemaError::kErrorPrefixStr = QString::fromLatin1("::"); /*! \class SchemaError @@ -61,6 +66,12 @@ const QString SchemaError::kMessageStr = QString::fromLatin1("message"); Error somewhere in the schema itself? \value InvalidObject Unable to parse an incoming object + \value FailedSchemaFileOpenRead + Schema file could not be opened or read from + \value InvalidSchemaFolder + Schema folder does not exist + \value InvalidSchemaLoading + Schema loading errors */ /*! @@ -68,8 +79,8 @@ const QString SchemaError::kMessageStr = QString::fromLatin1("message"); */ SchemaError::SchemaError(ErrorCode code, const QString & message) { - m_data.insert("code", code); - m_data.insert("message", message); + m_data.insert(kCodeStr, code); + m_data.insert(kMessageStr, message); } /*! @@ -77,7 +88,7 @@ SchemaError::SchemaError(ErrorCode code, const QString & message) */ SchemaError::ErrorCode SchemaError::errorCode() const { - return m_data.isEmpty() ? SchemaError::NoError : (SchemaError::ErrorCode)(m_data.value("code").toDouble()); + return m_data.isEmpty() ? SchemaError::NoError : (SchemaError::ErrorCode)(m_data.value(kCodeStr).toDouble()); } /*! @@ -85,7 +96,32 @@ SchemaError::ErrorCode SchemaError::errorCode() const */ QString SchemaError::errorString() const { - return m_data.isEmpty() ? QString() : m_data.value("message").toString(); + return m_data.isEmpty() ? QString() : m_data.value(kMessageStr).toString(); +} + +/*! + Returns a source of the last schema error. +*/ +QString SchemaError::errorSource() const +{ + return m_data.isEmpty() ? QString() : m_data.value(kSourceStr).toString(); +} + +/*! + Returns a list of sub errors. +*/ +QList<SchemaError> SchemaError::subErrors() const +{ + QList<SchemaError> errors; + foreach (QString key, m_data.keys()) { + if (!key.startsWith(kErrorPrefixStr)) { + QJsonObject object(m_data[key].toObject()); + if (object.contains(kCodeStr)) + errors.append(SchemaError(object)); + } + } + + return errors; } QT_END_NAMESPACE_JSONSTREAM diff --git a/src/qtjsonschema/schemaerror.h b/src/qtjsonschema/schemaerror.h index 2afadf6..71f1304 100644 --- a/src/qtjsonschema/schemaerror.h +++ b/src/qtjsonschema/schemaerror.h @@ -45,6 +45,7 @@ #include "jsonschema-global.h" #include <QJsonObject> +#include <QList> QT_BEGIN_NAMESPACE_JSONSTREAM @@ -55,7 +56,10 @@ public: NoError = 0, FailedSchemaValidation, // Invalid according to the schema InvalidSchemaOperation, - InvalidObject // Unable to parse an incoming object + InvalidObject, // Unable to parse an incoming object + FailedSchemaFileOpenRead, // Schema file could not be opened or read from + InvalidSchemaFolder, // Schema folder does not exist + InvalidSchemaLoading // Schema loading errors }; SchemaError() {} @@ -64,11 +68,17 @@ public: ErrorCode errorCode() const; QString errorString() const; + QString errorSource() const; + + QList<SchemaError> subErrors() const; QJsonObject object() const { return m_data; } static const QString kCodeStr; static const QString kMessageStr; + static const QString kSourceStr; + static const QString kCounterStr; + static const QString kErrorPrefixStr; private: QJsonObject m_data; diff --git a/src/qtjsonschema/schemavalidator.cpp b/src/qtjsonschema/schemavalidator.cpp index a4ea641..3c2b14b 100644 --- a/src/qtjsonschema/schemavalidator.cpp +++ b/src/qtjsonschema/schemavalidator.cpp @@ -243,6 +243,7 @@ QJsonObject SchemaValidator::_loadFromFolder(const QString & path, const QString { SchemaNameInitialization type(schemaNameProperty.isEmpty() ? UseFilename : UseProperty); QString name(UseProperty == type ? schemaNameProperty : QString::null); + int nLoaded = 0; // create a filter if required QStringList exts; @@ -263,8 +264,37 @@ QJsonObject SchemaValidator::_loadFromFolder(const QString & path, const QString { ret.insert(filename, ret0); } + else + { + nLoaded++; + } } + + // check result for errors + if (!ret.isEmpty()) // loading errors + { + int nFailed = ret.count(); + ret.insert(SchemaError::kCodeStr, SchemaError::InvalidSchemaLoading); + ret.insert(SchemaError::kMessageStr, QString("Loading failed for %1 schemas. %2 schemas are loaded successfully.").arg(nFailed).arg(nLoaded)); + + if (nLoaded) + ret.insert(SchemaError::kCounterStr, nLoaded); + } + else if (!nLoaded) // no schemas were found + { + ret = makeError(SchemaError::InvalidSchemaLoading, + QString("Folder '%1' does not contain any schema.").arg(dir.path())); + } + } + else + { + ret = makeError(SchemaError::InvalidSchemaFolder, + QString("Folder '%1' does not exist.").arg(dir.path())); } + + if (!ret.isEmpty()) + ret.insert(SchemaError::kSourceStr, dir.path()); + return ret; } @@ -278,10 +308,10 @@ QJsonObject SchemaValidator::_loadFromFile(const QString &filename, SchemaNameIn QJsonObject ret; if (!filename.isEmpty()) { + QByteArray json; QFile schemaFile(QFile::exists(filename) ? filename : QDir::currentPath() + QDir::separator() + filename); - if (schemaFile.open(QIODevice::ReadOnly)) + if (schemaFile.open(QIODevice::ReadOnly) && !(json = schemaFile.readAll()).isEmpty()) { - QByteArray json = schemaFile.readAll(); schemaFile.close(); QString name(shemaName); @@ -294,9 +324,18 @@ QJsonObject SchemaValidator::_loadFromFile(const QString &filename, SchemaNameIn ret = _loadFromData(json, name, type); } else - { - // file open error + { // file open error + ret = makeError(SchemaError::FailedSchemaFileOpenRead, + QString("Can't open/read '%1' schema file.").arg(schemaFile.fileName())); } + + if (!ret.isEmpty()) + ret.insert(SchemaError::kSourceStr, schemaFile.fileName()); + } + else + { + ret = makeError(SchemaError::FailedSchemaFileOpenRead, + "Filename is empty"); } return ret; } @@ -314,7 +353,7 @@ QJsonObject SchemaValidator::_loadFromData(const QByteArray & json, const QStrin //qDebug() << "shemaName " << name << " type= " << type; //qDebug() << "schemaBody " << schemaObject; - if (doc.isNull()) + if (doc.isNull() || schemaObject.isEmpty()) { return makeError(SchemaError::InvalidObject, "schema data is invalid"); diff --git a/tests/auto/jsonschema/tst_jsonschema.cpp b/tests/auto/jsonschema/tst_jsonschema.cpp index fc493f8..10eefa1 100644 --- a/tests/auto/jsonschema/tst_jsonschema.cpp +++ b/tests/auto/jsonschema/tst_jsonschema.cpp @@ -210,8 +210,9 @@ void tst_JsonSchema::testItemsValidation() array.removeAt(0); // [2] QVERIFY(!validate(array, "{ \"type\" : \"array\", \"items\" : { \"type\" : \"string\" } }")); // INVALID - array[0] = QLatin1String("foo"); - array[1] = QLatin1String("two"); //["foo", "two"] + array = QJsonArray(); + array.append(QLatin1String("foo")); + array.append(QLatin1String("two")); //["foo", "two"] // should fail!!!!! //fix QVERIFY(!validate(array, "{ \"type\" : \"array\", \"items\" : [{ \"type\" : \"string\" }, { \"type\" : \"number\" }] }")); } |