mirror of
https://github.com/QuasarApp/Heart.git
synced 2025-04-28 18:54:37 +00:00
new conditions of database objects
This commit is contained in:
parent
d929ce8399
commit
e923fbb10d
@ -221,25 +221,35 @@ void AbstractNodeInfo::reset() {
|
||||
setTrust(static_cast<int>(TrustNode::Default));
|
||||
setStatus(NodeCoonectionStatus::NotConnected);
|
||||
setIsLocal(false);
|
||||
|
||||
QMutexLocker lock(&_parsersListMutex);
|
||||
_parsersMap.clear();
|
||||
|
||||
}
|
||||
|
||||
QSharedPointer<QH::iParser> AbstractNodeInfo::getParser(unsigned short cmd) {
|
||||
QMutexLocker lock(&_parsersListMutex);
|
||||
|
||||
return _parsersMap.value(cmd, nullptr);
|
||||
}
|
||||
|
||||
QSharedPointer<iParser> AbstractNodeInfo::getParser(const QString &type) {
|
||||
QMutexLocker lock(&_parsersListMutex);
|
||||
|
||||
return _parsersKeysMap.value(type, nullptr);
|
||||
}
|
||||
|
||||
void QH::AbstractNodeInfo::addParser(unsigned short cmd,
|
||||
QSharedPointer<QH::iParser> parser) {
|
||||
QMutexLocker lock(&_parsersListMutex);
|
||||
|
||||
_parsersMap[cmd] = parser;
|
||||
_parsersKeysMap[parser->parserId()] = parser;
|
||||
}
|
||||
|
||||
void AbstractNodeInfo::addParser(QSharedPointer<iParser> parser) {
|
||||
QMutexLocker lock(&_parsersListMutex);
|
||||
|
||||
_parsersKeysMap[parser->parserId()] = parser;
|
||||
}
|
||||
|
||||
|
@ -12,6 +12,7 @@
|
||||
#include "distversion.h"
|
||||
#include "heart_global.h"
|
||||
#include "iparser.h"
|
||||
#include <QMutex>
|
||||
#include <hostaddress.h>
|
||||
|
||||
|
||||
@ -332,6 +333,7 @@ private:
|
||||
|
||||
QHash<unsigned short, QSharedPointer<iParser>> _parsersMap;
|
||||
QHash<QString, QSharedPointer<iParser>> _parsersKeysMap;
|
||||
QMutex _parsersListMutex;
|
||||
|
||||
VersionData _version;
|
||||
bool _fVersionReceived = false;
|
||||
|
@ -30,11 +30,27 @@ DBObject::~DBObject() {
|
||||
PrepareResult DBObject::prepareSelectQuery(QSqlQuery &q) const {
|
||||
|
||||
auto map = variantMap().keys();
|
||||
|
||||
QString queryString = "SELECT " + map.join(",") + " FROM %0 " + getWhereBlock();
|
||||
|
||||
QString queryString = "SELECT " + map.join(",") + " FROM %0 ";
|
||||
queryString = queryString.arg(table());
|
||||
|
||||
|
||||
auto [conditionQueryString, conditionBindingMap] = condition();
|
||||
|
||||
if (conditionQueryString.size()) {
|
||||
|
||||
queryString += " WHERE " + conditionQueryString;
|
||||
if (!q.prepare(queryString)) {
|
||||
return PrepareResult::Fail;
|
||||
}
|
||||
|
||||
for (auto it = conditionBindingMap.begin(); it != conditionBindingMap.end(); ++it) {
|
||||
q.bindValue(it.key(), it.value());
|
||||
}
|
||||
|
||||
return PrepareResult::Success;
|
||||
}
|
||||
|
||||
|
||||
if (!q.prepare(queryString)) {
|
||||
return PrepareResult::Fail;
|
||||
}
|
||||
@ -107,7 +123,15 @@ PrepareResult DBObject::prepareUpdateQuery(QSqlQuery &q) const {
|
||||
return PrepareResult::Fail;
|
||||
}
|
||||
|
||||
QString queryString = "UPDATE %0 SET %1 WHERE " + condition();
|
||||
auto [conditionQueryString, conditionBindingMap] = condition();
|
||||
|
||||
if (conditionQueryString.isEmpty()) {
|
||||
QuasarAppUtils::Params::log("The object soue not have condition for update object.",
|
||||
QuasarAppUtils::Error);
|
||||
return PrepareResult::Fail;
|
||||
}
|
||||
|
||||
QString queryString = "UPDATE %0 SET %1 WHERE " + conditionQueryString;
|
||||
|
||||
queryString = queryString.arg(table());
|
||||
QString tableUpdateValues = "";
|
||||
@ -144,6 +168,21 @@ PrepareResult DBObject::prepareUpdateQuery(QSqlQuery &q) const {
|
||||
q.bindValue(":" + it.key(), it.value().value);
|
||||
}
|
||||
|
||||
for (auto it = conditionBindingMap.begin(); it != conditionBindingMap.end(); ++it) {
|
||||
#ifdef QT_DEBUG
|
||||
if (bool(map.value(it.key()).type & MemberType::Update)) {
|
||||
QuasarAppUtils::Params::log(QString("Bad object configuration: "
|
||||
"The %0 field using in the condition and has MemberType::Update configuration."
|
||||
" All condition fields should not use the MemberType::Update. \n %1").
|
||||
arg(it.key(), toString()),
|
||||
QuasarAppUtils::Warning);
|
||||
}
|
||||
#endif
|
||||
q.bindValue(it.key(), it.value());
|
||||
}
|
||||
|
||||
|
||||
|
||||
return PrepareResult::Success;
|
||||
}
|
||||
|
||||
@ -162,72 +201,30 @@ bool DBObject::isBundle() const {
|
||||
return false;
|
||||
}
|
||||
|
||||
QString DBObject::condition() const {
|
||||
|
||||
// prepare key value to string condition
|
||||
auto prepareCondition = [](const QString& key, const QString &val){
|
||||
return key + "= '" + val + "'";
|
||||
};
|
||||
|
||||
auto byteArrayWarning = [](){
|
||||
QuasarAppUtils::Params::log("You try generate a condition from the raw bytes array."
|
||||
" This operation can not be brok the sql request."
|
||||
" Use the QString or int type for values of condition."
|
||||
" If you want to bytes array in condition then override the DBObject::condition method.",
|
||||
QuasarAppUtils::Warning);
|
||||
};
|
||||
|
||||
QString errorString = "WRONG OBJECT";
|
||||
std::pair<QString, QMap<QString, QVariant>> DBObject::condition() const {
|
||||
|
||||
// if object have a primaryKey then return primary key
|
||||
auto primaryVal = primaryValue();
|
||||
if (primaryVal.size()) {
|
||||
return prepareCondition(primaryKey(), primaryVal);
|
||||
if (!primaryVal.isNull()) {
|
||||
return {QString("%0 = :%0").arg(primaryKey()),
|
||||
{{QString(":%0").arg(primaryKey()), {primaryVal}}}};
|
||||
}
|
||||
|
||||
auto map = variantMap();
|
||||
|
||||
// check all objects fields
|
||||
for (auto it = map.begin(); it != map.end(); ++it) {
|
||||
// if field is unique then
|
||||
if (bool(it.value().type & MemberType::Unique)) {
|
||||
#if QT_VERSION < QT_VERSION_CHECK(6, 0, 0)
|
||||
|
||||
QVariant::Type type = it.value().value.type();
|
||||
|
||||
bool typeisString = type == QVariant::String;
|
||||
bool typeisArray = type == QVariant::ByteArray;
|
||||
|
||||
#else
|
||||
|
||||
int type = it.value().value.metaType().id();
|
||||
|
||||
bool typeisString = type == QMetaType::QString;
|
||||
bool typeisArray = type == QMetaType::QByteArray;
|
||||
|
||||
#endif
|
||||
|
||||
// if field is string then check size.
|
||||
if (typeisString) {
|
||||
QString val = it.value().value.toString();
|
||||
if (val.size()) {
|
||||
return prepareCondition(it.key(), val);
|
||||
}
|
||||
} else if (typeisArray) {
|
||||
byteArrayWarning();
|
||||
continue;
|
||||
} else if (it.value().value.isValid()) {
|
||||
return prepareCondition(it.key(), it.value().value.toString());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
QuasarAppUtils::Params::log("Fail to generate condition for object: " + toString() +
|
||||
". Object do not have valid unique fields or valid database address.",
|
||||
QuasarAppUtils::Error);
|
||||
|
||||
|
||||
return errorString;
|
||||
return {};
|
||||
}
|
||||
|
||||
QString DBObject::primaryKey() const {
|
||||
return "";
|
||||
}
|
||||
|
||||
QVariant DBObject::primaryValue() const {
|
||||
return {};
|
||||
}
|
||||
|
||||
bool DBObject::isInsertPrimaryKey() const {
|
||||
@ -243,17 +240,6 @@ QString DBObject::toString() const {
|
||||
QString(" %0").arg(dbAddress().toString());
|
||||
}
|
||||
|
||||
QString DBObject::getWhereBlock() const {
|
||||
auto con = condition();
|
||||
|
||||
if (!con.size())
|
||||
return "";
|
||||
|
||||
QString whereBlock = "WHERE " + con;
|
||||
|
||||
return whereBlock;
|
||||
}
|
||||
|
||||
QDataStream &DBObject::fromStream(QDataStream &stream) {
|
||||
QuasarAppUtils::Params::log("This object not support stream operator."
|
||||
" Please Override the fromStream method for this object. " + toString(),
|
||||
@ -272,17 +258,31 @@ QDataStream &DBObject::toStream(QDataStream &stream) const {
|
||||
|
||||
PrepareResult DBObject::prepareRemoveQuery(QSqlQuery &q) const {
|
||||
|
||||
QString queryString = "DELETE FROM %0 " + getWhereBlock();
|
||||
|
||||
QString queryString = "DELETE FROM %0 ";
|
||||
queryString = queryString.arg(table());
|
||||
|
||||
auto [conditionQueryString, conditionBindingMap] = condition();
|
||||
|
||||
if (conditionQueryString.size()) {
|
||||
|
||||
queryString += " WHERE " + conditionQueryString;
|
||||
if (!q.prepare(queryString)) {
|
||||
return PrepareResult::Fail;
|
||||
}
|
||||
|
||||
for (auto it = conditionBindingMap.begin(); it != conditionBindingMap.end(); ++it) {
|
||||
q.bindValue(it.key(), it.value());
|
||||
}
|
||||
|
||||
return PrepareResult::Success;
|
||||
}
|
||||
|
||||
QuasarAppUtils::Params::log("This object doues not have condition for remove." + toString(),
|
||||
QuasarAppUtils::Error);
|
||||
|
||||
return PrepareResult::Fail;
|
||||
}
|
||||
|
||||
DBVariantMap DBObject::variantMap() const {
|
||||
if (isHaveAPrimaryKey()) {
|
||||
return {{primaryKey(), {primaryValue(), MemberType::PrimaryKey}}};
|
||||
@ -296,7 +296,7 @@ bool DBObject::isValid() const {
|
||||
return false;
|
||||
|
||||
if (isInsertPrimaryKey()) {
|
||||
return primaryValue().size();
|
||||
return primaryValue().isValid();
|
||||
}
|
||||
|
||||
return table().size();
|
||||
|
@ -379,18 +379,19 @@ protected:
|
||||
* This method using on default implementation of DBObject::prepareSelectQuery and DBObject::prepareRemoveQuery methods.
|
||||
* The default implementation generate when block by map for more information see the variantMap nethod.
|
||||
* Override this method for customize your select or delete query.
|
||||
* @return condition string.
|
||||
* @return condition string and qvariant map of the values for binding (bindingKey:bindValue).
|
||||
* @note This operation can not be block the sql request. Use the QString or int type for values of condition. If you want to bytes array in condition then override the DBObject::condition method.
|
||||
*
|
||||
* Example of overriding:
|
||||
* \code{cpp}
|
||||
* QString DBObject::condition() const {
|
||||
return {"id = '" + getId().toRaw() + "'"};
|
||||
return {{"id = :id"},
|
||||
{{{":id"}, {getId()}}}};
|
||||
}
|
||||
* \endcode
|
||||
*/
|
||||
|
||||
virtual QString condition() const;
|
||||
virtual std::pair<QString, QMap<QString, QVariant>> condition() const;
|
||||
|
||||
/**
|
||||
* @brief primaryKey This method must be return the name of primary key of this object table.
|
||||
@ -398,7 +399,7 @@ protected:
|
||||
* @note If you returned empty value then this method can not be prepare insert update and delete querys.
|
||||
* @return The primary key name.
|
||||
*/
|
||||
virtual QString primaryKey() const = 0;
|
||||
virtual QString primaryKey() const;
|
||||
|
||||
/**
|
||||
* @brief primaryValue This method is wraper of DBAddress::id. If This object do not contains a id value then return invalid value.
|
||||
@ -406,7 +407,7 @@ protected:
|
||||
* @note If you alredy override the condition method then You can return empty string because this method using in generate default condition only.
|
||||
* @see DBObject::condition.
|
||||
*/
|
||||
virtual QString primaryValue() const = 0;
|
||||
virtual QVariant primaryValue() const;
|
||||
|
||||
/**
|
||||
* @brief isInsertPrimaryKey This method check primaryKeys type.
|
||||
@ -415,8 +416,6 @@ protected:
|
||||
*/
|
||||
bool isInsertPrimaryKey() const;
|
||||
|
||||
private:
|
||||
QString getWhereBlock() const;
|
||||
};
|
||||
}
|
||||
}
|
||||
|
@ -56,14 +56,6 @@ public:
|
||||
_conditions = conditions;
|
||||
};
|
||||
|
||||
QString primaryValue() const override {
|
||||
return "";
|
||||
}
|
||||
|
||||
QString primaryKey() const override {
|
||||
return "";
|
||||
}
|
||||
|
||||
void clear() override {
|
||||
_data.clear();
|
||||
};
|
||||
@ -115,8 +107,8 @@ public:
|
||||
|
||||
protected:
|
||||
|
||||
QString condition() const override {
|
||||
return _conditions;
|
||||
std::pair<QString, QMap<QString, QVariant> > condition() const override {
|
||||
return {_conditions, {}};
|
||||
}
|
||||
|
||||
DBObject *createDBObject() const override {
|
||||
|
@ -72,8 +72,8 @@ QString DeleteObject::primaryKey() const {
|
||||
return "id";
|
||||
}
|
||||
|
||||
QString DeleteObject::primaryValue() const {
|
||||
return _address.id().toString();
|
||||
QVariant DeleteObject::primaryValue() const {
|
||||
return _address.id();
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -50,7 +50,7 @@ public:
|
||||
|
||||
protected:
|
||||
QString primaryKey() const override;
|
||||
QString primaryValue() const override;
|
||||
QVariant primaryValue() const override;
|
||||
|
||||
QDataStream &fromStream(QDataStream &stream) override;
|
||||
QDataStream &toStream(QDataStream &stream) const override;
|
||||
|
@ -36,7 +36,6 @@ PrepareResult GetMaxIntegerId::prepareSelectQuery(QSqlQuery &q) const {
|
||||
|
||||
bool GetMaxIntegerId::fromSqlRecord(const QSqlRecord &q) {
|
||||
_value = q.value(0).toInt();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -48,13 +47,5 @@ QString GetMaxIntegerId::table() const {
|
||||
return _table;
|
||||
}
|
||||
|
||||
QString GetMaxIntegerId::primaryKey() const {
|
||||
return "";
|
||||
}
|
||||
|
||||
QString GetMaxIntegerId::primaryValue() const {
|
||||
return "";
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
@ -41,10 +41,6 @@ public:
|
||||
bool isCached() const override;
|
||||
QString table() const override;
|
||||
|
||||
protected:
|
||||
QString primaryKey() const override;
|
||||
QString primaryValue() const override;
|
||||
|
||||
private:
|
||||
QString _table;
|
||||
QString _field;
|
||||
|
@ -19,9 +19,9 @@ GetSingleValue::GetSingleValue(const DbAddress& address,
|
||||
const QString& primaryKey) {
|
||||
|
||||
_table = address.table();
|
||||
_id = address.id().toString();
|
||||
_primaryValue = address.id();
|
||||
_field = field;
|
||||
_key = primaryKey;
|
||||
_primaryKey = primaryKey;
|
||||
}
|
||||
|
||||
QVariant GetSingleValue::value() const {
|
||||
@ -33,14 +33,15 @@ DBObject *GetSingleValue::createDBObject() const {
|
||||
}
|
||||
|
||||
PrepareResult GetSingleValue::prepareSelectQuery(QSqlQuery &q) const {
|
||||
QString queryString = "SELECT %0 FROM %1 WHERE %2='%3'";
|
||||
|
||||
queryString = queryString.arg(_field, table(), _key, _id);
|
||||
QString queryString = "SELECT %0 FROM %1 WHERE %2=:%2";
|
||||
queryString = queryString.arg(_field, table(), _primaryKey);
|
||||
|
||||
if (!q.prepare(queryString)) {
|
||||
return PrepareResult::Fail;
|
||||
}
|
||||
|
||||
q.bindValue(":" + _primaryKey, _primaryValue);
|
||||
|
||||
return PrepareResult::Success;
|
||||
}
|
||||
|
||||
@ -59,11 +60,11 @@ QString GetSingleValue::table() const {
|
||||
}
|
||||
|
||||
QString GetSingleValue::primaryKey() const {
|
||||
return _id;
|
||||
return _primaryKey;
|
||||
}
|
||||
|
||||
QString GetSingleValue::primaryValue() const {
|
||||
return _field;
|
||||
QVariant GetSingleValue::primaryValue() const {
|
||||
return _primaryValue;
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -63,13 +63,13 @@ public:
|
||||
|
||||
protected:
|
||||
QString primaryKey() const override;
|
||||
QString primaryValue() const override;
|
||||
QVariant primaryValue() const override;
|
||||
private:
|
||||
QString _id;
|
||||
QString _field;
|
||||
QString _primaryKey;
|
||||
QVariant _primaryValue;
|
||||
QString _table;
|
||||
QVariant _value;
|
||||
QString _key;
|
||||
QString _field;
|
||||
|
||||
};
|
||||
}
|
||||
|
@ -20,7 +20,7 @@ SetSingleValue::SetSingleValue(const DbAddress& address,
|
||||
const QString& field,
|
||||
const QVariant& value,
|
||||
const QString &primaryKey) {
|
||||
_id = address.id().toString();
|
||||
_primaryValue = address.id();
|
||||
_table = address.table();
|
||||
_field = field;
|
||||
_value = value;
|
||||
@ -32,9 +32,9 @@ DBObject *SetSingleValue::createDBObject() const {
|
||||
}
|
||||
|
||||
PrepareResult SetSingleValue::prepareUpdateQuery(QSqlQuery &q) const {
|
||||
QString queryString = "UPDATE %0 SET %1=:%1 WHERE %2='%3'";
|
||||
QString queryString = "UPDATE %0 SET %1=:%1 WHERE %2=:%2";
|
||||
|
||||
queryString = queryString.arg(table(), _field, primaryKey(), _id);
|
||||
queryString = queryString.arg(table(), _field, primaryKey());
|
||||
|
||||
if (!q.prepare(queryString)) {
|
||||
|
||||
@ -44,6 +44,7 @@ PrepareResult SetSingleValue::prepareUpdateQuery(QSqlQuery &q) const {
|
||||
}
|
||||
|
||||
q.bindValue(":" + _field, _value);
|
||||
q.bindValue(":" + _primaryKey, _primaryValue);
|
||||
|
||||
return PrepareResult::Success;
|
||||
}
|
||||
@ -63,7 +64,7 @@ PrepareResult SetSingleValue::prepareInsertQuery(QSqlQuery &q, bool replace) con
|
||||
return PrepareResult::Fail;
|
||||
}
|
||||
|
||||
q.bindValue(":" + primaryKey(), primaryValue());
|
||||
q.bindValue(":" + _primaryKey, _primaryValue);
|
||||
q.bindValue(":" + _field, _value);
|
||||
|
||||
return PrepareResult::Success;
|
||||
@ -85,8 +86,8 @@ QString SetSingleValue::primaryKey() const {
|
||||
return _primaryKey;
|
||||
}
|
||||
|
||||
QString SetSingleValue::primaryValue() const {
|
||||
return _id;
|
||||
QVariant SetSingleValue::primaryValue() const {
|
||||
return _primaryValue;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -59,14 +59,14 @@ public:
|
||||
|
||||
protected:
|
||||
QString primaryKey() const override;
|
||||
QString primaryValue() const override;
|
||||
QVariant primaryValue() const override;
|
||||
|
||||
private:
|
||||
QString _id;
|
||||
QString _table;
|
||||
QString _field;
|
||||
QString _primaryKey;
|
||||
QVariant _primaryValue;
|
||||
QString _table;
|
||||
QVariant _value;
|
||||
QString _field;
|
||||
};
|
||||
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user