This is a discussion on Enable/disable trigger path within the pgsql Interfaces Pgadmin Hackers forums, part of the PostgreSQL category; --> Hi all, Here is my first patch to support enable/disable trigger. This functionnality is available since release 8.1 of ...
| |||||||
| FAQ | Members List | Calendar | Search | Today's Posts | Mark Forums Read |
| ||||
| Hi all, Here is my first patch to support enable/disable trigger. This functionnality is available since release 8.1 of PostgreSQL. Im' not really happy with my code. I have some code to enable a trigger and some code to disable it. I think it would be better to merge them since they are pretty close. For example, I use two menus (Enable trigger and Disable trigger). It would be better to use just one but I don't know what to do : * rename the menu's title * use a checked menu. Or perhaps two menus are just fine. Any advice on this ? Also, I would like to add enable/disable all triggers but I don't know where I should put the menu item : on the table name's contextual menu ? on the "Triggers" contextual menu ? Thanks for any tips on this matter. Regards. -- Guillaume. <!-- http://abs.traduc.org/ http://lfs.traduc.org/ http://docs.postgresqlfr.org/ --> Index: pgadmin/include/schema/pgTrigger.h ================================================== ================= --- pgadmin/include/schema/pgTrigger.h (révision 5866) +++ pgadmin/include/schema/pgTrigger.h (copie de travail) @@ -57,6 +57,8 @@ bool DropObject(wxFrame *frame, ctlTree *browser, bool cascaded); wxString GetSql(ctlTree *browser); pgObject *Refresh(ctlTree *browser, const wxTreeItemId item); + bool EnableTrigger(); + bool DisableTrigger(); bool HasStats() { return false; } bool HasDepends() { return true; } Index: pgadmin/include/dlg/dlgTrigger.h ================================================== ================= --- pgadmin/include/dlg/dlgTrigger.h (révision 5866) +++ pgadmin/include/dlg/dlgTrigger.h (copie de travail) @@ -39,4 +39,21 @@ }; +class enableTriggerFactory : public contextActionFactory +{ +public: + enableTriggerFactory(menuFactoryList *list, wxMenu *mnu, wxToolBar *toolbar); + wxWindow *StartDialog(frmMain *form, pgObject *obj); + bool CheckEnable(pgObject *obj); +}; + + +class disableTriggerFactory : public contextActionFactory +{ +public: + disableTriggerFactory(menuFactoryList *list, wxMenu *mnu, wxToolBar *toolbar); + wxWindow *StartDialog(frmMain *form, pgObject *obj); + bool CheckEnable(pgObject *obj); +}; + #endif Index: pgadmin/frm/frmMain.cpp ================================================== ================= --- pgadmin/frm/frmMain.cpp (révision 5866) +++ pgadmin/frm/frmMain.cpp (copie de travail) @@ -63,6 +63,7 @@ #include "dlg/dlgServer.h" #include "dlg/dlgDatabase.h" #include "dlg/dlgTable.h" +#include "dlg/dlgTrigger.h" #include "dlg/dlgServer.h" #include "slony/dlgRepCluster.h" #include "slony/dlgRepSet.h" @@ -258,6 +259,8 @@ actionFactory *refFact=new refreshFactory(menuFactories, viewMenu, toolBar); new countRowsFactory(menuFactories, viewMenu, 0); new executePgstattupleFactory(menuFactories, viewMenu, 0); + new enableTriggerFactory(menuFactories, viewMenu, 0); + new disableTriggerFactory(menuFactories, viewMenu, 0); //-------------------------- Index: pgadmin/schema/pgTrigger.cpp ================================================== ================= --- pgadmin/schema/pgTrigger.cpp (révision 5866) +++ pgadmin/schema/pgTrigger.cpp (copie de travail) @@ -48,6 +48,20 @@ } +bool pgTrigger::EnableTrigger() +{ + wxString sql = wxT("ALTER TABLE ") + GetQuotedFullTable() + wxT(" ENABLE TRIGGER ") + GetQuotedIdentifier(); + return GetDatabase()->ExecuteVoid(sql); +} + + +bool pgTrigger: +{ + wxString sql = wxT("ALTER TABLE ") + GetQuotedFullTable() + wxT(" DISABLE TRIGGER ") + GetQuotedIdentifier(); + return GetDatabase()->ExecuteVoid(sql); +} + + void pgTrigger::SetDirty() { if (expandedKids) Index: pgadmin/dlg/dlgTrigger.cpp ================================================== ================= --- pgadmin/dlg/dlgTrigger.cpp (révision 5866) +++ pgadmin/dlg/dlgTrigger.cpp (copie de travail) @@ -15,6 +15,7 @@ // App headers #include "pgAdmin3.h" #include "utils/misc.h" +#include "frm/frmMain.h" #include "utils/pgDefs.h" #include "dlg/dlgTrigger.h" @@ -208,3 +209,58 @@ EnableOK(enable); } } + +enableTriggerFactory::enableTriggerFactory(menuFa ctoryList *list, wxMenu *mnu, wxToolBar *toolbar) : contextActionFactory(list) +{ + mnu->Append(id, _("&Enable trigger"), _("Enable trigger.")); +} + + +wxWindow *enableTriggerFactory::StartDialog(frmMain *form, pgObject *obj) +{ + if (((pgTrigger*)obj)->EnableTrigger()) + ((pgTrigger*)obj)->iSetEnabled(true); + + wxTreeItemId item=form->GetBrowser()->GetSelection(); + { + obj->ShowTreeDetail(form->GetBrowser(), 0, form->GetProperties()); + form->GetMenuFactories()->CheckMenu(obj, form->GetMenuBar(), form->GetToolBar()); + } + + return 0; +} + + +bool enableTriggerFactory::CheckEnable(pgObject *obj) +{ + return obj && obj->IsCreatedBy(triggerFactory) && ! ((pgTrigger*)obj)->GetEnabled() + && ((pgTrigger*)obj)->GetConnection()->BackendMinimumVersion(8, 1); +} + +disableTriggerFactory::disableTriggerFactory(menu FactoryList *list, wxMenu *mnu, wxToolBar *toolbar) : contextActionFactory(list) +{ + mnu->Append(id, _("&Disable trigger"), _("Disable trigger.")); +} + + +wxWindow *disableTriggerFactory::StartDialog(frmMain *form, pgObject *obj) +{ + if (((pgTrigger*)obj)->DisableTrigger()) + ((pgTrigger*)obj)->iSetEnabled(false); + + wxTreeItemId item=form->GetBrowser()->GetSelection(); + if (obj == form->GetBrowser()->GetObject(item)) + { + obj->ShowTreeDetail(form->GetBrowser(), 0, form->GetProperties()); + form->GetMenuFactories()->CheckMenu(obj, form->GetMenuBar(), form->GetToolBar()); + } + + return 0; +} + + +bool disableTriggerFactory::CheckEnable(pgObject *obj) +{ + return obj && obj->IsCreatedBy(triggerFactory) && ((pgTrigger*)obj)->GetEnabled() + && ((pgTrigger*)obj)->GetConnection()->BackendMinimumVersion(8, 1); +} ---------------------------(end of broadcast)--------------------------- TIP 1: if posting/reading through Usenet, please send an appropriate subscribe-nomail command to majordomo@postgresql.org so that your message can get through to the mailing list cleanly |
| |||
| Guillaume Lelarge wrote: > Hi all, > > Here is my first patch to support enable/disable trigger. This > functionnality is available since release 8.1 of PostgreSQL. Im' not > really happy with my code. I have some code to enable a trigger and some > code to disable it. I think it would be better to merge them since they > are pretty close. For example, I use two menus (Enable trigger and > Disable trigger). It would be better to use just one but I don't know > what to do : > * rename the menu's title > * use a checked menu. > > Or perhaps two menus are just fine. Any advice on this ? > > Also, I would like to add enable/disable all triggers but I don't know > where I should put the menu item : on the table name's contextual menu ? > on the "Triggers" contextual menu ? > > Thanks for any tips on this matter. Bullet pointed tips, purely because that's how they escaped from my brain :-) - This should be on the Tools menu, not the View menu. - Use a single factory, and a check/uncheck menu option. See the changes I made to the pg_stattuple stuff as an example of a check option. - The menu option should probably become something like 'Trigger enabled?' - pgTrigger::Enable/DisableTrigger should manage the state of the enabled flag themselves - you should not have to change that from the factory. - If Enable/Disable trigger don't work for some reason, StartDialog should exit without doing anything else as a general rule. Otherwise it looks OK though - certainly looks like you've got the hang of the factories :-) Regards, Dave. ---------------------------(end of broadcast)--------------------------- TIP 3: Have you checked our extensive FAQ? http://www.postgresql.org/docs/faq |
| |||
| Dave Page a écrit : > [...] > Bullet pointed tips, purely because that's how they escaped from my > brain :-) > > - This should be on the Tools menu, not the View menu. > I don't understand what you mean by this. I put them on the Tools contextual menu but I don't see a View contextual menu. Can you give me more details ? > - Use a single factory, and a check/uncheck menu option. See the changes > I made to the pg_stattuple stuff as an example of a check option. > Done. > - The menu option should probably become something like 'Trigger enabled?' > Done too. > - pgTrigger::Enable/DisableTrigger should manage the state of the > enabled flag themselves - you should not have to change that from the > factory. > OK. I discarded pgTrigger::Enable/DisableTrigger to use pgTrigger::iSetEnabled. Everything takes place in this method. > - If Enable/Disable trigger don't work for some reason, StartDialog > should exit without doing anything else as a general rule. > OK. > Otherwise it looks OK though - certainly looks like you've got the hang > of the factories :-) > Hehe... I added some code to make use of the "ENABLE/DISABLE TRIGGER ALL" on a table. You'll find my new patch attached. Regards. -- Guillaume. <!-- http://abs.traduc.org/ http://lfs.traduc.org/ http://docs.postgresqlfr.org/ --> Index: pgadmin/include/schema/pgTable.h ================================================== ================= --- pgadmin/include/schema/pgTable.h (révision 5875) +++ pgadmin/include/schema/pgTable.h (copie de travail) @@ -78,6 +78,8 @@ void iSetHasSubclass(bool b) { hasSubclass = b; } void iSetIsReplicated(bool b) { isReplicated = b; } bool GetIsReplicated() const { return isReplicated; } + bool GetAllTriggersEnabled(); + void iSetAllTriggersEnabled(const bool b); void UpdateRows(); bool DropObject(wxFrame *frame, ctlTree *browser, bool cascaded); bool CanView() { return true; } @@ -110,7 +112,7 @@ void AppendStuff(wxString &sql, ctlTree *browser, pgaFactory &factory); wxULongLong rows; double estimatedRows; - bool hasOids, hasSubclass, rowsCounted, isReplicated, showExtendedStatistics; + bool hasOids, hasSubclass, rowsCounted, isReplicated, showExtendedStatistics, allTriggersEnabled; long inheritedTableCount; wxString quotedInheritedTables, inheritedTables, primaryKey, quotedPrimaryKey, primaryKeyName, primaryKeyColNumbers, tablespace; Index: pgadmin/include/schema/pgTrigger.h ================================================== ================= --- pgadmin/include/schema/pgTrigger.h (révision 5875) +++ pgadmin/include/schema/pgTrigger.h (copie de travail) @@ -45,7 +45,7 @@ long GetTriggerType() const {return triggerType; } void iSetTriggerType(const long l) { triggerType=l; } bool GetEnabled() const { return enabled; } - void iSetEnabled(const bool b) {enabled=b; } + void iSetEnabled(const bool b); void iSetTriggerFunction(pgFunction *fkt) { triggerFunction=fkt; } wxString GetQuotedFullTable() const { return quotedFullTable; } void iSetQuotedFullTable(const wxString &s) { quotedFullTable=s; } Index: pgadmin/include/dlg/dlgTrigger.h ================================================== ================= --- pgadmin/include/dlg/dlgTrigger.h (révision 5875) +++ pgadmin/include/dlg/dlgTrigger.h (copie de travail) @@ -39,4 +39,14 @@ }; +class enabledisableTriggerFactory : public contextActionFactory +{ +public: + enabledisableTriggerFactory(menuFactoryList *list, wxMenu *mnu, wxToolBar *toolbar); + wxWindow *StartDialog(frmMain *form, pgObject *obj); + bool CheckEnable(pgObject *obj); + bool CheckChecked(pgObject *obj); +}; + + #endif Index: pgadmin/include/dlg/dlgTable.h ================================================== ================= --- pgadmin/include/dlg/dlgTable.h (révision 5875) +++ pgadmin/include/dlg/dlgTable.h (copie de travail) @@ -92,4 +92,15 @@ bool CheckChecked(pgObject *obj); }; + +class enabledisableAllTriggersFactory : public contextActionFactory +{ +public: + enabledisableAllTriggersFactory(menuFactoryList *list, wxMenu *mnu, wxToolBar *toolbar); + wxWindow *StartDialog(frmMain *form, pgObject *obj); + bool CheckEnable(pgObject *obj); + bool CheckChecked(pgObject *obj); +}; + + #endif Index: pgadmin/frm/frmMain.cpp ================================================== ================= --- pgadmin/frm/frmMain.cpp (révision 5875) +++ pgadmin/frm/frmMain.cpp (copie de travail) @@ -63,6 +63,7 @@ #include "dlg/dlgServer.h" #include "dlg/dlgDatabase.h" #include "dlg/dlgTable.h" +#include "dlg/dlgTrigger.h" #include "dlg/dlgServer.h" #include "slony/dlgRepCluster.h" #include "slony/dlgRepSet.h" @@ -258,8 +259,10 @@ actionFactory *refFact=new refreshFactory(menuFactories, viewMenu, toolBar); new countRowsFactory(menuFactories, viewMenu, 0); new executePgstattupleFactory(menuFactories, viewMenu, 0); + new enabledisableTriggerFactory(menuFactories, viewMenu, 0); + new enabledisableAllTriggersFactory(menuFactories, viewMenu, 0); - + //-------------------------- new separatorFactory(menuFactories); Index: pgadmin/schema/pgTable.cpp ================================================== ================= --- pgadmin/schema/pgTable.cpp (révision 5875) +++ pgadmin/schema/pgTable.cpp (copie de travail) @@ -408,6 +408,30 @@ } +void pgTable::iSetAllTriggersEnabled(const bool b) +{ + if (((allTriggersEnabled && !b) || (!allTriggersEnabled && b))) + { + wxString sql = wxT("ALTER TABLE ") + GetQuotedFullIdentifier() + wxT(" "); + if (allTriggersEnabled && !b) + sql += wxT("DISABLE"); + else if (!allTriggersEnabled && b) + sql += wxT("ENABLE"); + sql += wxT(" TRIGGER ALL"); +printf((sql + wxT("\n")).ToAscii()); + GetDatabase()->ExecuteVoid(sql); + } + + allTriggersEnabled=b; +} + + +bool pgTable::GetAllTriggersEnabled() +{ + return allTriggersEnabled; +} + + void pgTable::UpdateRows() { pgSet *props = ExecuteSet(wxT("SELECT count(*) AS rows FROM ONLY ") + GetQuotedFullIdentifier()); Index: pgadmin/schema/pgTrigger.cpp ================================================== ================= --- pgadmin/schema/pgTrigger.cpp (révision 5875) +++ pgadmin/schema/pgTrigger.cpp (copie de travail) @@ -48,6 +48,23 @@ } +void pgTrigger::iSetEnabled(const bool b) +{ + if (GetQuotedFullTable().Len() > 0 && ((enabled && !b) || (!enabled && b))) + { + wxString sql = wxT("ALTER TABLE ") + GetQuotedFullTable() + wxT(" "); + if (enabled && !b) + sql += wxT("DISABLE"); + else if (!enabled && b) + sql += wxT("ENABLE"); + sql += wxT(" TRIGGER ") + GetQuotedIdentifier(); + GetDatabase()->ExecuteVoid(sql); + } + + enabled=b; +} + + void pgTrigger::SetDirty() { if (expandedKids) Index: pgadmin/dlg/dlgTable.cpp ================================================== ================= --- pgadmin/dlg/dlgTable.cpp (révision 5875) +++ pgadmin/dlg/dlgTable.cpp (copie de travail) @@ -1205,4 +1205,34 @@ bool executePgstattupleFactory::CheckChecked(pgObject *obj) { return obj && ((pgTable*)obj)->GetShowExtendedStatistics(); -} \ Pas de fin de ligne Ã* la fin du fichier +} + +enabledisableAllTriggersFactory::enabledisableAll TriggersFactory(menuFactoryList *list, wxMenu *mnu, wxToolBar *toolbar) : contextActionFactory(list) +{ + mnu->Append(id, _("All table's triggers enabled?"), _("Enable or disable all triggers on selected table."), wxITEM_CHECK); +} + + +wxWindow *enabledisableAllTriggersFactory::StartDialog(frmM ain *form, pgObject *obj) +{ + ((pgTable*)obj)->iSetAllTriggersEnabled(!((pgTable*)obj)->GetAllTriggersEnabled()); + + wxTreeItemId item=form->GetBrowser()->GetSelection(); + if (obj == form->GetBrowser()->GetObject(item)) + obj->ShowTreeDetail(form->GetBrowser(), 0, form->GetProperties()); + form->GetMenuFactories()->CheckMenu(obj, form->GetMenuBar(), form->GetToolBar()); + + return 0; +} + + +bool enabledisableAllTriggersFactory::CheckEnable(pgObj ect *obj) +{ + return obj && obj->IsCreatedBy(tableFactory) + && ((pgTable*)obj)->GetConnection()->BackendMinimumVersion(8, 1); +} + +bool enabledisableAllTriggersFactory::CheckChecked(pgOb ject *obj) +{ + return obj && obj->IsCreatedBy(tableFactory) && ((pgTable*)obj)->GetAllTriggersEnabled(); +} Index: pgadmin/dlg/dlgTrigger.cpp ================================================== ================= --- pgadmin/dlg/dlgTrigger.cpp (révision 5875) +++ pgadmin/dlg/dlgTrigger.cpp (copie de travail) @@ -15,6 +15,7 @@ // App headers #include "pgAdmin3.h" #include "utils/misc.h" +#include "frm/frmMain.h" #include "utils/pgDefs.h" #include "dlg/dlgTrigger.h" @@ -208,3 +209,34 @@ EnableOK(enable); } } + + +enabledisableTriggerFactory::enabledisableTrigger Factory(menuFactoryList *list, wxMenu *mnu, wxToolBar *toolbar) : contextActionFactory(list) +{ + mnu->Append(id, _("Trigger enabled?"), _("Enable or disable selected trigger."), wxITEM_CHECK); +} + + +wxWindow *enabledisableTriggerFactory::StartDialog(frmMain *form, pgObject *obj) +{ + ((pgTrigger*)obj)->iSetEnabled(!((pgTrigger*)obj)->GetEnabled()); + + wxTreeItemId item=form->GetBrowser()->GetSelection(); + if (obj == form->GetBrowser()->GetObject(item)) + obj->ShowTreeDetail(form->GetBrowser(), 0, form->GetProperties()); + form->GetMenuFactories()->CheckMenu(obj, form->GetMenuBar(), form->GetToolBar()); + + return 0; +} + + +bool enabledisableTriggerFactory::CheckEnable(pgObject *obj) +{ + return obj && obj->IsCreatedBy(triggerFactory) + && ((pgTrigger*)obj)->GetConnection()->BackendMinimumVersion(8, 1); +} + +bool enabledisableTriggerFactory::CheckChecked(pgObject *obj) +{ + return obj && obj->IsCreatedBy(triggerFactory) && ((pgTrigger*)obj)->GetEnabled(); +} ---------------------------(end of broadcast)--------------------------- TIP 7: You can help support the PostgreSQL project by donating at http://www.postgresql.org/about/donate |
| ||||
| OK, nearly there... :-) Guillaume Lelarge wrote: > Dave Page a écrit : >> [...] >> Bullet pointed tips, purely because that's how they escaped from my >> brain :-) >> >> - This should be on the Tools menu, not the View menu. >> > > I don't understand what you mean by this. I put them on the Tools > contextual menu but I don't see a View contextual menu. Can you give me > more details ? You had: + new enabledisableTriggerFactory(menuFactories, viewMenu, 0); + new enabledisableAllTriggersFactory(menuFactories, viewMenu, 0); but that should be + new enabledisableTriggerFactory(menuFactories, toolsMenu, 0); + new enabledisableAllTriggersFactory(menuFactories, toolsMenu, 0); Enabling/disabling triggers is something you do, not something you look at. Anyhoo, I've applied a modifed version of the patch: - Added a heap of refatoring to move actionFactories to live with the objects they ac on, rather than the object's properties dialog. - Changed enable/disable all to two factories. This is because we cannot easily track the state of all triggers, and we definitely cannot represent all enabled/some enabled/none enabled with a check menu item. We now have enable all and disable all options, with no attempt to track status. - Recursively reset the enabled flag of the trigger objects under a table after enabling/disabling them all. Thanks, Dave ---------------------------(end of broadcast)--------------------------- TIP 2: Don't 'kill -9' the postmaster |
| Thread Tools | |
| Display Modes | |
|
|