Hi, In 9.2, domains and check constraints can be declared not valid. Their validity can be forced later. This patch adds support for this new feature.
Comments? -- Guillaume http://blog.guillaume.lelarge.info http://www.dalibo.com
>From 144f3d63dd009949ec56cb914f5b26dc893b78db Mon Sep 17 00:00:00 2001 From: Guillaume Lelarge <guilla...@lelarge.info> Date: Sat, 9 Jul 2011 15:15:33 +0200 Subject: [PATCH] Support for not valid domain and check constraints In 9.2, domains and check constraints can be declared not valid. Their validity can be forced later. This patch adds support for this. --- pgadmin/dlg/dlgCheck.cpp | 32 ++++++++++++- pgadmin/dlg/dlgDomain.cpp | 58 ++++++++++++++++++++++- pgadmin/dlg/dlgTable.cpp | 6 +- pgadmin/frm/frmMain.cpp | 4 ++ pgadmin/include/dlg/dlgCheck.h | 2 + pgadmin/include/dlg/dlgDomain.h | 1 + pgadmin/include/images/checkbad.png | Bin 0 -> 368 bytes pgadmin/include/schema/pgCheck.h | 28 +++++++++++ pgadmin/include/schema/pgDomain.h | 29 +++++++++++- pgadmin/schema/pgCheck.cpp | 88 ++++++++++++++++++++++++++++++---- pgadmin/schema/pgDomain.cpp | 60 +++++++++++++++++++++++- pgadmin/schema/pgTable.cpp | 2 + pgadmin/ui/dlgCheck.xrc | 16 ++++++- pgadmin/ui/dlgDomain.xrc | 16 ++++++- 14 files changed, 318 insertions(+), 24 deletions(-) create mode 100755 pgadmin/include/images/checkbad.png diff --git a/pgadmin/dlg/dlgCheck.cpp b/pgadmin/dlg/dlgCheck.cpp index 268b571..31687a0 100644 --- a/pgadmin/dlg/dlgCheck.cpp +++ b/pgadmin/dlg/dlgCheck.cpp @@ -21,10 +21,12 @@ #include "dlg/dlgCheck.h" #define txtWhere CTRL_TEXT("txtWhere") +#define chkDontValidate CTRL_CHECKBOX("chkDontValidate") BEGIN_EVENT_TABLE(dlgCheck, dlgProperty) EVT_TEXT(XRCID("txtWhere"), dlgProperty::OnChange) + EVT_CHECKBOX(XRCID("chkDontValidate"), dlgCheck::OnChangeValidate) END_EVENT_TABLE(); @@ -43,13 +45,16 @@ dlgCheck::dlgCheck(pgaFactory *f, frmMain *frame, pgCheck *node, pgTable *parent void dlgCheck::CheckChange() { + bool enable = true; if (check) { - EnableOK(txtComment->GetValue() != check->GetComment()); + enable = txtComment->GetValue() != check->GetComment(); + if (connection->BackendMinimumVersion(9, 2) && !check->GetValid() && !chkDontValidate->GetValue()) + enable = true; + EnableOK(enable); } else { - bool enable = true; txtComment->Enable(!GetName().IsEmpty()); CheckValid(enable, !txtWhere->GetValue().IsEmpty(), _("Please specify condition.")); EnableOK(enable); @@ -86,6 +91,12 @@ int dlgCheck::Go(bool modal) txtWhere->SetValue(check->GetDefinition()); txtWhere->Disable(); + + if (connection->BackendMinimumVersion(9, 2)) + chkDontValidate->SetValue(!check->GetValid()); + else + chkDontValidate->SetValue(true); + chkDontValidate->Enable(connection->BackendMinimumVersion(9, 2) && !check->GetDefinition().IsEmpty() && !check->GetValid()); } else { @@ -96,11 +107,19 @@ int dlgCheck::Go(bool modal) cbClusterSet->Disable(); cbClusterSet = 0; } + chkDontValidate->Enable(connection->BackendMinimumVersion(9, 2)); } + return dlgProperty::Go(modal); } +void dlgCheck::OnChangeValidate(wxCommandEvent &ev) +{ + CheckChange(); +} + + wxString dlgCheck::GetSql() { wxString sql; @@ -114,6 +133,12 @@ wxString dlgCheck::GetSql() sql += wxT(" CHECK ") + GetDefinition() + wxT(";\n"); } + else if (!chkDontValidate->GetValue()) + { + sql = wxT("ALTER TABLE ") + table->GetQuotedFullIdentifier() + + wxT(" VALIDATE CONSTRAINT ") + qtIdent(name) + wxT(";\n"); + } + if (!name.IsEmpty()) AppendComment(sql, wxT("CONSTRAINT ") + qtIdent(name) + wxT(" ON ") + table->GetQuotedFullIdentifier(), check); @@ -127,5 +152,8 @@ wxString dlgCheck::GetDefinition() sql = wxT("(") + txtWhere->GetValue() + wxT(")"); + if (chkDontValidate->GetValue()) + sql += wxT(" NOT VALID"); + return sql; } diff --git a/pgadmin/dlg/dlgDomain.cpp b/pgadmin/dlg/dlgDomain.cpp index 1538018..f5f66e2 100644 --- a/pgadmin/dlg/dlgDomain.cpp +++ b/pgadmin/dlg/dlgDomain.cpp @@ -28,6 +28,7 @@ #define txtDefault CTRL_TEXT("txtDefault") #define txtCheck CTRL_TEXT("txtCheck") #define cbCollation CTRL_COMBOBOX("cbCollation") +#define chkDontValidate CTRL_CHECKBOX("chkDontValidate") BEGIN_EVENT_TABLE(dlgDomain, dlgTypeProperty) EVT_TEXT(XRCID("txtLength"), dlgProperty::OnChange) @@ -37,6 +38,8 @@ BEGIN_EVENT_TABLE(dlgDomain, dlgTypeProperty) EVT_TEXT(XRCID("txLength"), dlgProperty::OnChange) EVT_TEXT(XRCID("txtDefault"), dlgProperty::OnChange) EVT_CHECKBOX(XRCID("chkNotNull"), dlgProperty::OnChange) + EVT_CHECKBOX(XRCID("chkDontValidate"), dlgDomain::OnChangeValidate) + EVT_TEXT(XRCID("txtCheck"), dlgProperty::OnChange) END_EVENT_TABLE(); @@ -83,7 +86,6 @@ int dlgDomain::Go(bool modal) txtName->Disable(); cbDatatype->Disable(); - txtCheck->Disable(); cbCollation->SetValue(domain->GetQuotedCollation()); cbCollation->Disable(); @@ -94,6 +96,9 @@ int dlgDomain::Go(bool modal) txtDefault->Disable(); chkNotNull->Disable(); } + + if (connection->BackendMinimumVersion(9, 2)) + chkDontValidate->SetValue(!domain->GetValid()); } else { @@ -125,6 +130,11 @@ int dlgDomain::Go(bool modal) cbCollation->SetSelection(0); } } + + if (connection->BackendMinimumVersion(9, 2)) + chkDontValidate->Enable(!domain || (domain && !domain->GetValid())); + else + chkDontValidate->Enable(false); return dlgProperty::Go(modal); } @@ -144,12 +154,18 @@ pgObject *dlgDomain::CreateObject(pgCollection *collection) void dlgDomain::CheckChange() { + bool enable; + if (domain) { - EnableOK(txtDefault->GetValue() != domain->GetDefault() + enable = txtDefault->GetValue() != domain->GetDefault() || chkNotNull->GetValue() != domain->GetNotNull() + || txtCheck->GetValue() != domain->GetCheck() || cbOwner->GetValue() != domain->GetOwner() - || txtComment->GetValue() != domain->GetComment()); + || txtComment->GetValue() != domain->GetComment(); + if (connection->BackendMinimumVersion(9, 2) && !domain->GetValid() && !chkDontValidate->GetValue()) + enable = true; + EnableOK(enable); } else { @@ -187,6 +203,12 @@ void dlgDomain::OnSelChangeTyp(wxCommandEvent &ev) } +void dlgDomain::OnChangeValidate(wxCommandEvent &ev) +{ + CheckChange(); +} + + wxString dlgDomain::GetSql() { wxString sql, name; @@ -211,6 +233,28 @@ wxString dlgDomain::GetSql() else sql += wxT(" SET DEFAULT ") + txtDefault->GetValue() + wxT(";\n"); } + if (txtCheck->GetValue() != domain->GetCheck()) + { + if (!domain->GetCheck().IsEmpty()) + sql += wxT("ALTER DOMAIN ") + schema->GetQuotedPrefix() + qtIdent(name) + + wxT(" DROP CONSTRAINT ") + qtIdent(domain->GetCheckConstraintName()); + + if (!txtCheck->GetValue().IsEmpty()) + { + sql += wxT("ALTER DOMAIN ") + schema->GetQuotedPrefix() + qtIdent(name) + + wxT(" ADD "); + if (!domain->GetCheck().IsEmpty()) + sql += wxT("CONSTRAINT ") + qtIdent(domain->GetCheckConstraintName()); + sql += wxT("\n CHECK (") + txtCheck->GetValue() + wxT(")"); + if (chkDontValidate->GetValue()) + sql += wxT(" NOT VALID"); + } + } + if (chkDontValidate->IsEnabled() && !domain->GetValid() && !chkDontValidate->GetValue()) + { + sql += wxT("ALTER DOMAIN ") + schema->GetQuotedPrefix() + qtIdent(name) + + wxT(" VALIDATE CONSTRAINT ") + qtIdent(domain->GetCheckConstraintName()) + wxT(";\n"); + } AppendOwnerChange(sql, wxT("DOMAIN ") + domain->GetQuotedFullIdentifier()); } else @@ -221,16 +265,24 @@ wxString dlgDomain::GetSql() if (!cbCollation->GetValue().IsEmpty() && cbCollation->GetValue() != wxT("pg_catalog.\"default\"")) sql += wxT("\n COLLATE ") + cbCollation->GetValue(); + + if (chkDontValidate->GetValue()) + sql += wxT(";\nALTER DOMAIN ") + schema->GetQuotedPrefix() + qtIdent(name) + wxT(" ADD "); AppendIfFilled(sql, wxT("\n DEFAULT "), txtDefault->GetValue()); if (chkNotNull->GetValue()) sql += wxT("\n NOT NULL"); if (!txtCheck->GetValue().IsEmpty()) sql += wxT("\n CHECK (") + txtCheck->GetValue() + wxT(")"); + + if (chkDontValidate->GetValue()) + sql += wxT(" NOT VALID"); + sql += wxT(";\n"); AppendOwnerNew(sql, wxT("DOMAIN ") + schema->GetQuotedPrefix() + qtIdent(name)); } + AppendComment(sql, wxT("DOMAIN"), schema, domain); return sql; diff --git a/pgadmin/dlg/dlgTable.cpp b/pgadmin/dlg/dlgTable.cpp index d3ae082..5c9d2d9 100644 --- a/pgadmin/dlg/dlgTable.cpp +++ b/pgadmin/dlg/dlgTable.cpp @@ -1274,9 +1274,9 @@ wxString dlgTable::GetSql() needComma = true; sql += wxT("\n "); - AppendIfFilled(sql, wxT("CONSTRAINT "), qtIdent(name)); - - sql += wxT(" ") + GetItemConstraintType(lstConstraints, pos) + wxT(" ") + definition; + if (!name.IsEmpty()) + sql += wxT("CONSTRAINT ") + qtIdent(name) + wxT(" "); + sql += GetItemConstraintType(lstConstraints, pos) + wxT(" ") + definition; } if (!typedTable || (typedTable && lstConstraints->GetItemCount() > 0)) diff --git a/pgadmin/frm/frmMain.cpp b/pgadmin/frm/frmMain.cpp index cafaa9c..84b964b 100644 --- a/pgadmin/frm/frmMain.cpp +++ b/pgadmin/frm/frmMain.cpp @@ -78,6 +78,8 @@ #include "slony/slCluster.h" #include "slony/slSet.h" #include "schema/pgForeignKey.h" +#include "schema/pgCheck.h" +#include "schema/pgDomain.h" #if wxDIALOG_UNIT_COMPATIBILITY @@ -288,6 +290,8 @@ void frmMain::CreateMenus() new disableAllTriggersFactory(menuFactories, toolsMenu, 0); new enableAllTriggersFactory(menuFactories, toolsMenu, 0); new validateForeignKeyFactory(menuFactories, toolsMenu, 0); + new validateCheckFactory(menuFactories, toolsMenu, 0); + new validateDomainCheckFactory(menuFactories, toolsMenu, 0); toolsMenu->AppendSeparator(); //-------------------------- diff --git a/pgadmin/include/dlg/dlgCheck.h b/pgadmin/include/dlg/dlgCheck.h index bfea4a2..e55ca95 100644 --- a/pgadmin/include/dlg/dlgCheck.h +++ b/pgadmin/include/dlg/dlgCheck.h @@ -37,6 +37,8 @@ public: private: pgCheck *check; pgTable *table; + + void OnChangeValidate(wxCommandEvent &ev); DECLARE_EVENT_TABLE() }; diff --git a/pgadmin/include/dlg/dlgDomain.h b/pgadmin/include/dlg/dlgDomain.h index 497e4f7..91f3ff9 100644 --- a/pgadmin/include/dlg/dlgDomain.h +++ b/pgadmin/include/dlg/dlgDomain.h @@ -31,6 +31,7 @@ public: private: void OnSelChangeTyp(wxCommandEvent &ev); + void OnChangeValidate(wxCommandEvent &ev); pgSchema *schema; pgDomain *domain; diff --git a/pgadmin/include/images/checkbad.png b/pgadmin/include/images/checkbad.png new file mode 100755 index 0000000000000000000000000000000000000000..b983578d06ddd740ae27bfdb4fb61b6b9de9c114 GIT binary patch literal 368 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!63?wyl`GbKJV{wqX6T`Z5GB1Igq5z)|*W;I$ z9KEz~>CU_j2kWoi+fz7MynmbdlCyqukGeOl&{}gNeB<5N_BHxvuCLwtIH_iV^0}KE zyEYllIqtgnyw95J5r;n()Gt<VU#q|IUd+7Xo~M6RPTga_`AF-LkA+7*79IOsvgnlG z^4&%257sp-Rxg+&cIV0Q>xQ%IK~5<N@(X5gcy=QV#7XjYcVXyYmGuB}I14-?iy0WW zg+Z8+Vb&Z8pdfpRr>`sfZ8kYENx`HIM>BvzS)MMAArhCD_ImR*8}PWC-J!RIV`~Eo z`-eOKdrD;zH@??dwCDN!6Y-J@%4=>E&pFjlu{T{^N{1`pW$)!RxBadfxP)wa+|&2N z{G8;^x=CHi?(2i|!j<A=Yv)(bOj$g8quPrN1v^}Bi|apOf4iE4XJVmv4bWBwPgg&e IbxsLQ0KmGJ;Q#;t literal 0 HcmV?d00001 diff --git a/pgadmin/include/schema/pgCheck.h b/pgadmin/include/schema/pgCheck.h index b73e00b..7f37d1f 100644 --- a/pgadmin/include/schema/pgCheck.h +++ b/pgadmin/include/schema/pgCheck.h @@ -24,6 +24,14 @@ public: pgCheckFactory(); virtual dlgProperty *CreateDialog(frmMain *frame, pgObject *node, pgObject *parent); virtual pgObject *CreateObjects(pgCollection *obj, ctlTree *browser, const wxString &restr = wxEmptyString); + + int GetClosedIconId() + { + return closedId; + } + +protected: + int closedId; }; extern pgCheckFactory checkFactory; @@ -34,6 +42,8 @@ public: pgCheck(pgTable *newTable, const wxString &newName = wxT("")); ~pgCheck(); + int GetIconId(); + wxString GetTranslatedMessage(int kindOfMessage) const; void ShowTreeDetail(ctlTree *browser, frmMain *form = 0, ctlListView *properties = 0, ctlSQLBox *sqlPane = 0); @@ -61,6 +71,14 @@ public: { definition = s; } + bool GetValid() const + { + return valid; + } + void iSetValid(const bool b) + { + valid = b; + } bool DropObject(wxFrame *frame, ctlTree *browser, bool cascaded); wxString GetConstraint(); @@ -83,9 +101,11 @@ public: { return true; } + void Validate(frmMain *form); private: wxString definition, fkTable, fkSchema; + bool valid; }; class pgCheckCollection : public pgSchemaObjCollection @@ -95,4 +115,12 @@ public: wxString GetTranslatedMessage(int kindOfMessage) const; }; +class validateCheckFactory : public contextActionFactory +{ +public: + validateCheckFactory(menuFactoryList *list, wxMenu *mnu, ctlMenuToolbar *toolbar); + wxWindow *StartDialog(frmMain *form, pgObject *obj); + bool CheckEnable(pgObject *obj); +}; + #endif diff --git a/pgadmin/include/schema/pgDomain.h b/pgadmin/include/schema/pgDomain.h index 08a8f18..5fc3a02 100644 --- a/pgadmin/include/schema/pgDomain.h +++ b/pgadmin/include/schema/pgDomain.h @@ -164,6 +164,22 @@ public: { typmod = l; } + bool GetValid() const + { + return constraintvalid; + } + void iSetValid(const bool b) + { + constraintvalid = b; + } + wxString GetCheckConstraintName() const + { + return checkconstraintname; + } + void iSetCheckConstraintName(const wxString &s) + { + checkconstraintname = s; + } bool DropObject(wxFrame *frame, ctlTree *browser, bool cascaded); wxString GetSql(ctlTree *browser); @@ -181,12 +197,13 @@ public: { return true; } + void Validate(frmMain *form); private: - wxString basetype, quotedBasetype, defaultVal, delimiter, check, collation, quotedCollation; + wxString basetype, quotedBasetype, defaultVal, delimiter, check, collation, quotedCollation, checkconstraintname; long length, precision, dimensions; long typlen, typmod; - bool notNull, isDup; + bool notNull, isDup, constraintvalid; OID basetypeOid, collationOid; }; @@ -197,4 +214,12 @@ public: wxString GetTranslatedMessage(int kindOfMessage) const; }; +class validateDomainCheckFactory : public contextActionFactory +{ +public: + validateDomainCheckFactory(menuFactoryList *list, wxMenu *mnu, ctlMenuToolbar *toolbar); + wxWindow *StartDialog(frmMain *form, pgObject *obj); + bool CheckEnable(pgObject *obj); +}; + #endif diff --git a/pgadmin/schema/pgCheck.cpp b/pgadmin/schema/pgCheck.cpp index b98b618..c5a9cd6 100644 --- a/pgadmin/schema/pgCheck.cpp +++ b/pgadmin/schema/pgCheck.cpp @@ -14,6 +14,7 @@ // App headers #include "pgAdmin3.h" +#include "frm/frmMain.h" #include "utils/misc.h" #include "schema/pgCheck.h" @@ -94,6 +95,15 @@ wxString pgCheck::GetTranslatedMessage(int kindOfMessage) const } +int pgCheck::GetIconId() +{ + if (!GetDatabase()->BackendMinimumVersion(9, 2) || GetValid()) + return checkFactory.GetIconId(); + else + return checkFactory.GetClosedIconId(); +} + + bool pgCheck::DropObject(wxFrame *frame, ctlTree *browser, bool cascaded) { wxString sql = wxT("ALTER TABLE ") + qtIdent(fkSchema) + wxT(".") + qtIdent(fkTable) @@ -106,7 +116,12 @@ bool pgCheck::DropObject(wxFrame *frame, ctlTree *browser, bool cascaded) wxString pgCheck::GetConstraint() { - return GetQuotedIdentifier() + wxT(" CHECK (") + GetDefinition() + wxT(")"); + sql = GetQuotedIdentifier() + wxT(" CHECK (") + GetDefinition() + wxT(")"); + + if (GetDatabase()->BackendMinimumVersion(9, 2) && !GetValid()) + sql += wxT(" NOT VALID"); + + return sql; } @@ -141,6 +156,8 @@ void pgCheck::ShowTreeDetail(ctlTree *browser, frmMain *form, ctlListView *prope properties->AppendItem(_("Name"), GetName()); properties->AppendItem(_("OID"), GetOid()); properties->AppendItem(_("Definition"), GetDefinition()); + if (GetDatabase()->BackendMinimumVersion(9, 2)) + properties->AppendItem(_("Valid?"), BoolToYesNo(GetValid())); properties->AppendItem(_("Comment"), firstLineOnly(GetComment())); } } @@ -158,21 +175,34 @@ pgObject *pgCheck::Refresh(ctlTree *browser, const wxTreeItemId item) } +void pgCheck::Validate(frmMain *form) +{ + wxString sql = wxT("ALTER TABLE ") + GetQuotedSchemaPrefix(fkSchema) + qtIdent(fkTable) + + wxT("\n VALIDATE CONSTRAINT ") + GetQuotedIdentifier(); + GetDatabase()->ExecuteVoid(sql); + + iSetValid(true); + UpdateIcon(form->GetBrowser()); +} + pgObject *pgCheckFactory::CreateObjects(pgCollection *coll, ctlTree *browser, const wxString &restriction) { pgTableObjCollection *collection = (pgTableObjCollection *)coll; pgCheck *check = 0; - pgSet *checks = collection->GetDatabase()->ExecuteSet( - wxT("SELECT c.oid, conname, relname, nspname, description,\n") - wxT(" pg_get_expr(conbin, conrelid") + collection->GetDatabase()->GetPrettyOption() + wxT(") as consrc\n") - wxT(" FROM pg_constraint c\n") - wxT(" JOIN pg_class cl ON cl.oid=conrelid\n") - wxT(" JOIN pg_namespace nl ON nl.oid=relnamespace\n") - wxT(" LEFT OUTER JOIN pg_description des ON des.objoid=c.oid\n") - wxT(" WHERE contype = 'c' AND conrelid = ") + NumToStr(collection->GetOid()) - + restriction + wxT("::oid\n") - wxT(" ORDER BY conname")); + wxString sql = wxT("SELECT c.oid, conname, relname, nspname, description,\n") + wxT(" pg_get_expr(conbin, conrelid") + collection->GetDatabase()->GetPrettyOption() + wxT(") as consrc\n"); + if (collection->GetDatabase()->BackendMinimumVersion(9, 2)) + sql += wxT(", convalidated"); + sql += wxT(" FROM pg_constraint c\n") + wxT(" JOIN pg_class cl ON cl.oid=conrelid\n") + wxT(" JOIN pg_namespace nl ON nl.oid=relnamespace\n") + wxT(" LEFT OUTER JOIN pg_description des ON des.objoid=c.oid\n") + wxT(" WHERE contype = 'c' AND conrelid = ") + NumToStr(collection->GetOid()) + + restriction + wxT("::oid\n") + wxT(" ORDER BY conname"); + + pgSet *checks = collection->GetDatabase()->ExecuteSet(sql); if (checks) { @@ -184,6 +214,8 @@ pgObject *pgCheckFactory::CreateObjects(pgCollection *coll, ctlTree *browser, co check->iSetDefinition(checks->GetVal(wxT("consrc"))); check->iSetFkTable(checks->GetVal(wxT("relname"))); check->iSetFkSchema(checks->GetVal(wxT("nspname"))); + if (collection->GetDatabase()->BackendMinimumVersion(9, 2)) + check->iSetValid(checks->GetBool(wxT("convalidated"))); check->iSetComment(checks->GetVal(wxT("description"))); if (browser) @@ -225,13 +257,47 @@ wxString pgCheckCollection::GetTranslatedMessage(int kindOfMessage) const ///////////////////////////// #include "images/check.pngc" +#include "images/checkbad.pngc" pgCheckFactory::pgCheckFactory() : pgTableObjFactory(__("Check"), __("New Check..."), __("Create a new Check constraint."), check_png_img) { metaType = PGM_CHECK; collectionFactory = &constraintCollectionFactory; + closedId = addIcon(checkbad_png_img); } pgCheckFactory checkFactory; + +validateCheckFactory::validateCheckFactory(menuFactoryList *list, wxMenu *mnu, ctlMenuToolbar *toolbar) : contextActionFactory(list) +{ + mnu->Append(id, _("Validate check constraint"), _("Validate the selected check constraint.")); +} + + +wxWindow *validateCheckFactory::StartDialog(frmMain *form, pgObject *obj) +{ + ((pgCheck *)obj)->Validate(form); + ((pgCheck *)obj)->SetDirty(); + + wxTreeItemId item = form->GetBrowser()->GetSelection(); + if (obj == form->GetBrowser()->GetObject(item)) + { + obj->ShowTreeDetail(form->GetBrowser(), 0, form->GetProperties()); + form->GetSqlPane()->SetReadOnly(false); + form->GetSqlPane()->SetText(((pgCheck *)obj)->GetSql(form->GetBrowser())); + form->GetSqlPane()->SetReadOnly(true); + } + form->GetMenuFactories()->CheckMenu(obj, form->GetMenuBar(), (ctlMenuToolbar *)form->GetToolBar()); + + return 0; +} + + +bool validateCheckFactory::CheckEnable(pgObject *obj) +{ + return obj && obj->IsCreatedBy(checkFactory) && obj->CanEdit() + && ((pgCheck *)obj)->GetConnection()->BackendMinimumVersion(9, 2) + && !((pgCheck *)obj)->GetValid(); +} diff --git a/pgadmin/schema/pgDomain.cpp b/pgadmin/schema/pgDomain.cpp index 2a2bb2f..71a35e1 100644 --- a/pgadmin/schema/pgDomain.cpp +++ b/pgadmin/schema/pgDomain.cpp @@ -14,6 +14,7 @@ // App headers #include "pgAdmin3.h" +#include "frm/frmMain.h" #include "utils/misc.h" #include "schema/pgDomain.h" #include "schema/pgDatatype.h" @@ -132,7 +133,8 @@ void pgDomain::ShowTreeDetail(ctlTree *browser, frmMain *form, ctlListView *prop if (GetConnection()->BackendMinimumVersion(7, 4)) { pgSet *set = ExecuteSet( - wxT("SELECT conname, pg_get_constraintdef(oid) AS consrc FROM pg_constraint WHERE contypid=") + GetOidStr()); + wxT("SELECT conname, convalidated, pg_get_constraintdef(oid) AS consrc FROM pg_constraint WHERE contypid=") + GetOidStr()); + check = wxEmptyString; if (set) { while (!set->Eof()) @@ -145,6 +147,14 @@ void pgDomain::ShowTreeDetail(ctlTree *browser, frmMain *form, ctlListView *prop if (!conname.StartsWith(wxT("$"))) check += wxT("CONSTRAINT ") + qtIdent(conname) + wxT(" "); check += set->GetVal(wxT("consrc")); + + // there may be more than one constraint + // but there is only one check constraint + if (!set->GetBool(wxT("convalidated"))) + { + iSetCheckConstraintName(set->GetVal(wxT("conname"))); + iSetValid(false); + } set->MoveNext(); } @@ -186,6 +196,17 @@ pgObject *pgDomain::Refresh(ctlTree *browser, const wxTreeItemId item) } +void pgDomain::Validate(frmMain *form) +{ + wxString sql = wxT("ALTER DOMAIN ") + GetQuotedFullIdentifier() + + wxT("\n VALIDATE CONSTRAINT ") + GetCheckConstraintName(); + GetDatabase()->ExecuteVoid(sql); + + iSetValid(true); + UpdateIcon(form->GetBrowser()); +} + + //////////////////////////////////////////////////// @@ -250,6 +271,10 @@ pgObject *pgDomainFactory::CreateObjects(pgCollection *collection, ctlTree *brow } else domain->iSetCollationOid(0); + + // we suppose the constraint valid now + // this is checked in ShowTreeDetail for each domain + domain->iSetValid(true); if (browser) { @@ -312,3 +337,36 @@ pgCollection *pgDomainFactory::CreateCollection(pgObject *obj) pgDomainFactory domainFactory; static pgaCollectionFactory cf(&domainFactory, __("Domains"), domains_png_img); + +validateDomainCheckFactory::validateDomainCheckFactory(menuFactoryList *list, wxMenu *mnu, ctlMenuToolbar *toolbar) : contextActionFactory(list) +{ + mnu->Append(id, _("Validate domain check constraint"), _("Validate the selected domain check constraint.")); +} + + +wxWindow *validateDomainCheckFactory::StartDialog(frmMain *form, pgObject *obj) +{ + ((pgDomain *)obj)->Validate(form); + ((pgDomain *)obj)->SetDirty(); + + wxTreeItemId item = form->GetBrowser()->GetSelection(); + if (obj == form->GetBrowser()->GetObject(item)) + { + obj->ShowTreeDetail(form->GetBrowser(), 0, form->GetProperties()); + form->GetSqlPane()->SetReadOnly(false); + form->GetSqlPane()->SetText(((pgDomain *)obj)->GetSql(form->GetBrowser())); + form->GetSqlPane()->SetReadOnly(true); + } + form->GetMenuFactories()->CheckMenu(obj, form->GetMenuBar(), (ctlMenuToolbar *)form->GetToolBar()); + + return 0; +} + + +bool validateDomainCheckFactory::CheckEnable(pgObject *obj) +{ + return obj && obj->IsCreatedBy(domainFactory) && obj->CanEdit() + && ((pgDomain *)obj)->GetConnection()->BackendMinimumVersion(9, 2) + && !((pgDomain *)obj)->GetValid(); +} + diff --git a/pgadmin/schema/pgTable.cpp b/pgadmin/schema/pgTable.cpp index a8c6b7b..5cf9ed1 100644 --- a/pgadmin/schema/pgTable.cpp +++ b/pgadmin/schema/pgTable.cpp @@ -448,6 +448,8 @@ wxString pgTable::GetSql(ctlTree *browser) break; case PGM_CHECK: cols_sql += wxT("(") + ((pgCheck *)data)->GetDefinition() + wxT(")"); + if (GetDatabase()->BackendMinimumVersion(9, 2) && !((pgCheck *)data)->GetValid()) + cols_sql += wxT(" NOT VALID"); break; } } diff --git a/pgadmin/ui/dlgCheck.xrc b/pgadmin/ui/dlgCheck.xrc index d583e77..1c5ece4 100644 --- a/pgadmin/ui/dlgCheck.xrc +++ b/pgadmin/ui/dlgCheck.xrc @@ -73,7 +73,7 @@ <object class="wxPanel" name="pnlDefinition"> <object class="wxFlexGridSizer"> <cols>2</cols> - <rows>1</rows> + <rows>2</rows> <vgap>5</vgap> <hgap>5</hgap> <growablerows>0</growablerows> @@ -92,6 +92,20 @@ <flag>wxEXPAND|wxALIGN_CENTER_VERTICAL|wxALL</flag> <border>4</border> </object> + <object class="sizeritem"> + <object class="wxStaticText" name="stDontValidate"> + <label>Don't validate</label> + </object> + <flag>wxALIGN_CENTRE_VERTICAL|wxTOP|wxLEFT|wxRIGHT</flag> + <border>4</border> + </object> + <object class="sizeritem"> + <object class="wxCheckBox" name="chkDontValidate"> + <label></label> + </object> + <flag>wxEXPAND|wxALIGN_CENTER_VERTICAL|wxTOP|wxLEFT|wxRIGHT</flag> + <border>4</border> + </object> <flag>wxEXPAND|wxTOP|wxLEFT|wxRIGHT</flag> </object> </object> diff --git a/pgadmin/ui/dlgDomain.xrc b/pgadmin/ui/dlgDomain.xrc index 265ab1d..c0ca9c7 100644 --- a/pgadmin/ui/dlgDomain.xrc +++ b/pgadmin/ui/dlgDomain.xrc @@ -100,7 +100,7 @@ <object class="wxPanel" name="pnlDefinition"> <object class="wxFlexGridSizer"> <cols>2</cols> - <rows>6</rows> + <rows>7</rows> <vgap>5</vgap> <hgap>5</hgap> <growablerows>2</growablerows> @@ -147,6 +147,20 @@ <border>4</border> </object> <object class="sizeritem"> + <object class="wxStaticText" name="stDontValidate"> + <label>Don't validate</label> + </object> + <flag>wxALIGN_CENTRE_VERTICAL|wxTOP|wxLEFT|wxRIGHT</flag> + <border>4</border> + </object> + <object class="sizeritem"> + <object class="wxCheckBox" name="chkDontValidate"> + <label></label> + </object> + <flag>wxEXPAND|wxALIGN_CENTER_VERTICAL|wxTOP|wxLEFT|wxRIGHT</flag> + <border>4</border> + </object> + <object class="sizeritem"> <object class="wxStaticText" name="stLength"> <label>Length</label> </object> -- 1.7.6
-- Sent via pgadmin-hackers mailing list (pgadmin-hackers@postgresql.org) To make changes to your subscription: http://www.postgresql.org/mailpref/pgadmin-hackers