ogrmysqldatasource.cpp

来自「支持各种栅格图像和矢量图像读取的库」· C++ 代码 · 共 1,104 行 · 第 1/3 页

CPP
1,104
字号
/****************************************************************************** * $Id: ogrmysqldatasource.cpp 10646 2007-01-18 02:38:10Z warmerdam $ * * Project:  OpenGIS Simple Features Reference Implementation * Purpose:  Implements OGRMySQLDataSource class. * Author:   Frank Warmerdam, warmerdam@pobox.com * Author:   Howard Butler, hobu@hobu.net * ****************************************************************************** * Copyright (c) 2004, Frank Warmerdam <warmerdam@pobox.com> * * Permission is hereby granted, free of charge, to any person obtaining a * copy of this software and associated documentation files (the "Software"), * to deal in the Software without restriction, including without limitation * the rights to use, copy, modify, merge, publish, distribute, sublicense, * and/or sell copies of the Software, and to permit persons to whom the * Software is furnished to do so, subject to the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER * DEALINGS IN THE SOFTWARE. ****************************************************************************/#include <string>#include "ogr_mysql.h"#include <my_sys.h>#include "cpl_conv.h"#include "cpl_string.h"CPL_CVSID("$Id: ogrmysqldatasource.cpp 10646 2007-01-18 02:38:10Z warmerdam $");/************************************************************************//*                         OGRMySQLDataSource()                         *//************************************************************************/OGRMySQLDataSource::OGRMySQLDataSource(){    pszName = NULL;    papoLayers = NULL;    nLayers = 0;    hConn = 0;    nSoftTransactionLevel = 0;    nKnownSRID = 0;    panSRID = NULL;    papoSRS = NULL;    poLongResultLayer = NULL;}/************************************************************************//*                        ~OGRMySQLDataSource()                         *//************************************************************************/OGRMySQLDataSource::~OGRMySQLDataSource(){    int         i;    InterruptLongResult();    CPLFree( pszName );    for( i = 0; i < nLayers; i++ )        delete papoLayers[i];        CPLFree( papoLayers );    if( hConn != NULL )        mysql_close( hConn );    for( i = 0; i < nKnownSRID; i++ )    {        if( papoSRS[i] != NULL )            papoSRS[i]->Release();    }    CPLFree( panSRID );    CPLFree( papoSRS );}/************************************************************************//*                            ReportError()                             *//************************************************************************/void OGRMySQLDataSource::ReportError( const char *pszDescription ){    if( pszDescription )        CPLError( CE_Failure, CPLE_AppDefined,                   "MySQL error message:%s Description: %s",                   mysql_error( hConn ),                   pszDescription );    else        CPLError( CE_Failure, CPLE_AppDefined,                   "%s", mysql_error( hConn ) );}/************************************************************************//*                                Open()                                *//************************************************************************/int OGRMySQLDataSource::Open( const char * pszNewName, int bUpdate,                              int bTestOpen ){    CPLAssert( nLayers == 0 );/* -------------------------------------------------------------------- *//*      Verify MySQL prefix.                                            *//* -------------------------------------------------------------------- */    if( !EQUALN(pszNewName,"MYSQL:",6) )    {        if( !bTestOpen )            CPLError( CE_Failure, CPLE_AppDefined,                       "%s does not conform to MySQL naming convention,"                      " MYSQL:dbname[, user=..][,password=..][,host=..][,port=..][tables=table;table;...]",                      pszNewName );        return FALSE;    }    /* -------------------------------------------------------------------- *//*      Use options process to get .my.cnf file contents.               *//* -------------------------------------------------------------------- */    int nPort = 0, i;    char **papszTableNames=NULL;    std::string oHost, oPassword, oUser, oDB;    char *apszArgv[2] = { "org", NULL };    char **papszArgv = apszArgv;    int  nArgc = 1;    const char *client_groups[] = {"client", "ogr", NULL };    my_init(); // I hope there is no problem with calling this multiple times!    load_defaults( "my", client_groups, &nArgc, &papszArgv );    for( i = 0; i < nArgc; i++ )    {        if( EQUALN(papszArgv[i],"--user=",7) )            oUser = papszArgv[i] + 7;        else if( EQUALN(papszArgv[i],"--host=",7) )            oHost = papszArgv[i] + 7;        else if( EQUALN(papszArgv[i],"--password=",11) )            oPassword = papszArgv[i] + 11;        else if( EQUALN(papszArgv[i],"--port=",7) )            nPort = atoi(papszArgv[i] + 7);    }    // cleanup    free_defaults( papszArgv );/* -------------------------------------------------------------------- *//*      Parse out connection information.                               *//* -------------------------------------------------------------------- */    char **papszItems = CSLTokenizeString2( pszNewName+6, ",",                                             CSLT_HONOURSTRINGS );    if( CSLCount(papszItems) < 1 )    {        CSLDestroy( papszItems );        CPLError( CE_Failure, CPLE_AppDefined,                   "MYSQL: request missing databasename." );        return FALSE;    }    oDB = papszItems[0];    for( i = 1; papszItems[i] != NULL; i++ )    {        if( EQUALN(papszItems[i],"user=",5) )            oUser = papszItems[i] + 5;        else if( EQUALN(papszItems[i],"password=",9) )            oPassword = papszItems[i] + 9;        else if( EQUALN(papszItems[i],"host=",5) )            oHost = papszItems[i] + 5;        else if( EQUALN(papszItems[i],"port=",5) )            nPort = atoi(papszItems[i] + 5);        else if( EQUALN(papszItems[i],"tables=",7) )        {            papszTableNames = CSLTokenizeStringComplex(                 papszItems[i] + 7, ";", FALSE, FALSE );        }        else            CPLError( CE_Warning, CPLE_AppDefined,                       "'%s' in MYSQL datasource definition not recognised and ignored.", papszItems[i] );    }    CSLDestroy( papszItems );/* -------------------------------------------------------------------- *//*      Try to establish connection.                                    *//* -------------------------------------------------------------------- */    hConn = mysql_init( NULL );/* -------------------------------------------------------------------- *//*      Set the timeout for the connection if the users has specified.  *//* -------------------------------------------------------------------- */    const char *pszTimeoutLength =         CPLGetConfigOption( "MYSQL_TIMEOUT", "0" );      unsigned int timeout = atoi(pszTimeoutLength);            mysql_options(hConn, MYSQL_OPT_CONNECT_TIMEOUT, (char*)&timeout);        if( hConn == NULL )    {        CPLError( CE_Failure, CPLE_AppDefined,                  "mysql_init() failed." );    }    if( hConn        && mysql_real_connect( hConn,                                oHost.length() ? oHost.c_str() : NULL,                               oUser.length() ? oUser.c_str() : NULL,                               oPassword.length() ? oPassword.c_str() : NULL,                               oDB.length() ? oDB.c_str() : NULL,                               nPort, NULL, CLIENT_INTERACTIVE ) == NULL )    {        CPLError( CE_Failure, CPLE_AppDefined,                  "MySQL connect failed for: %s\n%s",                   pszNewName + 6, mysql_error( hConn ) );        mysql_close( hConn );        hConn = NULL;    }    if( hConn == NULL )    {        CSLDestroy( papszTableNames );        return FALSE;    }        pszName = CPLStrdup( pszNewName );        bDSUpdate = bUpdate;/* -------------------------------------------------------------------- *//*      Get a list of available tables.                                 *//* -------------------------------------------------------------------- */    if( papszTableNames == NULL )    {        MYSQL_RES *hResultSet;        MYSQL_ROW papszRow;        if( mysql_query( hConn, "SHOW TABLES" ) )        {            ReportError( "SHOW TABLES Failed" );            return FALSE;        }        hResultSet = mysql_store_result( hConn );        if( hResultSet == NULL )        {            ReportError( "mysql_store_result() failed on SHOW TABLES result.");            return FALSE;        }            while( (papszRow = mysql_fetch_row( hResultSet )) != NULL )        {            if( papszRow[0] == NULL )                continue;            if( EQUAL(papszRow[0],"spatial_ref_sys")                || EQUAL(papszRow[0],"geometry_columns") )                continue;            papszTableNames = CSLAddString(papszTableNames, papszRow[0] );        }        mysql_free_result( hResultSet );    }/* -------------------------------------------------------------------- *//*      Get the schema of the available tables.                         *//* -------------------------------------------------------------------- */    int iRecord;    for( iRecord = 0;          papszTableNames != NULL && papszTableNames[iRecord] != NULL;         iRecord++ )    {        //  FIXME: This should be fixed to deal with tables         //  for which we can't open because the name is bad/         OpenTable( papszTableNames[iRecord], bUpdate, FALSE );    }    CSLDestroy( papszTableNames );        return nLayers > 0 || bUpdate;}/************************************************************************//*                             OpenTable()                              *//************************************************************************/int OGRMySQLDataSource::OpenTable( const char *pszNewName, int bUpdate,                                int bTestOpen ){/* -------------------------------------------------------------------- *//*      Create the layer object.                                        *//* -------------------------------------------------------------------- */    OGRMySQLTableLayer  *poLayer;    OGRErr eErr;    poLayer = new OGRMySQLTableLayer( this, pszNewName, bUpdate );    eErr = poLayer->Initialize(pszNewName);    if (eErr == OGRERR_FAILURE)        return FALSE;/* -------------------------------------------------------------------- *//*      Add layer to data source layer list.                            *//* -------------------------------------------------------------------- */    papoLayers = (OGRMySQLLayer **)        CPLRealloc( papoLayers,  sizeof(OGRMySQLLayer *) * (nLayers+1) );    papoLayers[nLayers++] = poLayer;        return TRUE;}/************************************************************************//*                           TestCapability()                           *//************************************************************************/int OGRMySQLDataSource::TestCapability( const char * pszCap ){	    if( EQUAL(pszCap, ODsCCreateLayer) )        return TRUE;	if( EQUAL(pszCap, ODsCDeleteLayer))		return TRUE;    else        return FALSE;}/************************************************************************//*                              GetLayer()                              *//************************************************************************/OGRLayer *OGRMySQLDataSource::GetLayer( int iLayer ){    if( iLayer < 0 || iLayer >= nLayers )        return NULL;    else        return papoLayers[iLayer];}/************************************************************************//*                      InitializeMetadataTables()                      *//*                                                                      *//*      Create the metadata tables (SPATIAL_REF_SYS and                 *//*      GEOMETRY_COLUMNS). This method "does no harm" if the tables     *//*      exist and can be called at will.                                *//************************************************************************/OGRErr OGRMySQLDataSource::InitializeMetadataTables(){

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?