diff --git a/autotest/ogr/ogr_openfilegdb_write.py b/autotest/ogr/ogr_openfilegdb_write.py index 2cd1db7dc95b..ad2ccf036bb6 100755 --- a/autotest/ogr/ogr_openfilegdb_write.py +++ b/autotest/ogr/ogr_openfilegdb_write.py @@ -4265,7 +4265,7 @@ def test_ogr_openfilegdb_write_new_datetime_types(tmp_vsimem): lyr = ds.GetLayerByName("date_types") lyr_defn = lyr.GetLayerDefn() - fld_defn = lyr_defn.GetFieldDefn(lyr_defn.GetFieldIndex("date_")) + fld_defn = lyr_defn.GetFieldDefn(lyr_defn.GetFieldIndex("date")) assert fld_defn.GetType() == ogr.OFTDateTime assert fld_defn.GetDefault() == "'2023/02/01 04:05:06'" @@ -4282,13 +4282,13 @@ def test_ogr_openfilegdb_write_new_datetime_types(tmp_vsimem): assert fld_defn.GetDefault() == "'2023/02/01 04:05:06.000+06:00'" f = lyr.GetNextFeature() - assert f["date_"] == "2023/11/29 13:14:15+00" + assert f["date"] == "2023/11/29 13:14:15+00" assert f["date_only"] == "2023/11/29" assert f["time_only"] == "13:14:15" assert f["timestamp_offset"] == "2023/11/29 13:14:15-05" f = lyr.GetNextFeature() - assert f["date_"] == "2023/12/31 00:01:01+00" + assert f["date"] == "2023/12/31 00:01:01+00" assert f["date_only"] == "2023/12/31" assert f["time_only"] == "00:01:01" assert f["timestamp_offset"] == "2023/12/31 00:01:01+10" @@ -4297,13 +4297,13 @@ def test_ogr_openfilegdb_write_new_datetime_types(tmp_vsimem): lyr_defn = lyr.GetLayerDefn() f = lyr.GetNextFeature() - assert f["date_"] == "2023/11/29 13:14:15.678+00" + assert f["date"] == "2023/11/29 13:14:15.678+00" assert f["date_only"] == "2023/11/29" assert f["time_only"] == "13:14:15" assert f["timestamp_offset"] == "2023/11/29 13:14:15-05" f = lyr.GetNextFeature() - assert f["date_"] == "2023/12/31 00:01:01.001+00" + assert f["date"] == "2023/12/31 00:01:01.001+00" assert f["date_only"] == "2023/12/31" assert f["time_only"] == "00:01:01" assert f["timestamp_offset"] == "2023/12/31 00:01:01+10" diff --git a/ogr/ogrsf_frmts/filegdb/FGdbUtils.cpp b/ogr/ogrsf_frmts/filegdb/FGdbUtils.cpp index 3827e578a893..75e348747d3f 100644 --- a/ogr/ogrsf_frmts/filegdb/FGdbUtils.cpp +++ b/ogr/ogrsf_frmts/filegdb/FGdbUtils.cpp @@ -18,6 +18,7 @@ #include "ogr_api.h" #include "ogrpgeogeometry.h" +#include "filegdb_reserved_keywords.h" using std::string; @@ -531,21 +532,11 @@ std::wstring FGDBEscapeReservedKeywords(const std::wstring &name) std::string newName = WStringToString(name); std::string upperName = CPLString(newName).toupper(); - // From ESRI docs - static const char *const RESERVED_WORDS[] = { - FGDB_OID_NAME, "ADD", "ALTER", "AND", "AS", "ASC", - "BETWEEN", "BY", "COLUMN", "CREATE", "DATE", "DELETE", - "DESC", "DROP", "EXISTS", "FOR", "FROM", "IN", - "INSERT", "INTO", "IS", "LIKE", "NOT", "NULL", - "OR", "ORDER", "SELECT", "SET", "TABLE", "UPDATE", - "VALUES", "WHERE", nullptr}; - // Append an underscore to any FGDB reserved words used as field names // This is the same behavior ArcCatalog follows. - for (int i = 0; RESERVED_WORDS[i] != nullptr; i++) + for (const char *pszKeyword : apszRESERVED_WORDS) { - const char *w = RESERVED_WORDS[i]; - if (upperName == w) + if (upperName == pszKeyword) { newName += '_'; break; diff --git a/ogr/ogrsf_frmts/openfilegdb/filegdb_reserved_keywords.h b/ogr/ogrsf_frmts/openfilegdb/filegdb_reserved_keywords.h new file mode 100644 index 000000000000..1a006da3356d --- /dev/null +++ b/ogr/ogrsf_frmts/openfilegdb/filegdb_reserved_keywords.h @@ -0,0 +1,24 @@ +/****************************************************************************** + * + * Project: OpenGIS Simple Features Reference Implementation + * Purpose: List of reserver keywords for File Geodatabase + * Author: Even Rouault, + * + ****************************************************************************** + * Copyright (c) 2024, Even Rouault, + * + * SPDX-License-Identifier: MIT + ****************************************************************************/ + +#ifndef FILEGDB_RESERVED_KEYWORDS_H +#define FILEGDB_RESERVED_KEYWORDS_H + +// from https://support.esri.com/en-us/knowledge-base/what-are-the-reserved-words-for-esri-s-file-geodatabase-000010906 +static constexpr const char *const apszRESERVED_WORDS[] = { + "ADD", "ALTER", "AND", "BETWEEN", "BY", "COLUMN", "CREATE", + "DELETE", "DROP", "EXISTS", "FOR", "FROM", "GROUP", "IN", + "INSERT", "INTO", "IS", "LIKE", "NOT", "NULL", "OR", + "ORDER", "SELECT", "SET", "TABLE", "UPDATE", "VALUES", "WHERE", +}; + +#endif // FILEGDB_RESERVED_KEYWORDS_H diff --git a/ogr/ogrsf_frmts/openfilegdb/ogropenfilegdblayer_write.cpp b/ogr/ogrsf_frmts/openfilegdb/ogropenfilegdblayer_write.cpp index 8b487c83864b..78f7399ca8e7 100644 --- a/ogr/ogrsf_frmts/openfilegdb/ogropenfilegdblayer_write.cpp +++ b/ogr/ogrsf_frmts/openfilegdb/ogropenfilegdblayer_write.cpp @@ -40,6 +40,7 @@ #include "filegdbtable.h" #include "filegdbtable_priv.h" #include "filegdb_coordprec_write.h" +#include "filegdb_reserved_keywords.h" /*************************************************************************/ /* StringToWString() */ @@ -137,20 +138,11 @@ static std::wstring EscapeReservedKeywords(const std::wstring &name) std::string newName = WStringToString(name); std::string upperName = CPLString(newName).toupper(); - // From ESRI docs - static const char *const RESERVED_WORDS[] = { - "OBJECTID", "ADD", "ALTER", "AND", "AS", "ASC", "BETWEEN", - "BY", "COLUMN", "CREATE", "DATE", "DELETE", "DESC", "DROP", - "EXISTS", "FOR", "FROM", "IN", "INSERT", "INTO", "IS", - "LIKE", "NOT", "NULL", "OR", "ORDER", "SELECT", "SET", - "TABLE", "UPDATE", "VALUES", "WHERE", nullptr}; - // Append an underscore to any FGDB reserved words used as field names // This is the same behavior ArcCatalog follows. - for (int i = 0; RESERVED_WORDS[i] != nullptr; i++) + for (const char *pszKeyword : apszRESERVED_WORDS) { - const char *w = RESERVED_WORDS[i]; - if (upperName == w) + if (upperName == pszKeyword) { newName += '_'; break;