Made a start with showing foreignkeys in column list.

Not finished, need to decide what to do with multiple and multi column fkeys.
This commit is contained in:
eelke 2017-12-25 10:31:58 +01:00
parent a76686acfd
commit 190a6c04dc
14 changed files with 97 additions and 94 deletions

View file

@ -3,6 +3,7 @@
#include "PgAttribute.h" #include "PgAttribute.h"
#include "PgAttributeContainer.h" #include "PgAttributeContainer.h"
#include "PgClassContainer.h" #include "PgClassContainer.h"
#include "PgConstraintContainer.h"
#include "PgType.h" #include "PgType.h"
#include "PgTypeContainer.h" #include "PgTypeContainer.h"
#include "PgIndexContainer.h" #include "PgIndexContainer.h"
@ -69,6 +70,9 @@ QVariant ColumnTableModel::headerData(int section, Qt::Orientation orientation,
case DefaultCol: case DefaultCol:
c = tr("Default"); c = tr("Default");
break; break;
case ForeignKeyCol:
c = tr("Refs");
break;
case CollationCol: case CollationCol:
c = tr("Collation"); c = tr("Collation");
break; break;
@ -104,6 +108,9 @@ QVariant ColumnTableModel::headerData(int section, Qt::Orientation orientation,
case DefaultCol: case DefaultCol:
v = tr("Default value for the columns"); v = tr("Default value for the columns");
break; break;
case ForeignKeyCol:
v = tr("Foreign key constraint for this column");
break;
// case CollationCol: // case CollationCol:
// c = tr("Collation"); // c = tr("Collation");
// break; // break;
@ -178,6 +185,9 @@ QVariant ColumnTableModel::getData(const QModelIndex &index) const
case DefaultCol: case DefaultCol:
s = t.defaultValue; s = t.defaultValue;
break; break;
case ForeignKeyCol:
s = getFKey(t);
break;
case CollationCol: case CollationCol:
s = ""; //t.collation; s = ""; //t.collation;
break; break;
@ -188,6 +198,16 @@ QVariant ColumnTableModel::getData(const QModelIndex &index) const
return v; return v;
} }
QString ColumnTableModel::getFKey(const PgAttribute &column) const
{
QString result;
const PgConstraint *c = m_catalog->constraints()->getFKeyForTableColumn(column.relid, column.num);
if (c) {
result = c->name;
}
return result;
}
QVariant ColumnTableModel::data(const QModelIndex &index, int role) const QVariant ColumnTableModel::data(const QModelIndex &index, int role) const
{ {
if (role == Qt::ForegroundRole && index.column() == TypeCol) { if (role == Qt::ForegroundRole && index.column() == TypeCol) {

View file

@ -17,6 +17,7 @@ public:
TypeCol, TypeCol,
NullCol, NullCol,
DefaultCol, DefaultCol,
ForeignKeyCol,
CollationCol, CollationCol,
colCount }; colCount };
@ -44,6 +45,8 @@ protected:
t_Columns m_columns; t_Columns m_columns;
std::vector<PgIndex> m_indexes; std::vector<PgIndex> m_indexes;
QString getFKey(const PgAttribute &column) const;
}; };
#endif // COLUMNTABLEMODEL_H #endif // COLUMNTABLEMODEL_H

View file

@ -35,13 +35,13 @@ public:
void setConfig(const ConnectionConfig &config); void setConfig(const ConnectionConfig &config);
OpenDatabase* getDatabase() { return m_database; } std::shared_ptr<OpenDatabase> getDatabase() { return m_database; }
private: private:
Ui::MainWindow *ui; Ui::MainWindow *ui;
ConnectionConfig m_config; ConnectionConfig m_config;
OpenDatabase *m_database = nullptr; std::shared_ptr<OpenDatabase> m_database;
MasterController *m_masterController; MasterController *m_masterController;

View file

@ -3,22 +3,21 @@
#include "Pgsql_Connection.h" #include "Pgsql_Connection.h"
#include "TypeSelectionItemModel.h" #include "TypeSelectionItemModel.h"
Expected<OpenDatabase*> OpenDatabase::createOpenDatabase(const ConnectionConfig &cfg) Expected<OpenDatabase::OpenDatabaseSPtr> OpenDatabase::createOpenDatabase(const ConnectionConfig &cfg)
{ {
OpenDatabase *odb = new OpenDatabase(cfg, nullptr); OpenDatabaseSPtr odb(new OpenDatabase(cfg));
if (odb->Init()) { if (odb->Init()) {
return odb; return odb;
} }
//return Expected<ConnectionConfig>::fromException(std::out_of_range("Invalid row")); //return Expected<ConnectionConfig>::fromException(std::out_of_range("Invalid row"));
return Expected<OpenDatabase*>::fromException( return Expected<OpenDatabaseSPtr>::fromException(
std::runtime_error("Failed to get database information")); std::runtime_error("Failed to get database information"));
} }
OpenDatabase::OpenDatabase(const ConnectionConfig& cfg, QObject *parent) OpenDatabase::OpenDatabase(const ConnectionConfig& cfg)
: QObject(parent) : m_config(cfg)
, m_config(cfg)
, m_catalogue(std::make_shared<PgDatabaseCatalog>()) , m_catalogue(std::make_shared<PgDatabaseCatalog>())
{ {
} }

View file

@ -1,7 +1,6 @@
#ifndef OPENDATABASE_H #ifndef OPENDATABASE_H
#define OPENDATABASE_H #define OPENDATABASE_H
#include <QObject>
#include "ConnectionConfig.h" #include "ConnectionConfig.h"
#include "Expected.h" #include "Expected.h"
#include <memory> #include <memory>
@ -12,11 +11,13 @@ class TypeSelectionItemModel;
/** Instances of this class represent a single database on which atleast one /** Instances of this class represent a single database on which atleast one
* window is opened. This class is used to track details about that database. * window is opened. This class is used to track details about that database.
*/ */
class OpenDatabase : public QObject class OpenDatabase {
{
Q_OBJECT
public: public:
static Expected<OpenDatabase*> createOpenDatabase(const ConnectionConfig &cfg); using OpenDatabaseSPtr = std::shared_ptr<OpenDatabase>;
static Expected<OpenDatabaseSPtr> createOpenDatabase(const ConnectionConfig &cfg);
// using on_createResult_callback = std::function<void(Expected<std::shared_ptr<Pgsql::Result>>, qint64)>;
// void asyncCreateOpenDatabase(const ConnectionConfig &cfg, );
OpenDatabase(const OpenDatabase &) = delete; OpenDatabase(const OpenDatabase &) = delete;
OpenDatabase& operator=(const OpenDatabase &) = delete; OpenDatabase& operator=(const OpenDatabase &) = delete;
@ -24,9 +25,6 @@ public:
std::shared_ptr<PgDatabaseCatalog> catalogue(); std::shared_ptr<PgDatabaseCatalog> catalogue();
TypeSelectionItemModel* typeSelectionModel(); TypeSelectionItemModel* typeSelectionModel();
signals:
public slots:
private: private:
ConnectionConfig m_config; ConnectionConfig m_config;
@ -34,7 +32,7 @@ private:
TypeSelectionItemModel *m_typeSelectionModel = nullptr; TypeSelectionItemModel *m_typeSelectionModel = nullptr;
OpenDatabase(const ConnectionConfig& cfg, QObject *parent = 0); OpenDatabase(const ConnectionConfig& cfg);
bool Init(); bool Init();
}; };

View file

@ -38,7 +38,7 @@ public:
Oid am = InvalidOid; Oid am = InvalidOid;
Oid filenode = InvalidOid; Oid filenode = InvalidOid;
Oid tablespace = InvalidOid; Oid tablespace = InvalidOid;
int pages_est = 0; int32_t pages_est = 0;
float tuples_est = 0.0f; float tuples_est = 0.0f;
Oid toastrelid = InvalidOid; Oid toastrelid = InvalidOid;
bool isshared = false; bool isshared = false;

View file

@ -1,5 +1,6 @@
#include "PgConstraintContainer.h" #include "PgConstraintContainer.h"
#include "Pgsql_Col.h" #include "Pgsql_Col.h"
#include <algorithm>
std::string PgConstraintContainer::getLoadQuery() const std::string PgConstraintContainer::getLoadQuery() const
{ {
@ -30,6 +31,8 @@ FROM pg_constraint)__";
//} //}
PgConstraint PgConstraintContainer::loadElem(const Pgsql::Row &row) PgConstraint PgConstraintContainer::loadElem(const Pgsql::Row &row)
{ {
Pgsql::Col col(row); Pgsql::Col col(row);
@ -47,3 +50,16 @@ PgConstraint PgConstraintContainer::loadElem(const Pgsql::Row &row)
col >> v.bin >> v.src >> v.definition; col >> v.bin >> v.src >> v.definition;
return v; return v;
} }
const PgConstraint* PgConstraintContainer::getFKeyForTableColumn(Oid relid, int16_t attnum) const
{
const PgConstraint *result = nullptr;
// WHat do we want to find here? On ly single column constraints or all contstraints.
// auto res = std::find_if(m_container.begin(), m_container.end(),
// [relid, attnum] (const auto &c) {
// // the find on v.key may not look super efficient but remember it in general only has one or two elements.
// return relid == c.relid &&
// (std::find(attnum.begin(), attnum.end(), v.key) != attnum.end());
// });
return result;
}

View file

@ -12,6 +12,7 @@ public:
virtual std::string getLoadQuery() const override; virtual std::string getLoadQuery() const override;
//std::vector<PgConstraint> getIndexesForTable(Oid table_oid) const; //std::vector<PgConstraint> getIndexesForTable(Oid table_oid) const;
const PgConstraint* getFKeyForTableColumn(Oid relid, int16_t attnum) const;
protected: protected:
virtual PgConstraint loadElem(const Pgsql::Row &row) override; virtual PgConstraint loadElem(const Pgsql::Row &row) override;
}; };

View file

@ -3,6 +3,7 @@
#include "PgAttributeContainer.h" #include "PgAttributeContainer.h"
#include "PgAuthIdContainer.h" #include "PgAuthIdContainer.h"
#include "PgClassContainer.h" #include "PgClassContainer.h"
#include "PgConstraintContainer.h"
#include "PgDatabaseContainer.h" #include "PgDatabaseContainer.h"
#include "PgIndexContainer.h" #include "PgIndexContainer.h"
#include "PgNamespaceContainer.h" #include "PgNamespaceContainer.h"
@ -102,13 +103,14 @@ PgDatabaseCatalog::~PgDatabaseCatalog()
void PgDatabaseCatalog::loadAll(Pgsql::Connection &conn) void PgDatabaseCatalog::loadAll(Pgsql::Connection &conn)
{ {
loadInfo(conn); loadInfo(conn);
loadAttributes(conn); load2(m_attributes, conn);
loadAuthIds(conn); load2(m_authIds, conn);
loadClasses(conn); load2(m_classes, conn);
loadDatabases(conn); load2(m_constraints, conn);
loadIndexes(conn); load2(m_databases, conn);
loadNamespaces(conn); load2(m_indexes, conn);
loadTypes(conn); load2(m_namespaces, conn);
load2(m_types, conn);
} }
void PgDatabaseCatalog::loadInfo(Pgsql::Connection &conn) void PgDatabaseCatalog::loadInfo(Pgsql::Connection &conn)
@ -138,63 +140,6 @@ void load(Pgsql::Connection &conn, IPgContainter &pg_cont)
} }
void PgDatabaseCatalog::loadAttributes(Pgsql::Connection &conn)
{
if (!m_attributes)
m_attributes = std::make_shared<PgAttributeContainer>(shared_from_this());
load(conn, *m_attributes);
}
void PgDatabaseCatalog::loadAuthIds(Pgsql::Connection &conn)
{
if (!m_authIds)
m_authIds = std::make_shared<PgAuthIdContainer>(shared_from_this());
load(conn, *m_authIds);
}
void PgDatabaseCatalog::loadClasses(Pgsql::Connection &conn)
{
if (!m_classes)
m_classes = std::make_shared<PgClassContainer>(shared_from_this());
load(conn, *m_classes);
}
void PgDatabaseCatalog::loadDatabases(Pgsql::Connection &conn)
{
if (!m_databases)
m_databases = std::make_shared<PgDatabaseContainer>(shared_from_this());
load(conn, *m_databases);
}
void PgDatabaseCatalog::loadIndexes(Pgsql::Connection &conn)
{
if (!m_indexes)
m_indexes = std::make_shared<PgIndexContainer>(shared_from_this());
load(conn, *m_indexes);
}
void PgDatabaseCatalog::loadNamespaces(Pgsql::Connection &conn)
{
if (!m_namespaces)
m_namespaces = std::make_shared<PgNamespaceContainer>(shared_from_this());
load(conn, *m_namespaces);
}
void PgDatabaseCatalog::loadTypes(Pgsql::Connection &conn)
{
if (!m_types)
m_types = std::make_shared<PgTypeContainer>(shared_from_this());
load(conn, *m_types);
}
const QString& PgDatabaseCatalog::serverVersionString() const const QString& PgDatabaseCatalog::serverVersionString() const
{ {
return m_serverVersionString; return m_serverVersionString;
@ -220,6 +165,11 @@ std::shared_ptr<const PgClassContainer> PgDatabaseCatalog::classes() const
return m_classes; return m_classes;
} }
std::shared_ptr<const PgConstraintContainer> PgDatabaseCatalog::constraints() const
{
return m_constraints;
}
std::shared_ptr<const PgDatabaseContainer> PgDatabaseCatalog::databases() const std::shared_ptr<const PgDatabaseContainer> PgDatabaseCatalog::databases() const
{ {
return m_databases; return m_databases;

View file

@ -15,6 +15,7 @@ namespace Pgsql {
class PgAttributeContainer; class PgAttributeContainer;
class PgAuthIdContainer; class PgAuthIdContainer;
class PgClassContainer; class PgClassContainer;
class PgConstraintContainer;
class PgDatabaseContainer; class PgDatabaseContainer;
class PgIndexContainer; class PgIndexContainer;
class PgNamespaceContainer; class PgNamespaceContainer;
@ -32,13 +33,14 @@ public:
void loadAll(Pgsql::Connection &conn); void loadAll(Pgsql::Connection &conn);
void loadInfo(Pgsql::Connection &conn); void loadInfo(Pgsql::Connection &conn);
void loadAttributes(Pgsql::Connection &conn); //void loadAttributes(Pgsql::Connection &conn);
void loadAuthIds(Pgsql::Connection &conn); // void loadAuthIds(Pgsql::Connection &conn);
void loadClasses(Pgsql::Connection &conn); // void loadClasses(Pgsql::Connection &conn);
void loadDatabases(Pgsql::Connection &conn); // void loadConstraints(Pgsql::Connection &conn);
void loadIndexes(Pgsql::Connection &conn); // void loadDatabases(Pgsql::Connection &conn);
void loadNamespaces(Pgsql::Connection &conn); // void loadIndexes(Pgsql::Connection &conn);
void loadTypes(Pgsql::Connection &conn); // void loadNamespaces(Pgsql::Connection &conn);
// void loadTypes(Pgsql::Connection &conn);
const QString& serverVersionString() const; const QString& serverVersionString() const;
int serverVersion() const; int serverVersion() const;
@ -46,6 +48,7 @@ public:
std::shared_ptr<const PgAttributeContainer> attributes() const; std::shared_ptr<const PgAttributeContainer> attributes() const;
std::shared_ptr<const PgAuthIdContainer> authIds() const; std::shared_ptr<const PgAuthIdContainer> authIds() const;
std::shared_ptr<const PgClassContainer> classes() const; std::shared_ptr<const PgClassContainer> classes() const;
std::shared_ptr<const PgConstraintContainer> constraints() const;
std::shared_ptr<const PgDatabaseContainer> databases() const; std::shared_ptr<const PgDatabaseContainer> databases() const;
std::shared_ptr<const PgIndexContainer> indexes() const; std::shared_ptr<const PgIndexContainer> indexes() const;
std::shared_ptr<const PgNamespaceContainer> namespaces() const; std::shared_ptr<const PgNamespaceContainer> namespaces() const;
@ -57,10 +60,21 @@ private:
std::shared_ptr<PgAttributeContainer> m_attributes; std::shared_ptr<PgAttributeContainer> m_attributes;
std::shared_ptr<PgAuthIdContainer> m_authIds; std::shared_ptr<PgAuthIdContainer> m_authIds;
std::shared_ptr<PgClassContainer> m_classes; std::shared_ptr<PgClassContainer> m_classes;
std::shared_ptr<PgConstraintContainer> m_constraints;
std::shared_ptr<PgDatabaseContainer> m_databases; std::shared_ptr<PgDatabaseContainer> m_databases;
std::shared_ptr<PgIndexContainer> m_indexes; std::shared_ptr<PgIndexContainer> m_indexes;
std::shared_ptr<PgNamespaceContainer> m_namespaces; std::shared_ptr<PgNamespaceContainer> m_namespaces;
std::shared_ptr<PgTypeContainer> m_types; std::shared_ptr<PgTypeContainer> m_types;
template <typename T>
void load2(std::shared_ptr<T> &ptr, Pgsql::Connection &conn)
{
if (!ptr)
ptr = std::make_shared<T>(shared_from_this());
load(conn, *ptr);
}
}; };
QString getRoleNameFromOid(const PgDatabaseCatalog &cat, Oid oid); QString getRoleNameFromOid(const PgDatabaseCatalog &cat, Oid oid);

View file

@ -6,7 +6,7 @@
QueryParamListController::QueryParamListController(QTableView *tv, QueryParamListController::QueryParamListController(QTableView *tv,
OpenDatabase *opendb, QWidget *parent) std::shared_ptr<OpenDatabase> opendb, QWidget *parent)
: QObject(parent) : QObject(parent)
, paramTableView(tv) , paramTableView(tv)
, m_openDatabase(opendb) , m_openDatabase(opendb)

View file

@ -5,6 +5,7 @@
#include "ParamListModel.h" #include "ParamListModel.h"
#include "ParamTypeDelegate.h" #include "ParamTypeDelegate.h"
#include "Pgsql_Params.h" #include "Pgsql_Params.h"
#include <memory>
class QTableView; class QTableView;
class OpenDatabase; class OpenDatabase;
@ -12,7 +13,7 @@ class OpenDatabase;
class QueryParamListController : public QObject { class QueryParamListController : public QObject {
Q_OBJECT Q_OBJECT
public: public:
QueryParamListController(QTableView *tv, OpenDatabase *opendb, QWidget *parent); QueryParamListController(QTableView *tv, std::shared_ptr<OpenDatabase> opendb, QWidget *parent);
Pgsql::Params params() const; Pgsql::Params params() const;
bool empty() const; bool empty() const;
@ -21,7 +22,7 @@ public slots:
void on_removeParam(); void on_removeParam();
private: private:
QTableView *paramTableView; QTableView *paramTableView;
OpenDatabase *m_openDatabase; std::shared_ptr<OpenDatabase> m_openDatabase;
ParamListModel m_paramList; ParamListModel m_paramList;
ParamTypeDelegate m_typeDelegate; ParamTypeDelegate m_typeDelegate;
}; };

View file

@ -41,7 +41,7 @@ QueryTab::QueryTab(MainWindow *win, QWidget *parent) :
ui->queryEdit->setFont(font); ui->queryEdit->setFont(font);
highlighter = new SqlSyntaxHighlighter(ui->queryEdit->document()); highlighter = new SqlSyntaxHighlighter(ui->queryEdit->document());
OpenDatabase* open_database = m_win->getDatabase(); auto open_database = m_win->getDatabase();
if (open_database) { if (open_database) {
auto cat = open_database->catalogue(); auto cat = open_database->catalogue();
highlighter->setTypes(*cat->types()); highlighter->setTypes(*cat->types());

View file

@ -3,6 +3,7 @@
#include "ASyncWindow.h" #include "ASyncWindow.h"
#include "ConnectionConfig.h" #include "ConnectionConfig.h"
#include <memory>
namespace Ui { namespace Ui {
class ServerWindow; class ServerWindow;
@ -25,7 +26,7 @@ private:
MasterController *m_masterController = nullptr; MasterController *m_masterController = nullptr;
ConnectionConfig m_config; ConnectionConfig m_config;
OpenDatabase *m_database = nullptr; std::shared_ptr<OpenDatabase> m_database;
DatabasesTableModel *m_databasesModel = nullptr; DatabasesTableModel *m_databasesModel = nullptr;
RolesTableModel *m_rolesModel = nullptr; RolesTableModel *m_rolesModel = nullptr;
}; };