Line data Source code
1 : /******************************************************************************
2 : *
3 : * Project: OpenGIS Simple Features Reference Implementation
4 : * Purpose: Private definitions for OGR/PostgreSQL driver.
5 : * Author: Frank Warmerdam, warmerdam@pobox.com
6 : *
7 : ******************************************************************************
8 : * Copyright (c) 2000, Frank Warmerdam
9 : * Copyright (c) 2008-2013, Even Rouault <even dot rouault at spatialys.com>
10 : *
11 : * SPDX-License-Identifier: MIT
12 : ****************************************************************************/
13 :
14 : #ifndef OGR_PG_H_INCLUDED
15 : #define OGR_PG_H_INCLUDED
16 :
17 : #include "ogrsf_frmts.h"
18 : #include "libpq-fe.h"
19 : #include "cpl_string.h"
20 :
21 : #include "ogrpgutility.h"
22 : #include "ogr_pgdump.h"
23 :
24 : #include <map>
25 : #include <optional>
26 : #include <vector>
27 :
28 : /* These are the OIDs for some builtin types, as returned by PQftype(). */
29 : /* They were copied from pg_type.h in src/include/catalog/pg_type.h */
30 :
31 : #define BOOLOID 16
32 : #define BYTEAOID 17
33 : #define CHAROID 18
34 : #define NAMEOID 19
35 : #define INT8OID 20
36 : #define INT2OID 21
37 : #define INT2VECTOROID 22
38 : #define INT4OID 23
39 : #define REGPROCOID 24
40 : #define TEXTOID 25
41 : #define OIDOID 26
42 : #define TIDOID 27
43 : #define XIDOID 28
44 : #define CIDOID 29
45 : #define OIDVECTOROID 30
46 : #define JSONOID 114
47 : #define FLOAT4OID 700
48 : #define FLOAT8OID 701
49 : #define BOOLARRAYOID 1000
50 : #define INT2ARRAYOID 1005
51 : #define INT4ARRAYOID 1007
52 : #define TEXTARRAYOID 1009
53 : #define BPCHARARRAYOID 1014
54 : #define VARCHARARRAYOID 1015
55 : #define INT8ARRAYOID 1016
56 : #define FLOAT4ARRAYOID 1021
57 : #define FLOAT8ARRAYOID 1022
58 : #define BPCHAROID 1042
59 : #define VARCHAROID 1043
60 : #define DATEOID 1082
61 : #define TIMEOID 1083
62 : #define TIMESTAMPOID 1114
63 : #define TIMESTAMPTZOID 1184
64 : #define NUMERICOID 1700
65 : #define NUMERICARRAYOID 1231
66 : #define UUIDOID 2950
67 : #define JSONBOID 3802
68 :
69 : CPLString OGRPGEscapeString(void *hPGConn, const char *pszStrValue,
70 : int nMaxLength = -1, const char *pszTableName = "",
71 : const char *pszFieldName = "");
72 : CPLString OGRPGEscapeColumnName(const char *pszColumnName);
73 :
74 : #define UNDETERMINED_SRID \
75 : -2 /* Special value when we haven't yet looked for SRID */
76 :
77 : class OGRPGDataSource;
78 : class OGRPGLayer;
79 :
80 : typedef enum
81 : {
82 : GEOM_TYPE_UNKNOWN = 0,
83 : GEOM_TYPE_GEOMETRY = 1,
84 : GEOM_TYPE_GEOGRAPHY = 2,
85 : GEOM_TYPE_WKB = 3
86 : } PostgisType;
87 :
88 : typedef struct
89 : {
90 : char *pszName;
91 : char *pszGeomType;
92 : int GeometryTypeFlags;
93 : int nSRID;
94 : PostgisType ePostgisType;
95 : int bNullable;
96 : } PGGeomColumnDesc;
97 :
98 : /************************************************************************/
99 : /* OGRPGGeomFieldDefn */
100 : /************************************************************************/
101 :
102 : class OGRPGGeomFieldDefn final : public OGRGeomFieldDefn
103 : {
104 : OGRPGGeomFieldDefn(const OGRPGGeomFieldDefn &) = delete;
105 : OGRPGGeomFieldDefn &operator=(const OGRPGGeomFieldDefn &) = delete;
106 :
107 : protected:
108 : OGRPGLayer *poLayer;
109 :
110 : public:
111 566 : OGRPGGeomFieldDefn(OGRPGLayer *poLayerIn, const char *pszFieldName)
112 566 : : OGRGeomFieldDefn(pszFieldName, wkbUnknown), poLayer(poLayerIn),
113 : nSRSId(UNDETERMINED_SRID), GeometryTypeFlags(0),
114 566 : ePostgisType(GEOM_TYPE_UNKNOWN)
115 : {
116 566 : }
117 :
118 : virtual const OGRSpatialReference *GetSpatialRef() const override;
119 :
120 566 : void UnsetLayer()
121 : {
122 566 : poLayer = nullptr;
123 566 : }
124 :
125 : mutable int nSRSId;
126 : mutable int GeometryTypeFlags;
127 : mutable PostgisType ePostgisType;
128 : };
129 :
130 : /************************************************************************/
131 : /* OGRPGFeatureDefn */
132 : /************************************************************************/
133 :
134 : class OGRPGFeatureDefn CPL_NON_FINAL : public OGRFeatureDefn
135 : {
136 : public:
137 954 : explicit OGRPGFeatureDefn(const char *pszName = nullptr)
138 954 : : OGRFeatureDefn(pszName)
139 : {
140 954 : SetGeomType(wkbNone);
141 954 : }
142 :
143 : virtual void UnsetLayer();
144 :
145 22566 : OGRPGGeomFieldDefn *GetGeomFieldDefn(int i) override
146 : {
147 22566 : return cpl::down_cast<OGRPGGeomFieldDefn *>(
148 22566 : OGRFeatureDefn::GetGeomFieldDefn(i));
149 : }
150 :
151 1536 : const OGRPGGeomFieldDefn *GetGeomFieldDefn(int i) const override
152 : {
153 1536 : return cpl::down_cast<const OGRPGGeomFieldDefn *>(
154 1536 : OGRFeatureDefn::GetGeomFieldDefn(i));
155 : }
156 : };
157 :
158 : /************************************************************************/
159 : /* OGRPGLayer */
160 : /************************************************************************/
161 :
162 : class OGRPGLayer CPL_NON_FINAL : public OGRLayer
163 : {
164 : OGRPGLayer(const OGRPGLayer &) = delete;
165 : OGRPGLayer &operator=(const OGRPGLayer &) = delete;
166 :
167 : protected:
168 : OGRPGFeatureDefn *poFeatureDefn = nullptr;
169 :
170 : int nCursorPage = 0;
171 : GIntBig iNextShapeId = 0;
172 :
173 : static char *GeometryToBYTEA(const OGRGeometry *, int nPostGISMajor,
174 : int nPostGISMinor);
175 : static GByte *BYTEAToGByteArray(const char *pszBytea, int *pnLength);
176 : static OGRGeometry *BYTEAToGeometry(const char *);
177 : Oid GeometryToOID(OGRGeometry *);
178 : OGRGeometry *OIDToGeometry(Oid);
179 :
180 : OGRPGDataSource *poDS = nullptr;
181 :
182 : char *pszQueryStatement = nullptr;
183 :
184 : char *pszCursorName = nullptr;
185 : PGresult *hCursorResult = nullptr;
186 : int bInvalidated = false;
187 :
188 : int nResultOffset = 0;
189 :
190 : int bWkbAsOid = false;
191 :
192 : char *pszFIDColumn = nullptr;
193 :
194 : int bCanUseBinaryCursor = true;
195 : int *m_panMapFieldNameToIndex = nullptr;
196 : int *m_panMapFieldNameToGeomIndex = nullptr;
197 :
198 : int ParsePGDate(const char *, OGRField *);
199 :
200 : void SetInitialQueryCursor();
201 : void CloseCursor();
202 :
203 : virtual CPLString GetFromClauseForGetExtent() = 0;
204 : OGRErr RunGetExtentRequest(OGREnvelope &sExtent, int bForce,
205 : const std::string &osCommand, int bErrorAsDebug);
206 : OGRErr RunGetExtent3DRequest(OGREnvelope3D &sExtent3D,
207 : const std::string &osCommand,
208 : int bErrorAsDebug);
209 : static void CreateMapFromFieldNameToIndex(PGresult *hResult,
210 : OGRFeatureDefn *poFeatureDefn,
211 : int *&panMapFieldNameToIndex,
212 : int *&panMapFieldNameToGeomIndex);
213 :
214 : int ReadResultDefinition(PGresult *hInitialResultIn);
215 :
216 : OGRFeature *RecordToFeature(PGresult *hResult,
217 : const int *panMapFieldNameToIndex,
218 : const int *panMapFieldNameToGeomIndex,
219 : int iRecord);
220 : OGRFeature *GetNextRawFeature();
221 :
222 : public:
223 : OGRPGLayer();
224 : virtual ~OGRPGLayer();
225 :
226 : virtual void ResetReading() override;
227 :
228 11984 : virtual OGRPGFeatureDefn *GetLayerDefn() override
229 : {
230 11984 : return poFeatureDefn;
231 : }
232 :
233 : OGRErr IGetExtent(int iGeomField, OGREnvelope *psExtent,
234 : bool bForce) override;
235 :
236 : OGRErr IGetExtent3D(int iGeomField, OGREnvelope3D *psExtent3D,
237 : bool bForce) override;
238 :
239 : virtual OGRErr StartTransaction() override;
240 : virtual OGRErr CommitTransaction() override;
241 : virtual OGRErr RollbackTransaction() override;
242 :
243 : void InvalidateCursor();
244 :
245 : virtual const char *GetFIDColumn() override;
246 :
247 : virtual OGRErr SetNextByIndex(GIntBig nIndex) override;
248 :
249 33 : OGRPGDataSource *GetDS()
250 : {
251 33 : return poDS;
252 : }
253 :
254 : GDALDataset *GetDataset() override;
255 :
256 : virtual void ResolveSRID(const OGRPGGeomFieldDefn *poGFldDefn) = 0;
257 : };
258 :
259 : /************************************************************************/
260 : /* OGRPGTableLayer */
261 : /************************************************************************/
262 :
263 : class OGRPGTableLayer final : public OGRPGLayer
264 : {
265 : OGRPGTableLayer(const OGRPGTableLayer &) = delete;
266 : OGRPGTableLayer &operator=(const OGRPGTableLayer &) = delete;
267 :
268 : static constexpr int USE_COPY_UNSET = -10;
269 :
270 : int bUpdateAccess = false;
271 :
272 : void BuildWhere();
273 : CPLString BuildFields();
274 : void BuildFullQueryStatement();
275 :
276 : char *pszTableName = nullptr;
277 : char *pszSchemaName = nullptr;
278 : char *m_pszTableDescription = nullptr;
279 : CPLString osForcedDescription{};
280 : bool m_bMetadataLoaded = false;
281 : bool m_bMetadataModified = false;
282 : char *pszSqlTableName = nullptr;
283 : int bTableDefinitionValid = -1;
284 :
285 : CPLString osPrimaryKey{};
286 :
287 : int bGeometryInformationSet = false;
288 :
289 : /* Name of the parent table with the geometry definition if it is a derived
290 : * table or NULL */
291 : char *pszSqlGeomParentTableName = nullptr;
292 :
293 : char *pszGeomColForced = nullptr;
294 :
295 : CPLString osQuery{};
296 : CPLString osWHERE{};
297 :
298 : int bLaunderColumnNames = true;
299 : bool m_bUTF8ToASCII = false;
300 : int bPreservePrecision = true;
301 : int bUseCopy = USE_COPY_UNSET;
302 : int bCopyActive = false;
303 : bool bFIDColumnInCopyFields = false;
304 : int bFirstInsertion = true;
305 :
306 : OGRErr CreateFeatureViaCopy(OGRFeature *poFeature);
307 : OGRErr CreateFeatureViaInsert(OGRFeature *poFeature);
308 : CPLString BuildCopyFields();
309 :
310 : int bHasWarnedIncompatibleGeom = false;
311 : void CheckGeomTypeCompatibility(int iGeomField, OGRGeometry *poGeom);
312 :
313 : int bRetrieveFID = true;
314 : int bSkipConflicts = false;
315 : int bHasWarnedAlreadySetFID = false;
316 :
317 : char **papszOverrideColumnTypes = nullptr;
318 : int nForcedSRSId = UNDETERMINED_SRID;
319 : int nForcedGeometryTypeFlags = -1;
320 : bool bCreateSpatialIndexFlag = true;
321 : CPLString osSpatialIndexType = "GIST";
322 : int bInResetReading = false;
323 :
324 : int bAutoFIDOnCreateViaCopy = false;
325 : int bUseCopyByDefault = false;
326 : bool bNeedToUpdateSequence = false;
327 :
328 : int bDeferredCreation = false;
329 : CPLString osCreateTable{};
330 : std::vector<std::string> m_aosDeferredCommentOnColumns{};
331 :
332 : int iFIDAsRegularColumnIndex = -1;
333 :
334 : CPLString m_osFirstGeometryFieldName{};
335 :
336 : std::string m_osLCOGeomType{};
337 :
338 17 : virtual CPLString GetFromClauseForGetExtent() override
339 : {
340 17 : return pszSqlTableName;
341 : }
342 :
343 : OGRErr RunAddGeometryColumn(const OGRPGGeomFieldDefn *poGeomField);
344 : OGRErr RunCreateSpatialIndex(const OGRPGGeomFieldDefn *poGeomField,
345 : int nIdx);
346 :
347 : void UpdateSequenceIfNeeded();
348 :
349 : void LoadMetadata();
350 : void SerializeMetadata();
351 :
352 : public:
353 : OGRPGTableLayer(OGRPGDataSource *, CPLString &osCurrentSchema,
354 : const char *pszTableName, const char *pszSchemaName,
355 : const char *pszDescriptionIn, const char *pszGeomColForced,
356 : int bUpdate);
357 : virtual ~OGRPGTableLayer();
358 :
359 : void SetGeometryInformation(PGGeomColumnDesc *pasDesc, int nGeomFieldCount);
360 :
361 : virtual OGRFeature *GetFeature(GIntBig nFeatureId) override;
362 : virtual void ResetReading() override;
363 : virtual OGRFeature *GetNextFeature() override;
364 : virtual GIntBig GetFeatureCount(int) override;
365 :
366 : OGRErr ISetSpatialFilter(int iGeomField,
367 : const OGRGeometry *poGeom) override;
368 :
369 : virtual OGRErr SetAttributeFilter(const char *) override;
370 :
371 : virtual OGRErr ISetFeature(OGRFeature *poFeature) override;
372 : OGRErr IUpdateFeature(OGRFeature *poFeature, int nUpdatedFieldsCount,
373 : const int *panUpdatedFieldsIdx,
374 : int nUpdatedGeomFieldsCount,
375 : const int *panUpdatedGeomFieldsIdx,
376 : bool bUpdateStyleString) override;
377 : virtual OGRErr DeleteFeature(GIntBig nFID) override;
378 : virtual OGRErr ICreateFeature(OGRFeature *poFeature) override;
379 :
380 : virtual OGRErr CreateField(const OGRFieldDefn *poField,
381 : int bApproxOK = TRUE) override;
382 : virtual OGRErr CreateGeomField(const OGRGeomFieldDefn *poGeomField,
383 : int bApproxOK = TRUE) override;
384 : virtual OGRErr DeleteField(int iField) override;
385 : virtual OGRErr AlterFieldDefn(int iField, OGRFieldDefn *poNewFieldDefn,
386 : int nFlags) override;
387 : virtual OGRErr
388 : AlterGeomFieldDefn(int iGeomFieldToAlter,
389 : const OGRGeomFieldDefn *poNewGeomFieldDefn,
390 : int nFlagsIn) override;
391 :
392 : virtual int TestCapability(const char *) override;
393 :
394 : OGRErr IGetExtent(int iGeomField, OGREnvelope *psExtent,
395 : bool bForce) override;
396 :
397 24 : const char *GetTableName()
398 : {
399 24 : return pszTableName;
400 : }
401 :
402 24 : const char *GetSchemaName()
403 : {
404 24 : return pszSchemaName;
405 : }
406 :
407 : virtual const char *GetFIDColumn() override;
408 :
409 : virtual char **GetMetadataDomainList() override;
410 : virtual char **GetMetadata(const char *pszDomain = "") override;
411 : virtual const char *GetMetadataItem(const char *pszName,
412 : const char *pszDomain = "") override;
413 : virtual CPLErr SetMetadata(char **papszMD,
414 : const char *pszDomain = "") override;
415 : virtual CPLErr SetMetadataItem(const char *pszName, const char *pszValue,
416 : const char *pszDomain = "") override;
417 :
418 : virtual OGRErr Rename(const char *pszNewName) override;
419 :
420 : OGRGeometryTypeCounter *GetGeometryTypes(int iGeomField, int nFlagsGGT,
421 : int &nEntryCountOut,
422 : GDALProgressFunc pfnProgress,
423 : void *pProgressData) override;
424 :
425 : int FindFieldIndex(const char *pszFieldName, int bExactMatch) override;
426 :
427 : // follow methods are not base class overrides
428 226 : void SetLaunderFlag(int bFlag)
429 : {
430 226 : bLaunderColumnNames = bFlag;
431 226 : }
432 :
433 226 : void SetUTF8ToASCIIFlag(bool bFlag)
434 : {
435 226 : m_bUTF8ToASCII = bFlag;
436 226 : }
437 :
438 226 : void SetPrecisionFlag(int bFlag)
439 : {
440 226 : bPreservePrecision = bFlag;
441 226 : }
442 :
443 : void SetOverrideColumnTypes(const char *pszOverrideColumnTypes);
444 :
445 : OGRErr StartCopy();
446 : OGRErr EndCopy();
447 :
448 : int ReadTableDefinition();
449 :
450 72383 : int HasGeometryInformation()
451 : {
452 72383 : return bGeometryInformationSet;
453 : }
454 :
455 : void SetTableDefinition(const char *pszFIDColumnName,
456 : const char *pszGFldName, OGRwkbGeometryType eType,
457 : const char *pszGeomType, int nSRSId,
458 : int GeometryTypeFlags);
459 :
460 : void SetForcedSRSId(int nForcedSRSIdIn)
461 : {
462 : nForcedSRSId = nForcedSRSIdIn;
463 : }
464 :
465 226 : void SetForcedGeometryTypeFlags(int GeometryTypeFlagsIn)
466 : {
467 226 : nForcedGeometryTypeFlags = GeometryTypeFlagsIn;
468 226 : }
469 :
470 226 : void SetCreateSpatialIndex(bool bFlag, const char *pszSpatialIndexType)
471 : {
472 226 : bCreateSpatialIndexFlag = bFlag;
473 226 : osSpatialIndexType = pszSpatialIndexType;
474 226 : }
475 :
476 : void SetForcedDescription(const char *pszDescriptionIn);
477 :
478 226 : void AllowAutoFIDOnCreateViaCopy()
479 : {
480 226 : bAutoFIDOnCreateViaCopy = TRUE;
481 226 : }
482 :
483 220 : void SetUseCopy()
484 : {
485 220 : bUseCopy = TRUE;
486 220 : bUseCopyByDefault = TRUE;
487 220 : }
488 :
489 : void SetDeferredCreation(int bDeferredCreationIn,
490 : const std::string &osCreateTable);
491 : OGRErr RunDeferredCreationIfNecessary();
492 :
493 : virtual void ResolveSRID(const OGRPGGeomFieldDefn *poGFldDefn) override;
494 : };
495 :
496 : /************************************************************************/
497 : /* OGRPGResultLayer */
498 : /************************************************************************/
499 :
500 : class OGRPGResultLayer final : public OGRPGLayer
501 : {
502 : OGRPGResultLayer(const OGRPGResultLayer &) = delete;
503 : OGRPGResultLayer &operator=(const OGRPGResultLayer &) = delete;
504 :
505 : void BuildFullQueryStatement();
506 :
507 : char *pszRawStatement = nullptr;
508 :
509 : char *pszGeomTableName = nullptr;
510 : char *pszGeomTableSchemaName = nullptr;
511 :
512 : CPLString osWHERE{};
513 :
514 6 : virtual CPLString GetFromClauseForGetExtent() override
515 : {
516 6 : CPLString osStr("(");
517 6 : osStr += pszRawStatement;
518 6 : osStr += ")";
519 6 : return osStr;
520 : }
521 :
522 : public:
523 : OGRPGResultLayer(OGRPGDataSource *, const char *pszRawStatement,
524 : PGresult *hInitialResult);
525 : virtual ~OGRPGResultLayer();
526 :
527 : virtual void ResetReading() override;
528 : virtual GIntBig GetFeatureCount(int) override;
529 :
530 : OGRErr ISetSpatialFilter(int iGeomField,
531 : const OGRGeometry *poGeom) override;
532 :
533 : virtual int TestCapability(const char *) override;
534 :
535 : virtual OGRFeature *GetNextFeature() override;
536 :
537 : virtual void ResolveSRID(const OGRPGGeomFieldDefn *poGFldDefn) override;
538 : };
539 :
540 : /************************************************************************/
541 : /* OGRPGDataSource */
542 : /************************************************************************/
543 :
544 432 : class OGRPGDataSource final : public GDALDataset
545 : {
546 : OGRPGDataSource(const OGRPGDataSource &) = delete;
547 : OGRPGDataSource &operator=(const OGRPGDataSource &) = delete;
548 :
549 : typedef struct
550 : {
551 : int nMajor;
552 : int nMinor;
553 : int nRelease;
554 : } PGver;
555 :
556 : OGRPGTableLayer **papoLayers = nullptr;
557 : int nLayers = 0;
558 :
559 : bool m_bUTF8ClientEncoding = false;
560 :
561 : int bDSUpdate = false;
562 : int bHavePostGIS = false;
563 : int bHaveGeography = false;
564 :
565 : bool bUserTransactionActive = false;
566 : int bSavePointActive = false;
567 : int nSoftTransactionLevel = 0;
568 :
569 : PGconn *hPGConn = nullptr;
570 :
571 : OGRErr DeleteLayer(int iLayer) override;
572 :
573 : Oid nGeometryOID = static_cast<Oid>(0);
574 : Oid nGeographyOID = static_cast<Oid>(0);
575 :
576 : // We maintain a list of known SRID to reduce the number of trips to
577 : // the database to get SRSes.
578 : std::map<int,
579 : std::unique_ptr<OGRSpatialReference, OGRSpatialReferenceReleaser>>
580 : m_oSRSCache{};
581 :
582 : OGRPGTableLayer *poLayerInCopyMode = nullptr;
583 :
584 : static void OGRPGDecodeVersionString(PGver *psVersion, const char *pszVer);
585 :
586 : CPLString osCurrentSchema{};
587 : CPLString GetCurrentSchema();
588 :
589 : // Actual value will be auto-detected if PostGIS >= 2.0 detected.
590 : int nUndefinedSRID = -1;
591 :
592 : char *pszForcedTables = nullptr;
593 : char **papszSchemaList = nullptr;
594 : int bHasLoadTables = false;
595 : CPLString osActiveSchema{};
596 : int bListAllTables = false;
597 : bool m_bSkipViews = false;
598 :
599 : bool m_bOgrSystemTablesMetadataTableExistenceTested = false;
600 : bool m_bOgrSystemTablesMetadataTableFound = false;
601 :
602 : bool m_bCreateMetadataTableIfNeededRun = false;
603 : bool m_bCreateMetadataTableIfNeededSuccess = false;
604 :
605 : bool m_bHasWritePermissionsOnMetadataTableRun = false;
606 : bool m_bHasWritePermissionsOnMetadataTableSuccess = false;
607 :
608 : void LoadTables();
609 :
610 : CPLString osDebugLastTransactionCommand{};
611 : OGRErr DoTransactionCommand(const char *pszCommand);
612 :
613 : OGRErr FlushSoftTransaction();
614 :
615 : OGRErr FlushCacheWithRet(bool bAtClosing);
616 :
617 : std::optional<std::string> FindSchema(const char *pszSchemaNameIn);
618 :
619 : bool IsSuperUser();
620 : bool OGRSystemTablesEventTriggerExists();
621 :
622 : public:
623 : PGver sPostgreSQLVersion = {0, 0, 0};
624 : PGver sPostGISVersion = {0, 0, 0};
625 :
626 : int bUseBinaryCursor = false;
627 : int bBinaryTimeFormatIsInt8 = false;
628 :
629 : bool m_bHasGeometryColumns = false;
630 : bool m_bHasSpatialRefSys = false;
631 :
632 747 : bool HavePostGIS() const
633 : {
634 747 : return bHavePostGIS;
635 : }
636 :
637 130 : int GetUndefinedSRID() const
638 : {
639 130 : return nUndefinedSRID;
640 : }
641 :
642 3739 : bool IsUTF8ClientEncoding() const
643 : {
644 3739 : return m_bUTF8ClientEncoding;
645 : }
646 :
647 : public:
648 : OGRPGDataSource();
649 : virtual ~OGRPGDataSource();
650 :
651 248140 : PGconn *GetPGConn()
652 : {
653 248140 : return hPGConn;
654 : }
655 :
656 : int FetchSRSId(const OGRSpatialReference *poSRS);
657 : const OGRSpatialReference *FetchSRS(int nSRSId);
658 : static OGRErr InitializeMetadataTables();
659 :
660 : int Open(const char *, int bUpdate, int bTestOpen, char **papszOpenOptions);
661 : OGRPGTableLayer *
662 : OpenTable(CPLString &osCurrentSchema, const char *pszTableName,
663 : const char *pszSchemaName, const char *pszDescription,
664 : const char *pszGeomColForced, int bUpdate, int bTestOpen);
665 :
666 : int GetLayerCount() override;
667 : OGRLayer *GetLayer(int) override;
668 : OGRLayer *GetLayerByName(const char *pszName) override;
669 :
670 : virtual CPLErr FlushCache(bool bAtClosing) override;
671 :
672 : OGRLayer *ICreateLayer(const char *pszName,
673 : const OGRGeomFieldDefn *poGeomFieldDefn,
674 : CSLConstList papszOptions) override;
675 :
676 : int TestCapability(const char *) override;
677 :
678 : virtual OGRErr StartTransaction(int bForce = FALSE) override;
679 : virtual OGRErr CommitTransaction() override;
680 : virtual OGRErr RollbackTransaction() override;
681 :
682 : OGRErr SoftStartTransaction();
683 : OGRErr SoftCommitTransaction();
684 : OGRErr SoftRollbackTransaction();
685 :
686 421 : Oid GetGeometryOID()
687 : {
688 421 : return nGeometryOID;
689 : }
690 :
691 471 : Oid GetGeographyOID()
692 : {
693 471 : return nGeographyOID;
694 : }
695 :
696 : virtual OGRLayer *ExecuteSQL(const char *pszSQLCommand,
697 : OGRGeometry *poSpatialFilter,
698 : const char *pszDialect) override;
699 : virtual OGRErr AbortSQL() override;
700 : virtual void ReleaseResultSet(OGRLayer *poLayer) override;
701 :
702 : virtual const char *GetMetadataItem(const char *pszKey,
703 : const char *pszDomain) override;
704 :
705 : int UseCopy();
706 : void StartCopy(OGRPGTableLayer *poPGLayer);
707 : OGRErr EndCopy();
708 :
709 16 : bool IsUserTransactionActive()
710 : {
711 16 : return bUserTransactionActive;
712 : }
713 :
714 : bool CreateMetadataTableIfNeeded();
715 : bool HasOgrSystemTablesMetadataTable();
716 : bool HasWritePermissionsOnMetadataTable();
717 : };
718 :
719 : #endif /* ndef OGR_PG_H_INCLUDED */
|