1 
2 ///////////////////////////////////////////////////////////
3 //                                                       //
4 //                         SAGA                          //
5 //                                                       //
6 //      System for Automated Geoscientific Analyses      //
7 //                                                       //
8 //                    User Interface                     //
9 //                                                       //
10 //                    Program: SAGA                      //
11 //                                                       //
12 //-------------------------------------------------------//
13 //                                                       //
14 //                 data_source_pgsql.cpp                 //
15 //                                                       //
16 //          Copyright (C) 2013 by Olaf Conrad            //
17 //                                                       //
18 //-------------------------------------------------------//
19 //                                                       //
20 // This file is part of 'SAGA - System for Automated     //
21 // Geoscientific Analyses'. SAGA is free software; you   //
22 // can redistribute it and/or modify it under the terms  //
23 // of the GNU General Public License as published by the //
24 // Free Software Foundation, either version 2 of the     //
25 // License, or (at your option) any later version.       //
26 //                                                       //
27 // SAGA is distributed in the hope that it will be       //
28 // useful, but WITHOUT ANY WARRANTY; without even the    //
29 // implied warranty of MERCHANTABILITY or FITNESS FOR A  //
30 // PARTICULAR PURPOSE. See the GNU General Public        //
31 // License for more details.                             //
32 //                                                       //
33 // You should have received a copy of the GNU General    //
34 // Public License along with this program; if not, see   //
35 // <http://www.gnu.org/licenses/>.                       //
36 //                                                       //
37 //-------------------------------------------------------//
38 //                                                       //
39 //    contact:    Olaf Conrad                            //
40 //                Institute of Geography                 //
41 //                University of Hamburg                  //
42 //                Germany                                //
43 //                                                       //
44 //    e-mail:     oconrad@saga-gis.org                   //
45 //                                                       //
46 ///////////////////////////////////////////////////////////
47 
48 //---------------------------------------------------------
49 #include <wx/menu.h>
50 
51 #include "helper.h"
52 
53 #include "res_controls.h"
54 #include "res_commands.h"
55 #include "res_dialogs.h"
56 #include "res_images.h"
57 
58 #include "wksp.h"
59 #include "wksp_data_manager.h"
60 
61 #include "data_source.h"
62 #include "data_source_pgsql.h"
63 
64 
65 ///////////////////////////////////////////////////////////
66 //														 //
67 //														 //
68 //														 //
69 ///////////////////////////////////////////////////////////
70 
71 //---------------------------------------------------------
72 enum
73 {
74 	TYPE_ROOT	= 0,
75 	TYPE_SERVER,
76 	TYPE_SOURCE,
77 	TYPE_TABLE,
78 	TYPE_SHAPES,
79 	TYPE_GRIDS,
80 	TYPE_GRID
81 };
82 
83 //---------------------------------------------------------
84 enum
85 {
86 	IMG_ROOT	= 0,
87 	IMG_SERVER,
88 	IMG_SRC_CLOSED,
89 	IMG_SRC_OPENED,
90 	IMG_TABLE,
91 	IMG_POINT,
92 	IMG_POINTS,
93 	IMG_LINE,
94 	IMG_POLYGON,
95 	IMG_GRIDS,
96 	IMG_GRID
97 };
98 
99 //---------------------------------------------------------
100 enum
101 {
102 	DB_PGSQL_Get_Connections	=  0,
103 	DB_PGSQL_Get_Connection		=  1,
104 	DB_PGSQL_Del_Connection		=  2,
105 	DB_PGSQL_Del_Connections	=  3,
106 	DB_PGSQL_Transaction_Start	=  4,
107 	DB_PGSQL_Transaction_Stop	=  5,
108 	DB_PGSQL_Execute_SQL		=  6,
109 
110 	DB_PGSQL_Table_List			= 10,
111 	DB_PGSQL_Table_Info			= 11,
112 	DB_PGSQL_Table_Load			= 12,
113 	DB_PGSQL_Table_Save			= 13,
114 	DB_PGSQL_Table_Drop			= 14,
115 	DB_PGSQL_Table_Query		= 15,
116 
117 	DB_PGSQL_Shapes_Load		= 20,
118 	DB_PGSQL_Shapes_Save		= 21,
119 	DB_PGSQL_Shapes_SRID_Update	= 22,
120 
121 	DB_PGSQL_Raster_Load		= 30,
122 	DB_PGSQL_Raster_Load_Band	= 33,
123 	DB_PGSQL_Raster_Save		= 31,
124 	DB_PGSQL_Rasters_Save		= 34,
125 	DB_PGSQL_Raster_SRID_Update	= 32,
126 
127 	DB_PGSQL_DB_Create			= 35,
128 	DB_PGSQL_DB_Drop			= 36
129 };
130 
131 //---------------------------------------------------------
132 static	wxString	g_Username	= "postgres";
133 static	wxString	g_Password	= "postgres";
134 
135 
136 ///////////////////////////////////////////////////////////
137 //														 //
138 //														 //
139 //														 //
140 ///////////////////////////////////////////////////////////
141 
142 //---------------------------------------------------------
143 #define RUN_TOOL(TOOL, bManager, bVerbose, CONDITION)	bool bResult = false;\
144 {\
145 	CSG_Tool	*pTool	= SG_Get_Tool_Library_Manager().Create_Tool("db_pgsql", TOOL, true);\
146 	\
147 	if(	pTool )\
148 	{\
149 		if( !bVerbose ) SG_UI_Msg_Lock(true);\
150 		pTool->On_Before_Execution();\
151 		if( !bManager ) pTool->Set_Manager(NULL);\
152 		bResult	= (CONDITION) && pTool->Execute();\
153 		if( !bVerbose ) SG_UI_Msg_Lock(false);\
154 		SG_Get_Tool_Library_Manager().Delete_Tool(pTool);\
155 	}\
156 }
157 
158 //---------------------------------------------------------
159 #define SET_PARAMETER(IDENTIFIER, VALUE)	pTool->Set_Parameter(IDENTIFIER, VALUE)
160 
161 
162 ///////////////////////////////////////////////////////////
163 //														 //
164 //														 //
165 //														 //
166 ///////////////////////////////////////////////////////////
167 
168 //---------------------------------------------------------
169 #include <wx/socket.h>
170 
171 //---------------------------------------------------------
is_Server_Responding(const CSG_String & Host,const CSG_String & Port,int Seconds)172 bool	is_Server_Responding	(const CSG_String &Host, const CSG_String &Port, int Seconds)
173 {
174 	wxIPV4address	Address;
175 
176 	if( !Address.Hostname(Host.c_str()) )
177 	{
178 		return( false );
179 	}
180 
181 	if( !Port.is_Empty() && !Address.Service(Port.c_str()) )
182 	{
183 		return( false );
184 	}
185 
186 	wxSocketClient	Client;
187 
188 	Client.Connect(Address, false);
189 
190 	if( !Client.IsConnected() && Seconds > 0 )
191 	{
192 		Client.WaitOnConnect(Seconds, 0);
193 	}
194 
195 	return( Client.IsConnected() );
196 }
197 
198 
199 ///////////////////////////////////////////////////////////
200 //														 //
201 //														 //
202 //														 //
203 ///////////////////////////////////////////////////////////
204 
205 //---------------------------------------------------------
PGSQL_Connect(const CSG_String & Host,const CSG_String & Port,const CSG_String & DBName)206 bool	PGSQL_Connect			(const CSG_String &Host, const CSG_String &Port, const CSG_String &DBName)
207 {
208 	if( PGSQL_is_Connected(Host, Port, DBName) )
209 	{
210 		return( true );
211 	}
212 
213 	if( !DLG_Login(g_Username, g_Password, wxString::Format("%s: %s [%s:%s]", _TL("Connect to Database"), DBName.c_str(), Host.c_str(), Port.c_str())) )
214 	{
215 		return( false );
216 	}
217 
218 	if( !is_Server_Responding(Host, Port, g_pData->Get_Parameter("PROJECT_DB_WAIT")->asInt()) )
219 	{
220 		return( false );
221 	}
222 
223 	RUN_TOOL(DB_PGSQL_Get_Connection, false, true,	// CGet_Connection
224 			SET_PARAMETER("PG_HOST", Host  )
225 		&&	SET_PARAMETER("PG_PORT", Port  )
226 		&&	SET_PARAMETER("PG_NAME", DBName)
227 		&&	SET_PARAMETER("PG_USER", CSG_String(&g_Username))
228 		&&	SET_PARAMETER("PG_PWD" , CSG_String(&g_Password))
229 	);
230 
231 	if( bResult )
232 	{
233 		CSG_String	Server	= DBName + " [" + Host + ":" + Port + "]";
234 
235 		g_pData_Source->Get_PgSQL()->Update_Source(Server.c_str(), g_Username, g_Password);
236 	}
237 
238 	return( bResult );
239 }
240 
241 //---------------------------------------------------------
PGSQL_is_Connected(const CSG_String & Host,const CSG_String & Port,const CSG_String & DBName)242 bool	PGSQL_is_Connected		(const CSG_String &Host, const CSG_String &Port, const CSG_String &DBName)
243 {
244 	return( PGSQL_is_Connected(DBName + " [" + Host + ":" + Port + "]") );
245 }
246 
247 //---------------------------------------------------------
PGSQL_is_Connected(const CSG_String & Server)248 bool	PGSQL_is_Connected		(const CSG_String &Server)
249 {
250 	CSG_Table	Connections;
251 
252 	RUN_TOOL(DB_PGSQL_Get_Connections, false, false, SET_PARAMETER("CONNECTIONS", &Connections));	// CGet_Connections
253 
254 	for(int i=0; bResult && i<Connections.Get_Count(); i++)
255 	{
256 		if( !Server.Cmp(Connections[i].asString(0)) )
257 		{
258 			return( true );
259 		}
260 	}
261 
262 	return( false );
263 }
264 
265 
266 ///////////////////////////////////////////////////////////
267 //														 //
268 ///////////////////////////////////////////////////////////
269 
270 //---------------------------------------------------------
PGSQL_Get_Connections(CSG_Strings & Servers,double vPostGIS)271 bool	PGSQL_Get_Connections	(CSG_Strings &Servers, double vPostGIS)
272 {
273 	Servers.Clear();
274 
275 	CSG_Table	Connections;
276 
277 	RUN_TOOL(DB_PGSQL_Get_Connections, false, false, SET_PARAMETER("CONNECTIONS", &Connections));	// CGet_Connections
278 
279 	for(int i=0; bResult && i<Connections.Get_Count(); i++)
280 	{
281 		if( vPostGIS <= 0.0 || vPostGIS <= Connections[i].asDouble("PostGIS") )
282 		{
283 			Servers	+= Connections[i].asString(0);
284 		}
285 	}
286 
287 	return( Servers.Get_Count() > 0 );
288 }
289 
290 //---------------------------------------------------------
PGSQL_has_Connections(double vPostGIS)291 bool	PGSQL_has_Connections	(double vPostGIS)
292 {
293 	CSG_Strings	Servers;
294 
295 	return( PGSQL_Get_Connections(Servers, vPostGIS) );
296 }
297 
298 
299 ///////////////////////////////////////////////////////////
300 //														 //
301 ///////////////////////////////////////////////////////////
302 
303 //---------------------------------------------------------
PGSQL_Save_Table(CSG_Table * pTable)304 bool	PGSQL_Save_Table	(CSG_Table *pTable)
305 {
306 	CSG_Tool	*pTool	= SG_Get_Tool_Library_Manager().Create_Tool("db_pgsql", DB_PGSQL_Table_Save, true);
307 
308 	bool	bResult	= pTool && pTool->On_Before_Execution() && pTool->Set_Parameter("TABLE", pTable)
309 		&&  DLG_Parameters(pTool->Get_Parameters()) && pTool->Execute();
310 
311 	SG_Get_Tool_Library_Manager().Delete_Tool(pTool);
312 
313 	return( bResult );
314 }
315 
316 //---------------------------------------------------------
PGSQL_Save_Shapes(CSG_Shapes * pShapes)317 bool	PGSQL_Save_Shapes	(CSG_Shapes *pShapes)
318 {
319 	CSG_Tool	*pTool	= SG_Get_Tool_Library_Manager().Create_Tool("db_pgsql", DB_PGSQL_Shapes_Save, true);
320 
321 	bool	bResult	= pTool && pTool->On_Before_Execution() && pTool->Set_Parameter("SHAPES", pShapes)
322 		&&  DLG_Parameters(pTool->Get_Parameters()) && pTool->Execute();
323 
324 	SG_Get_Tool_Library_Manager().Delete_Tool(pTool);
325 
326 	return( bResult );
327 }
328 
329 //---------------------------------------------------------
PGSQL_Save_Grid(CSG_Grid * pGrid)330 bool	PGSQL_Save_Grid		(CSG_Grid *pGrid)
331 {
332 	bool	bResult	= false;
333 
334 	CSG_Tool	*pTool	= SG_Get_Tool_Library_Manager().Create_Tool("db_pgsql", DB_PGSQL_Raster_Save, true);
335 
336 	if(	pTool && pTool->On_Before_Execution() && pTool->Set_Parameter("NAME", pGrid->Get_Name()) )
337 	{
338 		pTool->Get_Parameter("GRIDS")->asList()->Del_Items();
339 		pTool->Get_Parameter("GRIDS")->asList()->Add_Item(pGrid);
340 		pTool->Set_Parameter("CRS_EPSG", pGrid->Get_Projection().Get_EPSG());
341 
342 		bResult	= DLG_Parameters(pTool->Get_Parameters()) && pTool->Execute();
343 	}
344 
345 	SG_Get_Tool_Library_Manager().Delete_Tool(pTool);
346 
347 	return( false );
348 }
349 
350 //---------------------------------------------------------
PGSQL_Save_Grids(CSG_Grids * pGrids)351 bool	PGSQL_Save_Grids		(CSG_Grids *pGrids)
352 {
353 	CSG_Tool	*pTool	= SG_Get_Tool_Library_Manager().Create_Tool("db_pgsql", DB_PGSQL_Rasters_Save, true);
354 
355 	bool	bResult	= pTool && pTool->On_Before_Execution() && pTool->Set_Parameter("GRIDS", pGrids)
356 		&&  DLG_Parameters(pTool->Get_Parameters()) && pTool->Execute();
357 
358 	SG_Get_Tool_Library_Manager().Delete_Tool(pTool);
359 
360 	return( bResult );
361 }
362 
363 
364 ///////////////////////////////////////////////////////////
365 //														 //
366 //														 //
367 //														 //
368 ///////////////////////////////////////////////////////////
369 
370 //---------------------------------------------------------
371 class CData_Source_PgSQL_Data : public wxTreeItemData
372 {
373 public:
CData_Source_PgSQL_Data(int Type,const CSG_String & Value="",const CSG_String & Server="",const CSG_String & Username="",const CSG_String & Password="")374     CData_Source_PgSQL_Data(int Type, const CSG_String &Value = "", const CSG_String &Server = "", const CSG_String &Username = "", const CSG_String &Password = "")
375 		: m_Type(Type), m_Value(Value), m_Server(Server), m_Username(Username), m_Password(Password)
376 	{}
377 
Get_Type(void) const378 	int						Get_Type		(void)	const	{	return( m_Type     );	}
Get_Value(void) const379 	const CSG_String &		Get_Value		(void)	const	{	return( m_Value    );	}
Get_Server(void) const380 	const CSG_String &		Get_Server		(void)	const	{	return( m_Server   );	}
381 
Set_Username(const SG_Char * Username)382 	void					Set_Username	(const SG_Char *Username)	{	m_Username	= Username;	}
Get_Username(void) const383 	const CSG_String &		Get_Username	(void)	const	{	return( m_Username     );	}
Set_Password(const SG_Char * Password)384 	void					Set_Password	(const SG_Char *Password)	{	m_Password	= Password;	}
Get_Password(void) const385 	const CSG_String &		Get_Password	(void)	const	{	return( m_Password );	}
386 
Get_Host(void) const387 	CSG_String				Get_Host		(void)  const	{	return( m_Server.AfterLast ('[').BeforeFirst(':') );	}
Get_Port(void) const388 	CSG_String				Get_Port		(void)  const	{	return( m_Server.AfterLast (':').BeforeFirst(']') );	}
Get_DBName(void) const389 	CSG_String				Get_DBName		(void)  const	{	CSG_String s(m_Server.BeforeLast('[')); s.Trim(true); return( s );	}
390 
is_Connected(void) const391 	bool					is_Connected	(void)	const	{	return( PGSQL_is_Connected(m_Server) );	}
392 
393 
394 private:
395 
396     int						m_Type;
397 
398 	CSG_String				m_Value, m_Server, m_Username, m_Password;
399 
400 };
401 
402 
403 ///////////////////////////////////////////////////////////
404 //														 //
405 //														 //
406 //														 //
407 ///////////////////////////////////////////////////////////
408 
409 //---------------------------------------------------------
BEGIN_EVENT_TABLE(CData_Source_PgSQL,wxTreeCtrl)410 BEGIN_EVENT_TABLE(CData_Source_PgSQL, wxTreeCtrl)
411 	EVT_MENU                 (ID_CMD_DB_REFRESH          , CData_Source_PgSQL::On_Refresh         )
412 	EVT_MENU                 (ID_CMD_DB_SOURCE_CREATE    , CData_Source_PgSQL::On_Source_Create   )
413 	EVT_MENU                 (ID_CMD_DB_SOURCE_DROP      , CData_Source_PgSQL::On_Source_Drop     )
414 	EVT_MENU                 (ID_CMD_DB_SOURCE_OPEN      , CData_Source_PgSQL::On_Source_Open     )
415 	EVT_MENU                 (ID_CMD_DB_SOURCE_CLOSE     , CData_Source_PgSQL::On_Source_Close    )
416 	EVT_MENU                 (ID_CMD_DB_SOURCE_CLOSE_ALL , CData_Source_PgSQL::On_Sources_Close   )
417 	EVT_MENU                 (ID_CMD_DB_SOURCE_DELETE    , CData_Source_PgSQL::On_Source_Delete   )
418 	EVT_MENU                 (ID_CMD_DB_TABLE_OPEN       , CData_Source_PgSQL::On_Table_Open      )
419 	EVT_MENU                 (ID_CMD_DB_TABLE_FROM_QUERY , CData_Source_PgSQL::On_Table_From_Query)
420 	EVT_MENU                 (ID_CMD_DB_TABLE_RENAME     , CData_Source_PgSQL::On_Table_Rename    )
421 	EVT_MENU                 (ID_CMD_DB_TABLE_INFO       , CData_Source_PgSQL::On_Table_Info      )
422 	EVT_MENU                 (ID_CMD_DB_TABLE_DELETE     , CData_Source_PgSQL::On_Table_Drop      )
423 
424 	EVT_TREE_ITEM_ACTIVATED  (ID_WND_DATA_SOURCE_DATABASE, CData_Source_PgSQL::On_Item_Activated  )
425 	EVT_TREE_ITEM_RIGHT_CLICK(ID_WND_DATA_SOURCE_DATABASE, CData_Source_PgSQL::On_Item_RClick     )
426 	EVT_TREE_ITEM_MENU       (ID_WND_DATA_SOURCE_DATABASE, CData_Source_PgSQL::On_Item_Menu       )
427 END_EVENT_TABLE()
428 
429 
430 ///////////////////////////////////////////////////////////
431 //														 //
432 //														 //
433 //														 //
434 ///////////////////////////////////////////////////////////
435 
436 //---------------------------------------------------------
437 #define CFG_PGSQL_DIR	wxT("/PGSQL")
438 #define CFG_PGSQL_SRC	wxT("SRC_%03d")
439 
440 //---------------------------------------------------------
441 CData_Source_PgSQL::CData_Source_PgSQL(wxWindow *pParent)
442 	: wxTreeCtrl(pParent, ID_WND_DATA_SOURCE_DATABASE)
443 {
444 	AssignImageList(new wxImageList(IMG_SIZE_TREECTRL, IMG_SIZE_TREECTRL, true, 0));
445 	IMG_ADD_TO_TREECTRL(ID_IMG_WKSP_DB_SOURCES    );	// IMG_ROOT
446 	IMG_ADD_TO_TREECTRL(ID_IMG_WKSP_DB_SOURCES    );	// IMG_SERVER
447 	IMG_ADD_TO_TREECTRL(ID_IMG_WKSP_DB_SOURCE_OFF );	// IMG_SRC_CLOSED
448 	IMG_ADD_TO_TREECTRL(ID_IMG_WKSP_DB_SOURCE_ON  );	// IMG_SRC_OPENED
449 	IMG_ADD_TO_TREECTRL(ID_IMG_WKSP_DB_TABLE      );	// IMG_TABLE
450 	IMG_ADD_TO_TREECTRL(ID_IMG_WKSP_SHAPES_POINT  );	// IMG_POINT
451 	IMG_ADD_TO_TREECTRL(ID_IMG_WKSP_SHAPES_POINTS );	// IMG_POINTS
452 	IMG_ADD_TO_TREECTRL(ID_IMG_WKSP_SHAPES_LINE   );	// IMG_LINE
453 	IMG_ADD_TO_TREECTRL(ID_IMG_WKSP_SHAPES_POLYGON);	// IMG_POLYGON
454 	IMG_ADD_TO_TREECTRL(ID_IMG_WKSP_GRIDS         );	// IMG_GRIDS
455 	IMG_ADD_TO_TREECTRL(ID_IMG_WKSP_GRID          );	// IMG_GRID
456 
457 	AddRoot(_TL("PostgreSQL Sources"), IMG_ROOT, IMG_ROOT, new CData_Source_PgSQL_Data(TYPE_ROOT));
458 
459 	m_Wait4Response	= g_pData->Get_Parameter("PROJECT_DB_WAIT")->asInt();
460 
461 	//-----------------------------------------------------
462 	SG_UI_Msg_Lock(true);
463 
464 	wxString	Server;
465 
466 	for(int i=0; CONFIG_Read(CFG_PGSQL_DIR, wxString::Format(CFG_PGSQL_SRC, i), Server); i++)
467 	{
468 		wxString	User, Password;
469 
470 		if( Server.Find("|") > 0 )
471 		{
472 			User     = Server.AfterFirst ('|').BeforeFirst('|');
473 			Password = Server.AfterLast  ('|');
474 			Server   = Server.BeforeFirst('|');
475 		}
476 
477 		CData_Source_PgSQL_Data	*pData	= new CData_Source_PgSQL_Data(TYPE_SOURCE, &Server, &Server, &User, &Password);
478 
479 		Update_Source(AppendItem(Get_Server_Item(Server, true), pData->Get_DBName().c_str(), IMG_SRC_CLOSED, IMG_SRC_CLOSED, pData));
480 	}
481 
482 	Update_Sources();
483 
484 	SG_UI_Msg_Lock(false);
485 }
486 
487 //---------------------------------------------------------
~CData_Source_PgSQL(void)488 CData_Source_PgSQL::~CData_Source_PgSQL(void)
489 {
490 	long Reopen	= 0;
491 
492 	CONFIG_Read("/DATA", "PROJECT_DB_REOPEN", Reopen);
493 
494 	CONFIG_Delete(CFG_PGSQL_DIR);
495 
496 	wxTreeItemIdValue srvCookie; wxTreeItemId srvItem = GetFirstChild(GetRootItem(), srvCookie);
497 
498 	for(int i=0; srvItem.IsOk(); )
499 	{
500 		wxTreeItemIdValue Cookie; wxTreeItemId Item = GetFirstChild(srvItem, Cookie);
501 
502 		while( Item.IsOk() )
503 		{
504 			CData_Source_PgSQL_Data	*pData	= (CData_Source_PgSQL_Data *)GetItemData(Item);
505 
506 			if( pData && pData->Get_Type() == TYPE_SOURCE )
507 			{
508 				CSG_String	Connection	= pData->Get_Server().c_str();
509 
510 				if( Reopen && pData->is_Connected() && !pData->Get_Username().is_Empty() )	// store user and password
511 				{
512 					Connection	+= "|" + pData->Get_Username() + "|" + pData->Get_Password();
513 				}
514 
515 				CONFIG_Write(CFG_PGSQL_DIR, wxString::Format(CFG_PGSQL_SRC, i++), Connection.c_str());
516 			}
517 
518 			Item	= GetNextChild(srvItem, Cookie);
519 		}
520 
521 		srvItem	= GetNextChild(GetRootItem(), srvCookie);
522 	}
523 }
524 
525 
526 ///////////////////////////////////////////////////////////
527 //														 //
528 ///////////////////////////////////////////////////////////
529 
530 //---------------------------------------------------------
Autoconnect(void)531 void CData_Source_PgSQL::Autoconnect(void)
532 {
533 	long Reopen	= 0;
534 
535 	CONFIG_Read("/DATA", "PROJECT_DB_REOPEN", Reopen);
536 
537 	if( Reopen != 0 )
538 	{
539 		wxTreeItemIdValue srvCookie; wxTreeItemId srvItem = GetFirstChild(GetRootItem(), srvCookie);
540 
541 		while( srvItem.IsOk() )
542 		{
543 			wxTreeItemIdValue Cookie; wxTreeItemId Item = GetFirstChild(srvItem, Cookie);
544 
545 			while( Item.IsOk() )
546 			{
547 				CData_Source_PgSQL_Data	*pData	= Item.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Item) : NULL; if( pData == NULL )	return;
548 
549 				if( pData->Get_Type() == TYPE_SOURCE && !pData->Get_Username().is_Empty() )
550 				{
551 					Source_Open(pData, false);
552 				}
553 
554 				Item	= GetNextChild(srvItem, Cookie);
555 			}
556 
557 			srvItem	= GetNextChild(GetRootItem(), srvCookie);
558 		}
559 	}
560 }
561 
562 
563 ///////////////////////////////////////////////////////////
564 //														 //
565 ///////////////////////////////////////////////////////////
566 
567 //---------------------------------------------------------
On_Refresh(wxCommandEvent & WXUNUSED (event))568 void CData_Source_PgSQL::On_Refresh(wxCommandEvent &WXUNUSED(event))
569 {
570 	Update_Item(GetSelection());
571 }
572 
573 //---------------------------------------------------------
On_Source_Create(wxCommandEvent & WXUNUSED (event))574 void CData_Source_PgSQL::On_Source_Create(wxCommandEvent &WXUNUSED(event))
575 {
576 	Source_Create(GetSelection());
577 }
578 
579 //---------------------------------------------------------
On_Source_Drop(wxCommandEvent & WXUNUSED (event))580 void CData_Source_PgSQL::On_Source_Drop(wxCommandEvent &WXUNUSED(event))
581 {
582 	Source_Drop(GetSelection());
583 }
584 
585 //---------------------------------------------------------
On_Source_Open(wxCommandEvent & WXUNUSED (event))586 void CData_Source_PgSQL::On_Source_Open(wxCommandEvent &WXUNUSED(event))
587 {
588 	Source_Open(GetSelection());
589 }
590 
591 //---------------------------------------------------------
On_Source_Close(wxCommandEvent & WXUNUSED (event))592 void CData_Source_PgSQL::On_Source_Close(wxCommandEvent &WXUNUSED(event))
593 {
594 	Source_Close(GetSelection(), false);
595 }
596 
597 //---------------------------------------------------------
On_Sources_Close(wxCommandEvent & WXUNUSED (event))598 void CData_Source_PgSQL::On_Sources_Close(wxCommandEvent &WXUNUSED(event))
599 {
600 	Sources_Close();
601 }
602 
603 //---------------------------------------------------------
On_Source_Delete(wxCommandEvent & WXUNUSED (event))604 void CData_Source_PgSQL::On_Source_Delete(wxCommandEvent &WXUNUSED(event))
605 {
606 	Source_Close(GetSelection(), true);
607 }
608 
609 //---------------------------------------------------------
On_Table_Open(wxCommandEvent & WXUNUSED (event))610 void CData_Source_PgSQL::On_Table_Open(wxCommandEvent &WXUNUSED(event))
611 {
612 	Table_Open(GetSelection());
613 }
614 
615 //---------------------------------------------------------
On_Table_From_Query(wxCommandEvent & WXUNUSED (event))616 void CData_Source_PgSQL::On_Table_From_Query(wxCommandEvent &WXUNUSED(event))
617 {
618 	Table_From_Query(GetSelection());
619 }
620 
621 //---------------------------------------------------------
On_Table_Rename(wxCommandEvent & WXUNUSED (event))622 void CData_Source_PgSQL::On_Table_Rename(wxCommandEvent &WXUNUSED(event))
623 {
624 	Table_Rename(GetSelection());
625 }
626 
627 //---------------------------------------------------------
On_Table_Info(wxCommandEvent & WXUNUSED (event))628 void CData_Source_PgSQL::On_Table_Info(wxCommandEvent &WXUNUSED(event))
629 {
630 	Table_Info(GetSelection());
631 }
632 
633 //---------------------------------------------------------
On_Table_Drop(wxCommandEvent & WXUNUSED (event))634 void CData_Source_PgSQL::On_Table_Drop(wxCommandEvent &WXUNUSED(event))
635 {
636 	Table_Drop(GetSelection());
637 }
638 
639 
640 ///////////////////////////////////////////////////////////
641 //														 //
642 ///////////////////////////////////////////////////////////
643 
644 //---------------------------------------------------------
On_Item_Activated(wxTreeEvent & event)645 void CData_Source_PgSQL::On_Item_Activated(wxTreeEvent &event)
646 {
647 	CData_Source_PgSQL_Data	*pData	= event.GetItem().IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(event.GetItem()) : NULL; if( pData == NULL )	return;
648 
649 	switch( pData->Get_Type() )
650 	{
651 	case TYPE_ROOT:
652 		Update_Sources();
653 		break;
654 
655 	case TYPE_SERVER:
656 		Update_Sources(event.GetItem());
657 		break;
658 
659 	case TYPE_SOURCE:
660 		Source_Open(event.GetItem());
661 		break;
662 
663 	case TYPE_TABLE:
664 	case TYPE_SHAPES:
665 	case TYPE_GRIDS:
666 	case TYPE_GRID:
667 		Table_Open(event.GetItem());
668 		break;
669 	}
670 }
671 
672 //---------------------------------------------------------
On_Item_RClick(wxTreeEvent & event)673 void CData_Source_PgSQL::On_Item_RClick(wxTreeEvent &event)
674 {
675 	SelectItem(event.GetItem());
676 
677 	event.Skip();
678 }
679 
680 //---------------------------------------------------------
On_Item_Menu(wxTreeEvent & event)681 void CData_Source_PgSQL::On_Item_Menu(wxTreeEvent &event)
682 {
683 	CData_Source_PgSQL_Data	*pData	= event.GetItem().IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(event.GetItem()) : NULL; if( pData == NULL )	return;
684 
685 	wxMenu	Menu;
686 
687 	switch( pData->Get_Type() )
688 	{
689 	case TYPE_ROOT:
690 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_REFRESH);
691 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_SOURCE_CREATE);
692 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_SOURCE_OPEN);
693 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_SOURCE_CLOSE_ALL);
694 		break;
695 
696 	case TYPE_SERVER:
697 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_REFRESH);
698 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_SOURCE_CREATE);
699 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_SOURCE_OPEN);
700 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_SOURCE_CLOSE_ALL);
701 		break;
702 
703 	case TYPE_SOURCE:
704 		if( !pData->is_Connected() )
705 		{
706 			CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_REFRESH);
707 			CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_SOURCE_OPEN);
708 			CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_SOURCE_DELETE);
709 		}
710 		else
711 		{
712 			CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_REFRESH);
713 			CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_SOURCE_DROP);
714 			CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_SOURCE_CLOSE);
715 			CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_SOURCE_DELETE);
716 			CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_TABLE_FROM_QUERY);
717 		}
718 		break;
719 
720 	case TYPE_TABLE:
721 	case TYPE_SHAPES:
722 	case TYPE_GRIDS:
723 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_TABLE_OPEN);
724 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_TABLE_RENAME);
725 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_TABLE_DELETE);
726 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_TABLE_INFO);
727 		break;
728 
729 	case TYPE_GRID:
730 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_TABLE_OPEN);
731 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_TABLE_RENAME);
732 		CMD_Menu_Add_Item(&Menu, false, ID_CMD_DB_TABLE_DELETE);
733 		break;
734 	}
735 
736 	if( Menu.GetMenuItemCount() > 0 )
737 	{
738 		PopupMenu(&Menu);
739 	}
740 }
741 
742 
743 ///////////////////////////////////////////////////////////
744 //														 //
745 ///////////////////////////////////////////////////////////
746 
747 //---------------------------------------------------------
Get_Server_Item(const wxString & Server,bool bCreate)748 wxTreeItemId CData_Source_PgSQL::Get_Server_Item(const wxString &Server, bool bCreate)
749 {
750 	wxString	Name	= Server.AfterFirst('[').BeforeFirst(']');
751 
752 	wxTreeItemIdValue Cookie; wxTreeItemId Item = GetFirstChild(GetRootItem(), Cookie);
753 
754 	while( Item.IsOk() )
755 	{
756 		if( !Name.Cmp(GetItemText(Item)) )
757 		{
758 			return( Item );
759 		}
760 
761 		Item	= GetNextChild(GetRootItem(), Cookie);
762 	}
763 
764 	if( bCreate )
765 	{
766 		Item	= AppendItem(GetRootItem(), Name, IMG_SERVER, IMG_SERVER, new CData_Source_PgSQL_Data(TYPE_SERVER, &Name, &Name));
767 
768 		SortChildren(GetRootItem());
769 		Expand      (GetRootItem());
770 	}
771 
772 	return( Item );
773 }
774 
775 //---------------------------------------------------------
Find_Source(const wxString & Server)776 wxTreeItemId CData_Source_PgSQL::Find_Source(const wxString &Server)
777 {
778 	wxTreeItemId	Item, srvItem	= Get_Server_Item(Server, false);
779 
780 	if( srvItem.IsOk() )
781 	{
782 		wxTreeItemIdValue Cookie; Item = GetFirstChild(srvItem, Cookie);
783 
784 		wxString	Name	= Server.BeforeLast('['); Name.Trim(true);
785 
786 		while( Item.IsOk() && Name.Cmp(GetItemText(Item)) )
787 		{
788 			Item	= GetNextChild(srvItem, Cookie);
789 		}
790 	}
791 
792 	return( Item );
793 }
794 
795 //---------------------------------------------------------
Update_Item(const wxTreeItemId & Item)796 void CData_Source_PgSQL::Update_Item(const wxTreeItemId &Item)
797 {
798 	CData_Source_PgSQL_Data	*pData	= Item.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Item) : NULL; if( pData == NULL )	return;
799 
800 	switch( pData->Get_Type() )
801 	{
802 	case TYPE_ROOT  :	Update_Sources(    );	break;
803 	case TYPE_SERVER:	Update_Sources(Item);	break;
804 	case TYPE_SOURCE:	Update_Source (Item);	break;
805 	}
806 }
807 
808 //---------------------------------------------------------
Update_Sources(const wxTreeItemId & Root)809 void CData_Source_PgSQL::Update_Sources(const wxTreeItemId &Root)
810 {
811 	Freeze();
812 
813 	//-----------------------------------------------------
814 	wxTreeItemIdValue Cookie; wxTreeItemId Item = GetFirstChild(Root, Cookie);
815 
816 	while( Item.IsOk() )
817 	{
818 		Update_Source(Item);
819 
820 		Item	= GetNextChild(Root, Cookie);
821 	}
822 
823 	//-----------------------------------------------------
824 	CSG_Table	Connections;
825 
826 	RUN_TOOL(DB_PGSQL_Get_Connections, false, false, SET_PARAMETER("CONNECTIONS", &Connections));	// CGet_Connections
827 
828 	for(int i=0; i<Connections.Get_Count(); i++)
829 	{
830 		if( !Find_Source(Connections[i].asString(0)) )
831 		{
832 			Update_Source(Connections[i].asString(0));
833 		}
834 	}
835 
836 	//-----------------------------------------------------
837 	SortChildren(Root);
838 	Expand      (Root);
839 
840 	Thaw();
841 }
842 
843 //---------------------------------------------------------
Update_Sources(void)844 void CData_Source_PgSQL::Update_Sources(void)
845 {
846 	wxTreeItemIdValue Cookie; wxTreeItemId Item = GetFirstChild(GetRootItem(), Cookie);
847 
848 	while( Item.IsOk() )
849 	{
850 		Update_Sources(Item);
851 
852 		Item	= GetNextChild(GetRootItem(), Cookie);
853 	}
854 }
855 
856 //---------------------------------------------------------
Update_Source(const wxString & Server,const wxString & Username,const wxString & Password)857 void CData_Source_PgSQL::Update_Source(const wxString &Server, const wxString &Username, const wxString &Password)
858 {
859 	if( Server.IsEmpty() )
860 	{
861 		Update_Sources();
862 
863 		return;
864 	}
865 
866 	wxTreeItemId	Item	= Find_Source(Server);
867 
868 	if( PGSQL_is_Connected(&Server) )
869 	{
870 		if( !Item.IsOk() )
871 		{
872 			CData_Source_PgSQL_Data	*pData	= new CData_Source_PgSQL_Data(TYPE_SOURCE, &Server, &Server, &Username, &Password);
873 
874 			Item	= AppendItem(Get_Server_Item(Server, true), pData->Get_DBName().c_str(), IMG_SRC_OPENED, IMG_SRC_OPENED, pData);
875 		}
876 		else if( !Username.IsEmpty() )	// if( Item.isOk() ))
877 		{
878 			CData_Source_PgSQL_Data	*pData	= (CData_Source_PgSQL_Data *)GetItemData(Item);
879 
880 			if( pData )
881 			{
882 				pData->Set_Username(Username);
883 				pData->Set_Password(Password);
884 			}
885 		}
886 	}
887 
888 	Update_Source(Item);
889 }
890 
891 //---------------------------------------------------------
Update_Source(const wxTreeItemId & Item)892 void CData_Source_PgSQL::Update_Source(const wxTreeItemId &Item)
893 {
894 	CData_Source_PgSQL_Data	*pData	= Item.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Item) : NULL; if( pData == NULL )	return;
895 
896 	if( pData->Get_Type() != TYPE_SOURCE )
897 	{
898 		return;
899 	}
900 
901 	Freeze();
902 
903 	DeleteChildren(Item);
904 
905 	//-----------------------------------------------------
906 	if( !pData->is_Connected() )
907 	{
908 		SetItemImage(Item, IMG_SRC_CLOSED, wxTreeItemIcon_Normal);
909 		SetItemImage(Item, IMG_SRC_CLOSED, wxTreeItemIcon_Selected);
910 	}
911 	else
912 	{
913 		SetItemImage(Item, IMG_SRC_OPENED, wxTreeItemIcon_Normal);
914 		SetItemImage(Item, IMG_SRC_OPENED, wxTreeItemIcon_Selected);
915 
916 		CSG_Table	Tables;
917 
918 		RUN_TOOL(DB_PGSQL_Table_List, false, false,	// CTable_List
919 				SET_PARAMETER("CONNECTION", pData->Get_Value())
920 			&&	SET_PARAMETER("TABLES"    , &Tables)
921 		);
922 
923 	//	Tables.Set_Index(1, TABLE_INDEX_Ascending, 0, TABLE_INDEX_Ascending);	// sort by geometry type, then by name
924 		Tables.Set_Index(0, TABLE_INDEX_Ascending);	// sort by name
925 
926 		bool	bSkipPostGISTables	= true;
927 
928 		for(int i=0; i<Tables.Get_Count(); i++)
929 		{
930 			CSG_String	s(Tables[i].asString(0));
931 
932 			if( bSkipPostGISTables == false
933 			|| (s.CmpNoCase("geography_columns" )
934 			&&  s.CmpNoCase("geometry_columns"  )
935 			&&  s.CmpNoCase("raster_columns"    )
936 			&&  s.CmpNoCase("raster_overviews"  )
937 			&&  s.CmpNoCase("pointcloud_columns")
938 			&&  s.CmpNoCase("pointcloud_formats")
939 			&&  s.CmpNoCase("spatial_ref_sys"   )) )
940 			{
941 				s	= Tables[i].asString(1);
942 
943 				TSG_Shape_Type	Shape;
944 				TSG_Vertex_Type	Vertex;
945 
946 				if( CSG_Shapes_OGIS_Converter::to_ShapeType(s, Shape, Vertex) )
947 				{
948 					switch( Shape )
949 					{
950 					case SHAPE_TYPE_Point  : Append_Table(Item, Tables[i].asString(0), TYPE_SHAPES, IMG_POINT  ); break;
951 					case SHAPE_TYPE_Points : Append_Table(Item, Tables[i].asString(0), TYPE_SHAPES, IMG_POINTS ); break;
952 					case SHAPE_TYPE_Line   : Append_Table(Item, Tables[i].asString(0), TYPE_SHAPES, IMG_LINE   ); break;
953 					case SHAPE_TYPE_Polygon: Append_Table(Item, Tables[i].asString(0), TYPE_SHAPES, IMG_POLYGON); break;
954 					}
955 				}
956 				else if( !s.Cmp("RASTER" ) ) Append_Table(Item, Tables[i].asString(0), TYPE_GRIDS , IMG_GRIDS  );
957 				else if( !s.Cmp("TABLE"  ) ) Append_Table(Item, Tables[i].asString(0), TYPE_TABLE , IMG_TABLE  );
958 			}
959 		}
960 
961 		Expand(Item);
962 	}
963 
964 	Thaw();
965 }
966 
967 //---------------------------------------------------------
Append_Table(const wxTreeItemId & Parent,const SG_Char * Name,int Type,int Image)968 void CData_Source_PgSQL::Append_Table(const wxTreeItemId &Parent, const SG_Char *Name, int Type, int Image)
969 {
970 	CData_Source_PgSQL_Data	*pData	= Parent.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Parent) : NULL; if( pData == NULL )	return;
971 
972 	wxTreeItemId	Item	= AppendItem(Parent, Name, Image, Image, new CData_Source_PgSQL_Data(Type, Name, pData->Get_Server()));
973 
974 	if( Type == TYPE_GRIDS )
975 	{
976 		CSG_Table	Grids;
977 
978 		RUN_TOOL(DB_PGSQL_Table_Query, false, false,	// CTable_Query
979 				SET_PARAMETER("CONNECTION", pData->Get_Server())
980 			&&	SET_PARAMETER("TABLES"    , Name)
981 			&&	SET_PARAMETER("TABLE"     , &Grids)
982 			&&  SET_PARAMETER("FIELDS"    , SG_T("rid, name"))
983 		);
984 
985 		if( bResult )
986 		{
987 			for(int i=0; i<Grids.Get_Count(); i++)
988 			{
989 				AppendItem(Item, Grids[i].asString(1), IMG_GRID, IMG_GRID,
990 					new CData_Source_PgSQL_Data(TYPE_GRID, CSG_String::Format("%s:rid=%d", Name, Grids[i].asInt(0)), pData->Get_Server())
991 				);
992 			}
993 		}
994 	}
995 }
996 
997 
998 ///////////////////////////////////////////////////////////
999 //														 //
1000 ///////////////////////////////////////////////////////////
1001 
1002 //---------------------------------------------------------
Source_Create(const wxTreeItemId & Item)1003 bool CData_Source_PgSQL::Source_Create(const wxTreeItemId &Item)
1004 {
1005 	CData_Source_PgSQL_Data	*pData	= Item.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Item) : NULL; if( pData == NULL )	return( false );
1006 
1007 	if( pData->Get_Type() == TYPE_ROOT
1008 	||  pData->Get_Type() == TYPE_SERVER )
1009 	{
1010 		CSG_Tool	*pTool	= SG_Get_Tool_Library_Manager().Create_Tool("db_pgsql", DB_PGSQL_DB_Create, true);
1011 
1012 		if(	pTool && pTool->On_Before_Execution() )
1013 		{
1014 			if( pData->Get_Type() == TYPE_SERVER )
1015 			{
1016 				pTool->Set_Parameter("PG_HOST", pData->Get_Host());
1017 				pTool->Set_Parameter("PG_PORT", pData->Get_Port());
1018 			}
1019 
1020 			if( DLG_Parameters(pTool->Get_Parameters()) )
1021 			{
1022 				pTool->Execute();
1023 			}
1024 		}
1025 
1026 		SG_Get_Tool_Library_Manager().Delete_Tool(pTool);
1027 	}
1028 
1029 	return( true );
1030 }
1031 
1032 //---------------------------------------------------------
Source_Drop(const wxTreeItemId & Item)1033 bool CData_Source_PgSQL::Source_Drop(const wxTreeItemId &Item)
1034 {
1035 	CData_Source_PgSQL_Data	*pData	= Item.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Item) : NULL; if( pData == NULL )	return( false );
1036 
1037 	if( !DLG_Login(g_Username, g_Password, _TL("Drop Database")) )
1038 	{
1039 		return( false );
1040 	}
1041 
1042 	pData->Set_Username(g_Username);
1043 	pData->Set_Password(g_Password);
1044 
1045 	if( pData->Get_Type() == TYPE_SOURCE && pData->is_Connected() )
1046 	{
1047 		RUN_TOOL(DB_PGSQL_DB_Drop, true, true,	// CDatabase_Drop
1048 				SET_PARAMETER("PG_HOST", pData->Get_Host    ())
1049 			&&	SET_PARAMETER("PG_PORT", pData->Get_Port    ())
1050 			&&	SET_PARAMETER("PG_NAME", pData->Get_DBName  ())
1051 			&&	SET_PARAMETER("PG_USER", pData->Get_Username())
1052 			&&	SET_PARAMETER("PG_PWD" , pData->Get_Password())
1053 		);
1054 
1055 		if( bResult )
1056 		{
1057 			Delete(Item);
1058 
1059 			return( true );
1060 		}
1061 	}
1062 
1063 	return( false );
1064 }
1065 
1066 //---------------------------------------------------------
Source_Open(CData_Source_PgSQL_Data * pData,bool bDialog)1067 bool CData_Source_PgSQL::Source_Open(CData_Source_PgSQL_Data *pData, bool bDialog)
1068 {
1069 	if( bDialog )
1070 	{
1071 		if( !DLG_Login(g_Username, g_Password) )
1072 		{
1073 			return( false );
1074 		}
1075 
1076 		pData->Set_Username(g_Username);
1077 		pData->Set_Password(g_Password);
1078 	}
1079 
1080 	//-----------------------------------------------------
1081 	MSG_General_Add(wxString::Format("%s: %s...", _TL("Connecting to database"), pData->Get_Server().c_str()), true, true);
1082 
1083 	if( m_Wait4Response <= 0 || is_Server_Responding(pData->Get_Host(), pData->Get_Port(), m_Wait4Response) )
1084 	{
1085 		RUN_TOOL(DB_PGSQL_Get_Connection, false, false,	// CGet_Connection
1086 			SET_PARAMETER("PG_HOST", pData->Get_Host    ())
1087 			&&	SET_PARAMETER("PG_PORT", pData->Get_Port    ())
1088 			&&	SET_PARAMETER("PG_USER", pData->Get_Username())
1089 			&&	SET_PARAMETER("PG_PWD" , pData->Get_Password())
1090 			&&	SET_PARAMETER("PG_NAME", pData->Get_DBName  ())
1091 		);
1092 
1093 		if( bResult )
1094 		{
1095 			MSG_General_Add(_TL("okay"), false, false, SG_UI_MSG_STYLE_SUCCESS);
1096 
1097 			return( true );
1098 		}
1099 	}
1100 
1101 	MSG_General_Add(_TL("failed"), false, false, SG_UI_MSG_STYLE_FAILURE);
1102 
1103 	return( false );
1104 }
1105 
1106 //---------------------------------------------------------
Source_Open(const wxTreeItemId & Item)1107 void CData_Source_PgSQL::Source_Open(const wxTreeItemId &Item)
1108 {
1109 	CData_Source_PgSQL_Data	*pData	= Item.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Item) : NULL; if( pData == NULL )	return;
1110 
1111 	if( pData->Get_Type() == TYPE_ROOT
1112 	||  pData->Get_Type() == TYPE_SERVER )
1113 	{
1114 		CSG_Tool	*pTool	= SG_Get_Tool_Library_Manager().Create_Tool("db_pgsql", DB_PGSQL_Get_Connection, true);	// CGet_Connection
1115 
1116 		if(	pTool && pTool->On_Before_Execution() )
1117 		{
1118 			if( pData->Get_Type() == TYPE_SERVER )
1119 			{
1120 				pTool->Set_Parameter("PG_HOST", pData->Get_Host());
1121 				pTool->Set_Parameter("PG_PORT", pData->Get_Port());
1122 			}
1123 
1124 			if( DLG_Parameters(pTool->Get_Parameters()) )
1125 			{
1126 				pTool->Execute();
1127 			}
1128 		}
1129 
1130 		SG_Get_Tool_Library_Manager().Delete_Tool(pTool);
1131 	}
1132 	else if( pData->is_Connected() )
1133 	{
1134 		Update_Source(Item);
1135 	}
1136 	else if( !Source_Open(pData, true) )
1137 	{
1138 		DLG_Message_Show_Error(_TL("Could not connect to data source."), _TL("Connect to PostgreSQL"));
1139 	}
1140 }
1141 
1142 //---------------------------------------------------------
Source_Close(const wxTreeItemId & Item,bool bDelete)1143 void CData_Source_PgSQL::Source_Close(const wxTreeItemId &Item, bool bDelete)
1144 {
1145 	CData_Source_PgSQL_Data	*pData	= Item.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Item) : NULL; if( pData == NULL )	return;
1146 
1147 	if( pData->is_Connected() )
1148 	{
1149 		RUN_TOOL(DB_PGSQL_Del_Connection, true, false, SET_PARAMETER("CONNECTION", pData->Get_Server()));
1150 	}
1151 
1152 	if( bDelete )
1153 	{
1154 		Delete(Item);
1155 	}
1156 	else
1157 	{
1158 		pData->Set_Username(SG_T(""));
1159 		pData->Set_Password(SG_T(""));
1160 	}
1161 }
1162 
1163 //---------------------------------------------------------
Sources_Close(void)1164 void CData_Source_PgSQL::Sources_Close(void)
1165 {
1166 	RUN_TOOL(DB_PGSQL_Del_Connections, true, false, true);
1167 }
1168 
1169 
1170 ///////////////////////////////////////////////////////////
1171 //														 //
1172 ///////////////////////////////////////////////////////////
1173 
1174 //---------------------------------------------------------
Table_Open(const wxTreeItemId & Item)1175 void CData_Source_PgSQL::Table_Open(const wxTreeItemId &Item)
1176 {
1177 	CData_Source_PgSQL_Data	*pData	= Item.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Item) : NULL; if( pData == NULL )	return;
1178 
1179 	//-----------------------------------------------------
1180 	if( pData->Get_Type() == TYPE_TABLE )
1181 	{
1182 		CSG_Table	*pTable	= SG_Create_Table();
1183 
1184 		RUN_TOOL(DB_PGSQL_Table_Load, false, false,	// CTable_Load
1185 				SET_PARAMETER("CONNECTION", pData->Get_Server())
1186 			&&	SET_PARAMETER("TABLES"    , pData->Get_Value ())
1187 			&&	SET_PARAMETER("TABLE"     , pTable)
1188 		);
1189 
1190 		if( bResult )
1191 		{
1192 			SG_Get_Data_Manager().Add(pTable);
1193 			g_pData->Show(pTable, 0);
1194 		}
1195 		else
1196 		{
1197 			delete(pTable);
1198 		}
1199 	}
1200 
1201 	//-----------------------------------------------------
1202 	if( pData->Get_Type() == TYPE_SHAPES )
1203 	{
1204 		RUN_TOOL(DB_PGSQL_Shapes_Load, true, false,	// CPGIS_Shapes_Load
1205 				SET_PARAMETER("CONNECTION", pData->Get_Server())
1206 			&&	SET_PARAMETER("TABLES"    , pData->Get_Value ())
1207 		);
1208 	}
1209 
1210 	//-----------------------------------------------------
1211 	if( pData->Get_Type() == TYPE_GRIDS )
1212 	{
1213 		RUN_TOOL(DB_PGSQL_Raster_Load, true, false,
1214 				SET_PARAMETER("CONNECTION", pData->Get_Server())
1215 			&&	SET_PARAMETER("TABLES"    , pData->Get_Value ())
1216 		);
1217 	}
1218 
1219 	//-----------------------------------------------------
1220 	if( pData->Get_Type() == TYPE_GRID )
1221 	{
1222 		RUN_TOOL(DB_PGSQL_Raster_Load, true, false,
1223 				SET_PARAMETER("CONNECTION", pData->Get_Server())
1224 			&&	SET_PARAMETER("TABLES"    , pData->Get_Value ().BeforeFirst(':'))
1225 			&&	SET_PARAMETER("WHERE"     , pData->Get_Value ().AfterFirst (':'))
1226 		);
1227 	}
1228 }
1229 
1230 //---------------------------------------------------------
Table_From_Query(const wxTreeItemId & Item)1231 void CData_Source_PgSQL::Table_From_Query(const wxTreeItemId &Item)
1232 {
1233 	CData_Source_PgSQL_Data	*pData	= Item.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Item) : NULL; if( pData == NULL )	return;
1234 
1235 	CSG_Tool	*pTool	= SG_Get_Tool_Library_Manager().Create_Tool("db_pgsql", DB_PGSQL_Table_Query, true);
1236 
1237 	if(	pTool && pTool->On_Before_Execution() )
1238 	{
1239 		if( pData->Get_Type() == TYPE_SERVER )
1240 		{
1241 			pTool->Set_Parameter("PG_HOST", pData->Get_Host());
1242 			pTool->Set_Parameter("PG_PORT", pData->Get_Port());
1243 		}
1244 
1245 		if( DLG_Parameters(pTool->Get_Parameters()) )
1246 		{
1247 			pTool->Execute();
1248 		}
1249 	}
1250 
1251 	SG_Get_Tool_Library_Manager().Delete_Tool(pTool);
1252 }
1253 
1254 //---------------------------------------------------------
Table_Rename(const wxTreeItemId & Item)1255 void CData_Source_PgSQL::Table_Rename(const wxTreeItemId &Item)
1256 {
1257 	CData_Source_PgSQL_Data	*pData	= Item.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Item) : NULL; if( pData == NULL )	return;
1258 
1259 	wxString	Name	= GetItemText(Item);
1260 
1261 	switch( pData->Get_Type() )
1262 	{
1263 	//-----------------------------------------------------
1264 	case TYPE_GRID:
1265 		if( DLG_Get_Text(Name, _TL("Rename Raster Band"), _TL("Name")) )
1266 		{
1267 			CSG_String	Table	= pData->Get_Value().BeforeFirst(':');
1268 			CSG_String	rid		= pData->Get_Value().AfterFirst (':');
1269 			CSG_String	SQL	= "UPDATE \"" + Table + "\" SET name='" + CSG_String(&Name) + "' WHERE " + rid + ";";
1270 
1271 			RUN_TOOL(DB_PGSQL_Execute_SQL, false, false,
1272 					SET_PARAMETER("CONNECTION", pData->Get_Server())
1273 				&&	SET_PARAMETER("OUTPUT"    , 0)	// none
1274 				&&	SET_PARAMETER("SQL"       , SQL)
1275 			);
1276 
1277 			if( bResult )
1278 			{
1279 				SetItemText(Item, Name);
1280 			}
1281 		}
1282 		break;
1283 
1284 	//-----------------------------------------------------
1285 	default:
1286 		if( DLG_Get_Text(Name, _TL("Rename Table"), _TL("Name")) )
1287 		{
1288 			CSG_String	SQL	= "ALTER TABLE \"" + pData->Get_Value() + "\" RENAME TO \"" + CSG_String(&Name) + "\";";
1289 
1290 			RUN_TOOL(DB_PGSQL_Execute_SQL, false, false,
1291 					SET_PARAMETER("CONNECTION", pData->Get_Server())
1292 				&&	SET_PARAMETER("OUTPUT"    , 0)	// none
1293 				&&	SET_PARAMETER("SQL"       , SQL)
1294 			);
1295 
1296 			if( bResult )
1297 			{
1298 				SetItemText(Item, Name);
1299 			}
1300 		}
1301 		break;
1302 	}
1303 }
1304 
1305 //---------------------------------------------------------
Table_Info(const wxTreeItemId & Item)1306 void CData_Source_PgSQL::Table_Info(const wxTreeItemId &Item)
1307 {
1308 	CData_Source_PgSQL_Data	*pData	= Item.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Item) : NULL; if( pData == NULL )	return;
1309 
1310 	CSG_Table	*pTable	= SG_Create_Table();
1311 
1312 	RUN_TOOL(DB_PGSQL_Table_Info, false, false,	// CTable_Info
1313 			SET_PARAMETER("CONNECTION", pData->Get_Server())
1314 		&&	SET_PARAMETER("TABLES"    , pData->Get_Value ())
1315 		&&	SET_PARAMETER("TABLE"     , pTable)
1316 		&&	SET_PARAMETER("VERBOSE"   , true)
1317 	);
1318 
1319 	if( bResult )
1320 	{
1321 		SG_Get_Data_Manager().Add(pTable);
1322 		g_pData->Show(pTable, 0);
1323 	}
1324 	else
1325 	{
1326 		delete(pTable);
1327 	}
1328 }
1329 
1330 //---------------------------------------------------------
Table_Drop(const wxTreeItemId & Item)1331 void CData_Source_PgSQL::Table_Drop(const wxTreeItemId &Item)
1332 {
1333 	CData_Source_PgSQL_Data	*pData	= Item.IsOk() ? (CData_Source_PgSQL_Data *)GetItemData(Item) : NULL; if( pData == NULL )	return;
1334 
1335 	wxString	Name	= GetItemText(Item);
1336 
1337 	switch( pData->Get_Type() )
1338 	{
1339 	//-----------------------------------------------------
1340 	case TYPE_GRID:
1341 		if( DLG_Message_Confirm(wxString::Format("%s [%s]", _TL("Do you really want to delete this raster band"), Name.c_str()), _TL("Raster Band Deletion")) )
1342 		{
1343 			MSG_General_Add(wxString::Format("%s: [%s] %s...", _TL("Deleting raster band"), pData->Get_Server().c_str(), Name.c_str()), true, true);
1344 
1345 			CSG_String	Table	= pData->Get_Value().BeforeFirst(':');
1346 			CSG_String	rid		= pData->Get_Value().AfterFirst (':');
1347 			CSG_String	SQL	= "DELETE FROM \"" + Table + "\" WHERE " + rid + ";";
1348 
1349 			RUN_TOOL(DB_PGSQL_Execute_SQL, false, false,
1350 					SET_PARAMETER("CONNECTION", pData->Get_Server())
1351 				&&	SET_PARAMETER("OUTPUT"    , 0)	// none
1352 				&&	SET_PARAMETER("SQL"       , SQL)
1353 			);
1354 
1355 			if( bResult )
1356 			{
1357 				Delete(Item);
1358 
1359 				MSG_General_Add(_TL("okay"), false, false, SG_UI_MSG_STYLE_SUCCESS);
1360 			}
1361 			else
1362 			{
1363 				MSG_General_Add(_TL("failed"), false, false, SG_UI_MSG_STYLE_FAILURE);
1364 			}
1365 		}
1366 		break;
1367 
1368 	//-----------------------------------------------------
1369 	default:
1370 		if( DLG_Message_Confirm(wxString::Format("%s [%s]", _TL("Do you really want to delete the table"), pData->Get_Value().c_str()), _TL("Table Deletion")) )
1371 		{
1372 			MSG_General_Add(wxString::Format("%s: [%s] %s...", _TL("Deleting table"), pData->Get_Server().c_str(), pData->Get_Value().c_str()), true, true);
1373 
1374 			RUN_TOOL(DB_PGSQL_Table_Drop, false, false,	// CTable_Drop
1375 					SET_PARAMETER("CONNECTION", pData->Get_Server())
1376 				&&	SET_PARAMETER("TABLES"    , pData->Get_Value())
1377 			);
1378 
1379 			if( bResult )
1380 			{
1381 				Delete(Item);
1382 
1383 				MSG_General_Add(_TL("okay"), false, false, SG_UI_MSG_STYLE_SUCCESS);
1384 			}
1385 			else
1386 			{
1387 				MSG_General_Add(_TL("failed"), false, false, SG_UI_MSG_STYLE_FAILURE);
1388 			}
1389 		}
1390 		break;
1391 	}
1392 }
1393 
1394 
1395 ///////////////////////////////////////////////////////////
1396 //														 //
1397 //														 //
1398 //														 //
1399 ///////////////////////////////////////////////////////////
1400 
1401 //---------------------------------------------------------
1402