8#include "personmanager_p.h"
10#include "kpeople_debug.h"
14#include <QStandardPaths>
18#include <QDBusConnection>
19#include <QDBusMessage>
28 Transaction(
const Transaction &) =
delete;
29 Transaction &operator=(
const Transaction &) =
delete;
33 bool m_cancelled =
false;
42void Transaction::cancel()
48Transaction::~Transaction()
55PersonManager::PersonManager(
const QString &databasePath,
QObject *parent)
57 , m_db(
QSqlDatabase::addDatabase(QStringLiteral(
"QSQLITE"), QStringLiteral(
"kpeoplePersonsManager")))
59 m_db.setDatabaseName(databasePath);
61 qCWarning(KPEOPLE_LOG) <<
"Couldn't open the database at" << databasePath;
63 m_db.exec(QStringLiteral(
"CREATE TABLE IF NOT EXISTS persons (contactID VARCHAR UNIQUE NOT NULL, personID INT NOT NULL)"));
64 m_db.exec(QStringLiteral(
"CREATE INDEX IF NOT EXISTS contactIdIndex ON persons (contactId)"));
65 m_db.exec(QStringLiteral(
"CREATE INDEX IF NOT EXISTS personIdIndex ON persons (personId)"));
69 QStringLiteral(
"/KPeople"),
70 QStringLiteral(
"org.kde.KPeople"),
71 QStringLiteral(
"ContactAddedToPerson"),
75 QStringLiteral(
"/KPeople"),
76 QStringLiteral(
"org.kde.KPeople"),
77 QStringLiteral(
"ContactRemovedFromPerson"),
79 SIGNAL(contactRemovedFromPerson(
QString)));
83PersonManager::~PersonManager()
91 QSqlQuery query = m_db.exec(QStringLiteral(
"SELECT personID, contactID FROM persons"));
92 while (
query.next()) {
95 contactMapping.insert(personUri, contactID);
97 return contactMapping;
109 query.prepare(QStringLiteral(
"SELECT contactID FROM persons WHERE personId = ?"));
110 query.bindValue(0, personUri.
mid(strlen(
"kpeople://")));
113 while (
query.next()) {
114 contactUris <<
query.value(0).toString();
119QString PersonManager::personUriForContact(
const QString &contactUri)
const
122 query.prepare(QStringLiteral(
"SELECT personId FROM persons WHERE contactId = ?"));
123 query.bindValue(0, contactUri);
134 if (ids.
size() < 2) {
147 for (
const QString &
id : ids) {
162 QSqlQuery query = m_db.exec(QStringLiteral(
"SELECT MAX(personID) FROM persons"));
164 personUri =
query.value(0).toInt();
170 personUriString = metacontacts.
first();
177 if (metacontacts.
count() > 1) {
180 for (
const QString &
id : std::as_const(metacontacts)) {
181 if (
id != personUriString) {
182 personContacts << contactsForPersonUri(
id);
187 for (
const QString &
id : std::as_const(personContacts)) {
189 updateQuery.prepare(QStringLiteral(
"UPDATE persons SET personID = ? WHERE contactID = ?"));
190 updateQuery.bindValue(0, personUriString.
mid(strlen(
"kpeople://")));
191 updateQuery.bindValue(1,
id);
192 if (!updateQuery.exec()) {
196 pendingContactRemovedFromPerson.
append(
id);
197 pendingContactAddedToPerson.
append({id, personUriString});
203 for (
const QString &
id : std::as_const(contacts)) {
205 insertQuery.prepare(QStringLiteral(
"INSERT INTO persons VALUES (?, ?)"));
206 insertQuery.bindValue(0,
id);
207 insertQuery.bindValue(1, personUriString.
mid(strlen(
"kpeople://")));
208 if (!insertQuery.exec()) {
213 pendingContactAddedToPerson.
append({id, personUriString});
220 for (
const auto &
id : std::as_const(pendingContactRemovedFromPerson)) {
223 QDBusMessage::createSignal(QStringLiteral(
"/KPeople"), QStringLiteral(
"org.kde.KPeople"), QStringLiteral(
"ContactRemovedFromPerson"));
227 Q_EMIT contactRemovedFromPerson(
id);
230 for (
const auto &it : std::as_const(pendingContactAddedToPerson)) {
233 QDBusMessage::createSignal(QStringLiteral(
"/KPeople"), QStringLiteral(
"org.kde.KPeople"), QStringLiteral(
"ContactAddedToPerson"));
234 message.
setArguments(QVariantList() << it.first << it.second);
237 Q_EMIT contactAddedToPerson(it.first, it.second);
242 personUriString.
clear();
245 return personUriString;
248bool PersonManager::unmergeContact(
const QString &
id)
254 const QStringList contactUris = contactsForPersonUri(
id);
255 query.prepare(QStringLiteral(
"DELETE FROM persons WHERE personId = ?"));
256 query.bindValue(0,
id.mid(strlen(
"kpeople://")));
259 for (
const QString &contactUri : contactUris) {
263 QDBusMessage::createSignal(QStringLiteral(
"/KPeople"), QStringLiteral(
"org.kde.KPeople"), QStringLiteral(
"ContactRemovedFromPerson"));
268 Q_EMIT contactRemovedFromPerson(contactUri);
273 query.prepare(QStringLiteral(
"DELETE FROM persons WHERE contactId = ?"));
274 query.bindValue(0,
id);
277 Q_EMIT contactRemovedFromPerson(
id);
284PersonManager *PersonManager::instance(
const QString &databasePath)
286 static PersonManager *s_instance =
nullptr;
295 s_instance =
new PersonManager(path);
300#include "moc_personmanager_p.cpp"
std::optional< QSqlQuery > query(const QString &queryStatement)
QString path(const QString &relativePath)
bool connect(const QString &service, const QString &path, const QString &interface, const QString &name, QObject *receiver, const char *slot)
bool send(const QDBusMessage &message) const const
QDBusConnection sessionBus()
QDBusMessage createSignal(const QString &path, const QString &interface, const QString &name)
void setArguments(const QList< QVariant > &arguments)
bool mkpath(const QString &dirPath) const const
void append(QList< T > &&value)
qsizetype count() const const
bool isEmpty() const const
qsizetype size() const const
QString writableLocation(StandardLocation type)
bool isEmpty() const const
QString mid(qsizetype position, qsizetype n) const const
QString number(double n, char format, int precision)
bool startsWith(QChar c, Qt::CaseSensitivity cs) const const